Skip to content
This repository was archived by the owner on Aug 23, 2022. It is now read-only.

Commit ffcc6a8

Browse files
authored
Merge pull request #908 from maludwig/master
Resolve Issue 905, defaultChecked bug on Control.checkbox
2 parents e9e4980 + 53e2317 commit ffcc6a8

File tree

5 files changed

+122
-9
lines changed

5 files changed

+122
-9
lines changed

.gitignore

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -46,3 +46,4 @@ examples/sandbox
4646

4747
# Other
4848
.vscode/
49+
.idea/

src/actions/model-actions.js

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -96,7 +96,10 @@ export function createModelActions(s = defaultStrategies) {
9696
return change(model, multiValue);
9797
}
9898

99-
return change(model, !currentValue);
99+
if (typeof value === 'undefined') {
100+
return change(model, !currentValue);
101+
}
102+
return change(model, value);
100103
};
101104

102105
const check = (model, value) => (dispatch, getState) => {

src/components/control-component.js

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -662,23 +662,24 @@ function createControlClass(s = defaultStrategy) {
662662
const modelString = getModel(model, state);
663663
const fieldValue = s.getFieldFromState(state, modelString)
664664
|| initialFieldState;
665+
const modelValue = s.get(state, modelString);
665666

666667
return {
667668
model: modelString,
668-
modelValue: s.get(state, modelString),
669+
modelValue,
669670
fieldValue,
670671
controlProps: finalControlProps,
671672
};
672673
}
673674

674675
const ConnectedControl = resolveModel(connect(mapStateToProps, null, null, {
675-
areOwnPropsEqual(ownProps, nextOwnProps) {
676-
return shallowEqual(ownProps, nextOwnProps, {
676+
areOwnPropsEqual(nextOwnProps, ownProps) {
677+
return shallowEqual(nextOwnProps, ownProps, {
677678
omitKeys: ['mapProps'],
678679
});
679680
},
680-
areStatePropsEqual(stateProps, nextStateProps) {
681-
return shallowEqual(stateProps, nextStateProps, {
681+
areStatePropsEqual(nextStateProps, stateProps) {
682+
return shallowEqual(nextStateProps, stateProps, {
682683
deepKeys: ['controlProps'],
683684
});
684685
},

src/constants/control-props-map.js

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -57,9 +57,7 @@ const controlPropsMap = {
5757
},
5858
checkbox: {
5959
...standardPropsMap,
60-
checked: (props) => (props.defaultChecked
61-
? props.checked
62-
: isChecked(props)),
60+
checked: isChecked,
6361
},
6462
radio: {
6563
...standardPropsMap,

test/control-component-spec.js

Lines changed: 110 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -325,12 +325,14 @@ Object.keys(testContexts).forEach((testKey) => {
325325
assert.equal(
326326
get(store.getState().test, 'single'),
327327
false, 'false');
328+
assert.equal(checkbox.checked, false);
328329

329330
TestUtils.Simulate.change(checkbox);
330331

331332
assert.equal(
332333
get(store.getState().test, 'single'),
333334
true, 'true');
335+
assert.equal(checkbox.checked, true);
334336
});
335337

336338
it('should check/uncheck the checkbox when model is externally changed', () => {
@@ -350,6 +352,114 @@ Object.keys(testContexts).forEach((testKey) => {
350352
});
351353
});
352354

355+
describe('with <Control.checkbox /> (single toggle, dynamic form, defaultChecked)', () => {
356+
const initialState = getInitialState({ single: true });
357+
const store = testCreateStore({
358+
testForm: formReducer('test'),
359+
test: modelReducer('test', initialState),
360+
});
361+
362+
const field = TestUtils.renderIntoDocument(
363+
<Provider store={store}>
364+
<Control.checkbox model="test.other" defaultChecked />
365+
</Provider>
366+
);
367+
368+
const checkbox = TestUtils.findRenderedDOMComponentWithTag(field, 'input');
369+
370+
it('should initially set the checkbox to checked when defaultChecked is true', () => {
371+
assert.equal(checkbox.checked, true);
372+
});
373+
374+
it('should give each radio input a name attribute of the model', () => {
375+
assert.equal(checkbox.name, 'test.other');
376+
});
377+
378+
it('should dispatch a change event when changed', () => {
379+
TestUtils.Simulate.change(checkbox);
380+
381+
assert.equal(
382+
get(store.getState().test, 'other'),
383+
false, 'false');
384+
assert.equal(checkbox.checked, false);
385+
386+
TestUtils.Simulate.change(checkbox);
387+
388+
assert.equal(
389+
get(store.getState().test, 'other'),
390+
true, 'true');
391+
assert.equal(checkbox.checked, true);
392+
});
393+
394+
it('should check/uncheck the checkbox when model is externally changed', () => {
395+
store.dispatch(actions.change('test.other', true));
396+
assert.equal(checkbox.checked, true);
397+
398+
store.dispatch(actions.change('test.other', false));
399+
assert.equal(checkbox.checked, false);
400+
});
401+
402+
it('should uncheck the checkbox for any falsey value', () => {
403+
store.dispatch(actions.change('test.other', ''));
404+
405+
assert.equal(checkbox.checked, false);
406+
});
407+
});
408+
409+
describe('with <Control.checkbox /> (single toggle, dynamic form, !defaultChecked)', () => {
410+
const initialState = getInitialState({ single: true });
411+
const store = testCreateStore({
412+
testForm: formReducer('test'),
413+
test: modelReducer('test', initialState),
414+
});
415+
416+
const field = TestUtils.renderIntoDocument(
417+
<Provider store={store}>
418+
<Control.checkbox model="test.other" defaultChecked={false} />
419+
</Provider>
420+
);
421+
422+
const checkbox = TestUtils.findRenderedDOMComponentWithTag(field, 'input');
423+
424+
it('should initially set the checkbox to unchecked when defaultChecked is false', () => {
425+
assert.equal(checkbox.checked, false);
426+
});
427+
428+
it('should give each radio input a name attribute of the model', () => {
429+
assert.equal(checkbox.name, 'test.other');
430+
});
431+
432+
it('should dispatch a change event when changed', () => {
433+
TestUtils.Simulate.change(checkbox);
434+
435+
assert.equal(
436+
get(store.getState().test, 'other'),
437+
true, 'true');
438+
439+
TestUtils.Simulate.change(checkbox);
440+
441+
assert.equal(
442+
get(store.getState().test, 'other'),
443+
false, 'false');
444+
});
445+
446+
it('should check/uncheck the checkbox when model is externally changed', () => {
447+
store.dispatch(actions.change('test.other', false));
448+
449+
assert.equal(checkbox.checked, false);
450+
451+
store.dispatch(actions.change('test.other', true));
452+
453+
assert.equal(checkbox.checked, true);
454+
});
455+
456+
it('should uncheck the checkbox for any falsey value', () => {
457+
store.dispatch(actions.change('test.other', ''));
458+
459+
assert.equal(checkbox.checked, false);
460+
});
461+
});
462+
353463
describe('with <Control.checkbox /> (multi toggle)', () => {
354464
const initialState = getInitialState({ foo: [1] });
355465
const store = testCreateStore({

0 commit comments

Comments
 (0)