Skip to content

Commit 6a5d74a

Browse files
tpucciAlmouro
authored andcommitted
feat(package): Can focus nested input (avoiding not focusable fields)
1 parent fcc630f commit 6a5d74a

File tree

2 files changed

+31
-8
lines changed

2 files changed

+31
-8
lines changed

src/__tests__/withNextInputAutoFocus.js

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,10 @@ describe("withNextInputAutoFocus", () => {
3535
const wrapper = mount(
3636
<Form>
3737
<Input name="first" />
38-
<Input name="second" />
38+
<View>
39+
<View name="not-focusable" />
40+
<Input name="second" />
41+
</View>
3942
<Input name="last" />
4043
<Button onPress={jest.fn()} title="SUBMIT" />
4144
</Form>
@@ -62,7 +65,11 @@ describe("withNextInputAutoFocus", () => {
6265
const onSubmitEditing = jest.fn();
6366
const wrapper = mount(
6467
<Form>
65-
<Input name="first" returnKeyType="correct value" onSubmitEditing={onSubmitEditing} />
68+
<Input
69+
name="first"
70+
returnKeyType="correct value"
71+
onSubmitEditing={onSubmitEditing}
72+
/>
6673
</Form>
6774
);
6875

src/withNextInputAutoFocus.js

Lines changed: 22 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,14 @@ const withNextInputAutoFocusContextType = {
1010
getReturnKeyType: PropTypes.func
1111
};
1212

13-
const isInput = component => component && !!component.props.name;
13+
getInputs = children =>
14+
(isArray(children) ? children : [children]).reduce((partialInputs, child) => {
15+
if (child.props.children) {
16+
return partialInputs.concat(getInputs(child.props.children));
17+
}
18+
if (child && !!child.props.name) return partialInputs.concat(child);
19+
return partialInputs;
20+
}, []);
1421

1522
export const withNextInputAutoFocusForm = WrappedComponent => {
1623
class WithNextInputAutoFocusForm extends React.PureComponent {
@@ -20,14 +27,15 @@ export const withNextInputAutoFocusForm = WrappedComponent => {
2027
constructor(props) {
2128
super(props);
2229
const { children } = props;
23-
this.inputs = (isArray(children) ? children : [children]).filter(isInput);
30+
this.inputs = getInputs(children);
2431
}
2532

2633
inputs;
2734
inputNameMap;
2835
inputRefs = {};
2936

30-
getInputPosition = name => this.inputs.findIndex(input => input.props.name === name);
37+
getInputPosition = name =>
38+
this.inputs.findIndex(input => input.props.name === name);
3139

3240
getChildContext = () => ({
3341
setInput: (name, component) => {
@@ -40,8 +48,13 @@ export const withNextInputAutoFocusForm = WrappedComponent => {
4048
if (isLastInput) {
4149
this.context.formik.submitForm();
4250
} else {
43-
const nextInput = this.inputs[inputPosition + 1];
44-
this.inputRefs[nextInput.props.name].focus();
51+
const nextInputs = this.inputs.slice(inputPosition + 1);
52+
const nextFocusableInput = nextInputs.find(
53+
element =>
54+
this.inputRefs[element.props.name] &&
55+
this.inputRefs[element.props.name].focus
56+
);
57+
this.inputRefs[nextFocusableInput.props.name].focus();
4558
}
4659
},
4760
getReturnKeyType: name => {
@@ -61,7 +74,10 @@ export const withNextInputAutoFocusForm = WrappedComponent => {
6174
};
6275

6376
export const withNextInputAutoFocusInput = Input => {
64-
class WithNextInputAutoFocusInput extends React.Component<$FlowFixMeProps, $FlowFixMeState> {
77+
class WithNextInputAutoFocusInput extends React.Component<
78+
$FlowFixMeProps,
79+
$FlowFixMeState
80+
> {
6581
static contextTypes = withNextInputAutoFocusContextType;
6682

6783
setInput = component => {

0 commit comments

Comments
 (0)