Skip to content

Commit f789bbf

Browse files
Morta1danez
authored andcommitted
feat: Right to left support (#311)
* Added right to left support. * Added a new prop to README.md
1 parent c096200 commit f789bbf

File tree

7 files changed

+112
-3
lines changed

7 files changed

+112
-3
lines changed

README.md

+6
Original file line numberDiff line numberDiff line change
@@ -158,6 +158,12 @@ Provide a custom class name for the active tab panel.
158158
159159
> This option can also be set directly at the `<TabPanel />` component.
160160
161+
#### direction: `string`
162+
163+
> default: `"ltr"`
164+
165+
Provide the direction of the component, can be either rtl or ltr.
166+
161167
### &lt;TabList /&gt;
162168
163169
If you specify additional props on the `<TabList />` component they will be forwarded to the rendered `<ul />`.

examples/src/app.js

+2
Original file line numberDiff line numberDiff line change
@@ -5,12 +5,14 @@ import './example.less';
55
import SuperMario from './components/examples/SuperMario';
66
import MattGroening from './components/examples/MattGroening';
77
import Avengers from './components/examples/Avengers';
8+
import RightToLeft from './components/examples/RightToLeft';
89

910
ReactDOM.render(
1011
<div>
1112
<SuperMario />
1213
<MattGroening />
1314
<Avengers />
15+
<RightToLeft />
1416
</div>,
1517
document.getElementById('example'),
1618
);

examples/src/components/ExampleItem.js

+3-1
Original file line numberDiff line numberDiff line change
@@ -63,7 +63,9 @@ export default class ExampleItem extends Component {
6363
<div className={editorClassNames}>
6464
<LiveEditor ignoreTabKey />
6565
</div>
66-
<LivePreview />
66+
<LivePreview
67+
style={{ dir: this.props.direction === 'rtl' ? 'rtl' : 'ltr' }}
68+
/>
6769
</div>
6870
</LiveProvider>
6971
</div>
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,77 @@
1+
import React from 'react';
2+
import ExampleItem from '../ExampleItem';
3+
4+
const code = `const Component = (
5+
<div dir="rtl">
6+
<Tabs direction={'rtl'}>
7+
<TabList>
8+
<Tab>כותרת</Tab>
9+
<Tab disabled>כותרת כבויה</Tab>
10+
<Tab>כותרת שנייה</Tab>
11+
<Tab>כותרת שלישית</Tab>
12+
</TabList>
13+
<TabPanel>
14+
<p>
15+
לורם איפסום דולור סיט אמט, קונסקטורר אדיפיסינג אלית לורם איפסום דולור סיט אמט, קונסקטורר אדיפיסינג אלית. סת אלמנקום ניסי נון ניבאה. דס איאקוליס וולופטה דיאם. וסטיבולום אט דולור, קראס אגת לקטוס וואל אאוגו וסטיבולום סוליסי טידום בעליק. קונדימנטום קורוס בליקרה, נונסטי קלובר בריקנה סטום, לפריקך תצטריק לרטי.
16+
</p>
17+
<p>
18+
Source:{' '}
19+
<a href="https://en.wikipedia.org/wiki/" target="_blank">
20+
Wikipedia
21+
</a>
22+
</p>
23+
</TabPanel>
24+
<TabPanel>
25+
<p>
26+
לורם איפסום דולור סיט אמט, קונסקטורר אדיפיסינג אלית לורם איפסום דולור סיט אמט, קונסקטורר אדיפיסינג אלית. סת אלמנקום ניסי נון ניבאה. דס איאקוליס וולופטה דיאם. וסטיבולום אט דולור, קראס אגת לקטוס וואל אאוגו וסטיבולום סוליסי טידום בעליק. קונדימנטום קורוס בליקרה, נונסטי קלובר בריקנה סטום, לפריקך תצטריק לרטי.
27+
</p>
28+
<p>
29+
Source:{' '}
30+
<a href="https://en.wikipedia.org/wiki/" target="_blank">
31+
Wikipedia
32+
</a>
33+
</p>
34+
</TabPanel>
35+
<TabPanel>
36+
<p>
37+
לורם איפסום דולור סיט אמט, קונסקטורר אדיפיסינג אלית לורם איפסום דולור סיט אמט, קונסקטורר אדיפיסינג אלית. סת אלמנקום ניסי נון ניבאה. דס איאקוליס וולופטה דיאם. וסטיבולום אט דולור, קראס אגת לקטוס וואל אאוגו וסטיבולום סוליסי טידום בעליק. קונדימנטום קורוס בליקרה, נונסטי קלובר בריקנה סטום, לפריקך תצטריק לרטי.
38+
לורם איפסום דולור סיט אמט, קונסקטורר אדיפיסינג אלית לורם איפסום דולור סיט אמט, קונסקטורר אדיפיסינג אלית. סת אלמנקום ניסי נון ניבאה. דס איאקוליס וולופטה דיאם. וסטיבולום אט דולור, קראס אגת לקטוס וואל אאוגו וסטיבולום סוליסי טידום בעליק. קונדימנטום קורוס בליקרה, נונסטי קלובר בריקנה סטום, לפריקך תצטריק לרטי.
39+
לורם איפסום דולור סיט אמט, קונסקטורר אדיפיסינג אלית לורם איפסום דולור סיט אמט, קונסקטורר אדיפיסינג אלית. סת אלמנקום ניסי נון ניבאה. דס איאקוליס וולופטה דיאם. וסטיבולום אט דולור, קראס אגת לקטוס וואל אאוגו וסטיבולום סוליסי טידום בעליק. קונדימנטום קורוס בליקרה, נונסטי קלובר בריקנה סטום, לפריקך תצטריק לרטי.
40+
</p>
41+
<p>
42+
Source:{' '}
43+
<a href="https://en.wikipedia.org/wiki/" target="_blank">
44+
Wikipedia
45+
</a>
46+
</p>
47+
</TabPanel>
48+
<TabPanel>
49+
<h4>תת כותרת</h4>
50+
<p>
51+
לורם איפסום דולור סיט אמט, קונסקטורר אדיפיסינג אלית לורם איפסום דולור סיט אמט, קונסקטורר אדיפיסינג אלית. סת אלמנקום ניסי נון ניבאה. דס איאקוליס וולופטה דיאם. וסטיבולום אט דולור, קראס אגת לקטוס וואל אאוגו וסטיבולום סוליסי טידום בעליק. קונדימנטום קורוס בליקרה, נונסטי קלובר בריקנה סטום, לפריקך תצטריק לרטי.
52+
לורם איפסום דולור סיט אמט, קונסקטורר אדיפיסינג אלית לורם איפסום דולור סיט אמט, קונסקטורר אדיפיסינג אלית. סת אלמנקום ניסי נון ניבאה. דס איאקוליס וולופטה דיאם. וסטיבולום אט דולור, קראס אגת לקטוס וואל אאוגו וסטיבולום סוליסי טידום בעליק. קונדימנטום קורוס בליקרה, נונסטי קלובר בריקנה סטום, לפריקך תצטריק לרטי.
53+
</p>
54+
<p>
55+
Source:{' '}
56+
<a href="https://en.wikipedia.org/wiki/" target="_blank">
57+
Wikipedia
58+
</a>
59+
</p>
60+
</TabPanel>
61+
</Tabs>
62+
</div>
63+
);
64+
65+
render(Component);`;
66+
67+
const hint =
68+
'This is an example of a right to left option. Just pass the `direction` prop to the <Tabs /> element';
69+
70+
export default () => (
71+
<ExampleItem
72+
code={code}
73+
direction="rtl"
74+
hint={hint}
75+
label="Right To Left Example"
76+
/>
77+
);

src/components/Tabs.js

+1
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@ export default class Tabs extends Component {
2121

2222
static propTypes = {
2323
children: childrenPropType,
24+
direction: PropTypes.oneOf(['rtl', 'ltr']),
2425
className: PropTypes.oneOfType([
2526
PropTypes.string,
2627
PropTypes.array,

src/components/UncontrolledTabs.js

+12-2
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,7 @@ export default class UncontrolledTabs extends Component {
4343

4444
static propTypes = {
4545
children: childrenPropType,
46+
direction: PropTypes.oneOf(['rtl', 'ltr']),
4647
className: PropTypes.oneOfType([
4748
PropTypes.string,
4849
PropTypes.array,
@@ -241,6 +242,7 @@ export default class UncontrolledTabs extends Component {
241242
}
242243

243244
handleKeyDown = e => {
245+
const { direction } = this.props;
244246
if (this.isTabFromContainer(e.target)) {
245247
let { selectedIndex: index } = this.props;
246248
let preventDefault = false;
@@ -254,12 +256,20 @@ export default class UncontrolledTabs extends Component {
254256

255257
if (e.keyCode === 37 || e.keyCode === 38) {
256258
// Select next tab to the left
257-
index = this.getPrevTab(index);
259+
if (direction === 'rtl') {
260+
index = this.getNextTab(index);
261+
} else {
262+
index = this.getPrevTab(index);
263+
}
258264
preventDefault = true;
259265
useSelectedIndex = true;
260266
} else if (e.keyCode === 39 || e.keyCode === 40) {
261267
// Select next tab to the right
262-
index = this.getNextTab(index);
268+
if (direction === 'rtl') {
269+
index = this.getPrevTab(index);
270+
} else {
271+
index = this.getNextTab(index);
272+
}
263273
preventDefault = true;
264274
useSelectedIndex = true;
265275
} else if (e.keyCode === 35) {

src/components/__tests__/Tabs-test.js

+11
Original file line numberDiff line numberDiff line change
@@ -165,6 +165,17 @@ describe('<Tabs />', () => {
165165
assertTabSelected(wrapper, 1);
166166
});
167167

168+
test('should update selectedIndex when arrow left key pressed (RTL)', () => {
169+
const wrapper = mount(createTabs({ direction: 'rtl' }));
170+
wrapper
171+
.find(Tab)
172+
.at(1)
173+
.simulate('focus')
174+
.simulate('keydown', { keyCode: 37 });
175+
176+
assertTabSelected(wrapper, 1);
177+
});
178+
168179
test.skip('should not change selectedIndex when arrow left key pressed on a disabled tab', () => {
169180
const wrapper = mount(createTabs({ defaultIndex: 0 }));
170181
wrapper

0 commit comments

Comments
 (0)