Skip to content

Commit c378855

Browse files
committed
fix(handle): fix handleAxis not being passed to custom handles
1 parent 54d2a4b commit c378855

File tree

3 files changed

+66
-40
lines changed

3 files changed

+66
-40
lines changed

README.md

Lines changed: 7 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -115,7 +115,7 @@ type ResizableProps =
115115
onResizeStart?: ?(e: SyntheticEvent, data: ResizeCallbackData) => any,
116116
onResize?: ?(e: SyntheticEvent, data: ResizeCallbackData) => any,
117117
draggableOpts?: ?Object,
118-
resizeHandles?: ?Array<'s' | 'w' | 'e' | 'n' | 'sw' | 'nw' | 'se' | 'ne'> = ['se']
118+
resizeHandles?: ?Array<ResizeHandleAxis> = ['se']
119119
};
120120
```
121121
@@ -154,7 +154,8 @@ You must [forward the ref](https://reactjs.org/docs/forwarding-refs.html) and pr
154154
```js
155155
class MyHandleComponent extends React.Component {
156156
render() {
157-
return <div ref={this.props.innerRef} className="foo" {...this.props} />
157+
const {handleAxis, innerRef, ...props} = this.props;
158+
return <div ref={innerRef} className={`foo handle-${handleAxis}`} {...props} />
158159
}
159160
}
160161
const MyHandle = React.forwardRef((props, ref) => <MyHandleComponent innerRef={ref} {...props} />);
@@ -166,20 +167,21 @@ const MyHandle = React.forwardRef((props, ref) => <MyHandleComponent innerRef={r
166167
167168
```js
168169
const MyHandle = React.forwardRef((props, ref) => {
169-
return <div ref={ref} className="foo" {...props} />;
170+
const {handleAxis, ...restProps} = props;
171+
return <div ref={ref} className={`foo handle-${handleAxis}`} {...restProps} />;
170172
});
171173

172174
<Resizable handle={<MyHandle />} />
173175
```
174176
175177
##### Custom Function
176178
177-
You can define a function as a handle, which will simply receive props and ref. This may be more clear to read, depending on your coding style.
179+
You can define a function as a handle, which will simply receive an axis (see above `ResizeHandleAxis` type) and ref. This may be more clear to read, depending on your coding style.
178180
179181
```js
180182
const MyHandle = (props) => {
181183
return <div ref={props.innerRef} className="foo" {...props} />;
182184
};
183185

184-
<Resizable handle={(props, ref) => <MyHandle innerRef={ref} {...props} />} />
186+
<Resizable handle={(handleAxis, ref) => <MyHandle innerRef={ref} className={`foo handle-${handleAxis}`} {...props} />} />
185187
```

__tests__/Resizable.test.js

Lines changed: 58 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
// @flow
22
import React from 'react';
33
import renderer from 'react-test-renderer';
4-
import {shallow} from 'enzyme';
4+
import {shallow, mount} from 'enzyme';
55
import {DraggableCore} from "react-draggable";
66

77
import Resizable from '../lib/Resizable';
@@ -23,7 +23,6 @@ describe('render Resizable', () => {
2323
transformScale: 1,
2424
width: 50,
2525
};
26-
const handleFn = (axis, ref) => <span className={`custom-handle-${axis}`} ref={ref} />;
2726
const userChildren = <span className={'children'} />;
2827
const resizableBoxChildren = <div style={{width: '50px', height: '50px'}}>{userChildren}</div>;
2928

@@ -46,40 +45,65 @@ describe('render Resizable', () => {
4645
expect(cursorE).toHaveLength(1);
4746
});
4847

49-
test('with handle function', () => {
50-
const handleFn = (axis, ref) => {
51-
expect(axis).toMatch(/(se|e)/);
52-
expect(ref).toMatchObject({current: null}); // ReactRef
53-
return <span className={`custom-handle-${axis}`} ref={ref} />;
54-
};
55-
const element = shallow(<Resizable {...props} handle={handleFn}>{resizableBoxChildren}</Resizable>);
56-
expect(element.find('.test-classname').find('.children'));
57-
expect(element.find(DraggableCore)).toHaveLength(2);
58-
const cursorSe = element.find('.custom-handle-se');
59-
const cursorE = element.find('.custom-handle-e');
60-
expect(cursorSe).toHaveLength(1);
61-
expect(cursorE).toHaveLength(1);
62-
});
63-
64-
describe('and pass handle props', () => {
65-
test('as component', () => {
66-
const customProps = {
67-
...props,
68-
resizeHandles: ['se'],
69-
handle: <span className={'custom-component'} />
48+
describe('Handles', () => {
49+
test('with handle function', () => {
50+
const handleFn = (axis, ref) => {
51+
expect(axis).toMatch(/(se|e)/);
52+
expect(ref).toMatchObject({current: null}); // ReactRef
53+
return <span className={`custom-handle-${axis}`} ref={ref} />;
7054
};
71-
const element = shallow(<Resizable {...customProps}>{resizableBoxChildren}</Resizable>);
72-
expect(element.find('.react-resizable-handle-se')).toHaveLength(0);
73-
expect(element.find('.custom-component')).toHaveLength(1);
55+
const element = shallow(<Resizable {...props} handle={handleFn}>{resizableBoxChildren}</Resizable>);
56+
57+
expect(element.find('.test-classname').find('.children'));
58+
expect(element.find(DraggableCore)).toHaveLength(2);
59+
const cursorSe = element.find('.custom-handle-se');
60+
const cursorE = element.find('.custom-handle-e');
61+
expect(cursorSe).toHaveLength(1);
62+
expect(cursorE).toHaveLength(1);
7463
});
75-
test('as function', () => {
76-
const customProps = {
77-
...props,
78-
resizeHandles: ['se'],
79-
handle: (h) => <span className={`custom-component-${h}`} />
80-
};
81-
const element = shallow(<Resizable {...customProps}>{resizableBoxChildren}</Resizable>);
82-
expect(element.find('.custom-component-se')).toHaveLength(1);
64+
65+
test.only('with handle component', () => {
66+
const ResizeHandle = React.forwardRef((props, ref) => {
67+
// $FlowIgnore doens't know this is cloned and has handleAxis
68+
const {handleAxis, ...restProps} = props;
69+
return (
70+
<div
71+
ref={ref}
72+
className={`react-resizable-handle element-handle-${handleAxis}`}
73+
{...restProps}
74+
/>
75+
);
76+
});
77+
const element = mount(<Resizable {...props} handle={<ResizeHandle />}>{resizableBoxChildren}</Resizable>);
78+
79+
expect(element.find('.test-classname').find('.children'));
80+
expect(element.find(DraggableCore)).toHaveLength(2);
81+
const cursorSe = element.find('.element-handle-se');
82+
const cursorE = element.find('.element-handle-e');
83+
expect(cursorSe).toHaveLength(1);
84+
expect(cursorE).toHaveLength(1);
85+
});
86+
87+
describe('and pass handle props', () => {
88+
test('as component', () => {
89+
const customProps = {
90+
...props,
91+
resizeHandles: ['se'],
92+
handle: <span className={'custom-component'} />
93+
};
94+
const element = shallow(<Resizable {...customProps}>{resizableBoxChildren}</Resizable>);
95+
expect(element.find('.react-resizable-handle-se')).toHaveLength(0);
96+
expect(element.find('.custom-component')).toHaveLength(1);
97+
});
98+
test('as function', () => {
99+
const customProps = {
100+
...props,
101+
resizeHandles: ['se'],
102+
handle: (h) => <span className={`custom-component-${h}`} />
103+
};
104+
const element = shallow(<Resizable {...customProps}>{resizableBoxChildren}</Resizable>);
105+
expect(element.find('.custom-component-se')).toHaveLength(1);
106+
});
83107
});
84108
});
85109

lib/Resizable.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -159,7 +159,7 @@ export default class Resizable extends React.Component<Props, void> {
159159
if (typeof handle === 'function') {
160160
return handle(handleAxis, ref);
161161
}
162-
return React.cloneElement(handle, {ref});
162+
return React.cloneElement(handle, {ref, handleAxis});
163163
}
164164
return <span className={`react-resizable-handle react-resizable-handle-${handleAxis}`} ref={ref} />;
165165
}

0 commit comments

Comments
 (0)