Skip to content

Commit

Permalink
Merge fa8eb69 into fc13e7a
Browse files Browse the repository at this point in the history
  • Loading branch information
zombieJ committed Jan 16, 2019
2 parents fc13e7a + fa8eb69 commit 76b24ce
Show file tree
Hide file tree
Showing 10 changed files with 179 additions and 16 deletions.
4 changes: 4 additions & 0 deletions README.md
Expand Up @@ -306,6 +306,10 @@ scrollable tab bar, in addition to tab bar props, extra props:

scrollable tab bar with ink indicator, same with tab bar and ink bar and scrollable bar props.

| name | type | default | description |
|------|------|---------|-------------|
| children | (node) => node | - | Customize tab bar node |

### lib/SwipeableInkTabBar (Use for Mobile)

swipeable tab bar with ink indicator, same with tab bar/ink bar props, and below is the additional props.
Expand Down
2 changes: 0 additions & 2 deletions examples/activeKey.js
@@ -1,7 +1,6 @@
/* eslint react/no-multi-comp:0, no-console:0, react/prop-types:0 */
import 'rc-tabs/assets/index.less';
import React from 'react';
import Sortable from 'react-sortablejs';
import ReactDOM from 'react-dom';
import Tabs, { TabPane } from 'rc-tabs';
import TabContent from 'rc-tabs/lib/SwipeableTabContent';
Expand Down Expand Up @@ -53,7 +52,6 @@ class Demo extends React.Component {
<Tabs
renderTabBar={() => <ScrollableInkTabBar onTabClick={this.onTabClick}/>}
renderTabContent={() => <TabContent animatedWithMargin />}
navWrapper={(content) => <Sortable>{content}</Sortable>}
activeKey={this.state.activeKey}
onChange={this.onChange}
>
Expand Down
1 change: 1 addition & 0 deletions examples/dnd.html
@@ -0,0 +1 @@
placeholder
141 changes: 141 additions & 0 deletions examples/dnd.js
@@ -0,0 +1,141 @@
/* eslint react/no-multi-comp:0, no-console:0, react/prop-types:0 */
import 'rc-tabs/assets/index.less';
import React from 'react';
import HTML5Backend from 'react-dnd-html5-backend'
import ReactDOM from 'react-dom';
import Tabs, { TabPane } from 'rc-tabs';
import update from 'immutability-helper';
import TabContent from 'rc-tabs/lib/SwipeableTabContent';
import ScrollableInkTabBar from 'rc-tabs/lib/ScrollableInkTabBar';
import {
DragSource,
DropTarget,
DragDropContextProvider,
} from 'react-dnd';

// Drag & Drop node
class TabNode extends React.Component {
render() {
const {
connectDragSource,
connectDropTarget,
children,
} = this.props

return connectDragSource(
connectDropTarget(children),
);
}
}

const cardTarget = {
drop(props, monitor) {
const dragKey = monitor.getItem().index;
const hoverKey = props.index;

if (dragKey === hoverKey) {
return;
}

props.moveTabNode(dragKey, hoverKey);
monitor.getItem().index = hoverKey;
},
};

const cardSource = {
beginDrag(props) {
return {
id: props.id,
index: props.index,
}
},
};

const WrapTabNode = DropTarget(
'DND_NODE',
cardTarget,
(connect) => ({
connectDropTarget: connect.dropTarget(),
}),
)(
DragSource(
'DND_NODE',
cardSource,
(connect, monitor) => ({
connectDragSource: connect.dragSource(),
isDragging: monitor.isDragging(),
}),
)(TabNode),
);

// Demo
class Demo extends React.Component {
state = {
activeKey: '1',
tabs: ['1', '2', '3'],
};

onChange = (activeKey) => {
console.log(`onChange ${activeKey}`);
this.setState({
activeKey,
});
}

onTabClick = (key) => {
console.log(`onTabClick ${key}`);
if (key === this.state.activeKey) {
this.setState({
activeKey: '',
});
}
}

moveTabNode = (dragKey, hoverKey) => {
const { tabs } = this.state;
const dragIndex = tabs.indexOf(dragKey);
const hoverIndex = tabs.indexOf(hoverKey);
const dragTab = this.state.tabs[dragIndex];
this.setState(
update(this.state, {
tabs: {
$splice: [[dragIndex, 1], [hoverIndex, 0, dragTab]],
},
}),
);
};

renderTabBarNode = (node) => {
return (
<WrapTabNode key={node.key} index={node.key} moveTabNode={this.moveTabNode}>{node}</WrapTabNode>
);
};

render() {
return (
<DragDropContextProvider backend={HTML5Backend}>
<div style={{ margin: 20 }}>
<h1>Simple Tabs</h1>
<Tabs
renderTabBar={() => (
<ScrollableInkTabBar onTabClick={this.onTabClick}>
{this.renderTabBarNode}
</ScrollableInkTabBar>
)}
renderTabContent={() => <TabContent animatedWithMargin />}
activeKey={this.state.activeKey}
onChange={this.onChange}
>
{this.state.tabs.map(id => (
<TabPane tab={`tab ${id}`} key={id}>
{id}
</TabPane>
))}
</Tabs>
</div>
</DragDropContextProvider>
);
}
}

ReactDOM.render(<Demo />, document.getElementById('__react-content'));
4 changes: 3 additions & 1 deletion package.json
Expand Up @@ -74,16 +74,18 @@
"enzyme-to-json": "^3.3.4",
"fastclick": "~1.0.6",
"history": "^1.17.0",
"immutability-helper": "^2.9.0",
"jest": "^23.6.0",
"pre-commit": "1.x",
"preact": "^8.2.1",
"preact-compat": "^3.16.0",
"rc-test": "^6.0.1",
"rc-tools": "8.x",
"react": "^16.0.0",
"react-dnd": "^7.0.2",
"react-dnd-html5-backend": "^7.0.2",
"react-dom": "^16.0.0",
"react-router": "^3.0.0",
"react-sortablejs": "^1.3.6",
"react-test-renderer": "^16.0.0",
"sortablejs": "^1.7.0"
},
Expand Down
15 changes: 11 additions & 4 deletions src/ScrollableInkTabBar.js
@@ -1,5 +1,6 @@
/* eslint-disable react/prefer-stateless-function */
import React from 'react';
import PropTypes from 'prop-types';
import InkTabBarNode from './InkTabBarNode';
import TabBarTabsNode from './TabBarTabsNode';
import TabBarRootNode from './TabBarRootNode';
Expand All @@ -8,17 +9,23 @@ import SaveRef from './SaveRef';

export default class ScrollableInkTabBar extends React.Component {
render() {
const { children: renderTabBarNode, ...restProps } = this.props;

return (
<SaveRef>
{(saveRef, getRef) => (
<TabBarRootNode saveRef={saveRef} {...this.props}>
<ScrollableTabBarNode saveRef={saveRef} getRef={getRef} {...this.props}>
<TabBarTabsNode saveRef={saveRef} {...this.props} />
<InkTabBarNode saveRef={saveRef} getRef={getRef} {...this.props} />
<TabBarRootNode saveRef={saveRef} {...restProps}>
<ScrollableTabBarNode saveRef={saveRef} getRef={getRef} {...restProps}>
<TabBarTabsNode saveRef={saveRef} renderTabBarNode={renderTabBarNode} {...restProps} />
<InkTabBarNode saveRef={saveRef} getRef={getRef} {...restProps} />
</ScrollableTabBarNode>
</TabBarRootNode>
)}
</SaveRef>
);
}
}

ScrollableInkTabBar.propTypes = {
children: PropTypes.func,
};
1 change: 1 addition & 0 deletions src/ScrollableTabBarNode.js
Expand Up @@ -311,6 +311,7 @@ export default class ScrollableTabBarNode extends React.Component {
}

ScrollableTabBarNode.propTypes = {
activeKey: PropTypes.string,
getRef: PropTypes.func.isRequired,
saveRef: PropTypes.func.isRequired,
tabBarPosition: PropTypes.oneOf(['left', 'right', 'top', 'bottom']),
Expand Down
11 changes: 10 additions & 1 deletion src/TabBarTabsNode.js
Expand Up @@ -12,6 +12,7 @@ export default class TabBarTabsNode extends React.Component {
tabBarGutter,
saveRef,
tabBarPosition,
renderTabBarNode,
} = this.props;
const rst = [];

Expand Down Expand Up @@ -40,7 +41,8 @@ export default class TabBarTabsNode extends React.Component {
[isVertical(tabBarPosition) ? 'marginBottom' : 'marginRight']: gutter,
};
warning('tab' in child.props, 'There must be `tab` property on children of Tabs.');
rst.push(

let node = (
<div
role="tab"
aria-disabled={child.props.disabled ? 'true' : 'false'}
Expand All @@ -54,6 +56,12 @@ export default class TabBarTabsNode extends React.Component {
{child.props.tab}
</div>
);

if (renderTabBarNode) {
node = renderTabBarNode(node);
}

rst.push(node);
});

return (
Expand All @@ -71,6 +79,7 @@ TabBarTabsNode.propTypes = {
tabBarGutter: PropTypes.number,
onTabClick: PropTypes.func,
saveRef: PropTypes.func,
renderTabBarNode: PropTypes.func,
tabBarPosition: PropTypes.string,
};

Expand Down
8 changes: 4 additions & 4 deletions tests/__snapshots__/index.spec.js.snap
Expand Up @@ -73,7 +73,7 @@ exports[`rc-tabs should render Tabs with correct DOM structure 1`] = `
</div>
<div
role="presentation"
style="width:0;height:0;overflow:hidden"
style="width:0;height:0;overflow:hidden;position:absolute"
tabindex="0"
/>
<div
Expand All @@ -92,13 +92,13 @@ exports[`rc-tabs should render Tabs with correct DOM structure 1`] = `
>
<div
role="presentation"
style="width:0;height:0;overflow:hidden"
style="width:0;height:0;overflow:hidden;position:absolute"
tabindex="0"
/>
second
<div
role="presentation"
style="width:0;height:0;overflow:hidden"
style="width:0;height:0;overflow:hidden;position:absolute"
tabindex="0"
/>
</div>
Expand All @@ -110,7 +110,7 @@ exports[`rc-tabs should render Tabs with correct DOM structure 1`] = `
</div>
<div
role="presentation"
style="width:0;height:0;overflow:hidden"
style="width:0;height:0;overflow:hidden;position:absolute"
tabindex="0"
/>
</div>
Expand Down
8 changes: 4 additions & 4 deletions tests/__snapshots__/swipe.spec.js.snap
Expand Up @@ -133,7 +133,7 @@ exports[`rc-swipeable-tabs should render Slider with correct DOM structure 1`] =
</div>
<div
role="presentation"
style="width:0;height:0;overflow:hidden"
style="width:0;height:0;overflow:hidden;position:absolute"
tabindex="0"
/>
<div
Expand Down Expand Up @@ -187,7 +187,7 @@ exports[`rc-swipeable-tabs should render Slider with correct DOM structure 1`] =
>
<div
role="presentation"
style="width:0;height:0;overflow:hidden"
style="width:0;height:0;overflow:hidden;position:absolute"
tabindex="0"
/>
<div
Expand All @@ -197,7 +197,7 @@ exports[`rc-swipeable-tabs should render Slider with correct DOM structure 1`] =
</div>
<div
role="presentation"
style="width:0;height:0;overflow:hidden"
style="width:0;height:0;overflow:hidden;position:absolute"
tabindex="0"
/>
</div>
Expand All @@ -214,7 +214,7 @@ exports[`rc-swipeable-tabs should render Slider with correct DOM structure 1`] =
</div>
<div
role="presentation"
style="width:0;height:0;overflow:hidden"
style="width:0;height:0;overflow:hidden;position:absolute"
tabindex="0"
/>
</div>
Expand Down

0 comments on commit 76b24ce

Please sign in to comment.