Let\'s say I have a reusable container. It is a wizard with multiple pages.
The wizard state is driven by redux/actions. When an action is fired, I use a reducer to upda
Just partition your main state into as many wizard states as you need and send a wizard id along with each action so that your reducer knows which one to tackle.
{
wizards: [
{ id: 'A', state: true },
{ id: 'B', state: false },
{ id: 'C', state: true }
]
}
You can write a wizard reducer which understands how to reduce a single wizard state.
function wizardReducer(wizard, action) {
switch(action) {
case 'TOGGLE':
return {
id: wizard.id,
state: !wizard.state
};
default:
return wizard;
}
}
Then write a wizardsReducer
which understands how to reduce a list of wizards.
function wizardsReducer(wizards, action) {
return wizards.map(function(wizard) {
if(action.id == wizard.id) {
return wizardReducer(wizard, action);
} else {
return wizard;
}
});
}
Finally, use combineReducers
to create a root reducer which delegates responsibility for the wizards
property to this wizardsReducer
.
combineReducers({
wizards: wizardsReducer
});
If you're storing your wizards in an object instead, you'll have to construct your wizardsReducer
slightly differently.
{
wizards: {
A: { id: 'A', state: true },
B: { id: 'B', state: false },
C: { id: 'C', state: true }
}
}
It wouldn't make much sense to map over the states, when we can just select the state we need straight away.
function wizardsReducer(wizards, action) {
if(!(action.id in wizards)) return wizards;
const wizard = wizards[action.id];
const updatedWizard = wizardReducer(wizard, action);
return {
...wizards,
[action.id]: updatedWizard
};
}