React-те компонент-ұрпақтарының стейттері арқылы жұмыс істеу режимдері
Енді біздің өнімдер массивіміз келесідей болсын:
const initProds = [
{id: id(), name: 'prod1', cost: 'cost1', catg: 'catg1'},
{id: id(), name: 'prod2', cost: 'cost2', catg: 'catg2'},
{id: id(), name: 'prod3', cost: 'cost3', catg: 'catg3'},
];
Осы өнімдерді HTML кестесі түрінде шығарайық.
Сонымен бірге кестенің кез келген ұяшығына басқанда
сол ұяшықта өңдеу үшін енгізу өрісі пайда болатындай етейік. Мәселені шешу үшін
3 компонент жасаймыз.
Products компоненты өнімдермен стейтті
сақтайды және өнімдерді шығару үшін Product
компоненттерін қолданады. Өз кезегінде Product
компоненті де белгілі бір өнім өрісін (атауы, бағасы, санаты) шығару үшін
ProductField компоненттерін қолданады.
ProductField компоненті не өріс мәтінін көрсетеді,
не оны өңдеу үшін енгізу өрісін көрсетеді.
Бұл ретте өңдеу режимі не көрсету режимі осы компоненттің стейті арқылы
реттеледі.
Яғни біз режимді ата-аналық стейтте сақтамаймыз. Онда бұл өте ыңғайсыз болар еді, өйткені біз әрбір өнім өрісі үшін режимді көрсетуіміз керек болар еді, бұл біздің стейтімізді келесідей нәрсеге айналдырар еді:
const initProds = [
[
{field: 'name', value: 'prod1', isEdit: false},
{field: 'cost', value: 'cost1', isEdit: false},
{field: 'catg', value: 'catg1', isEdit: false},
],
[
{field: 'name', value: 'prod2', isEdit: false},
{field: 'cost', value: 'cost2', isEdit: false},
{field: 'catg', value: 'catg2', isEdit: false},
],
[
{field: 'name', value: 'prod3', isEdit: false},
{field: 'cost', value: 'cost3', isEdit: false},
{field: 'catg', value: 'catg3', isEdit: false},
],
]
Алайда, біз мұндай стейт жасамаймыз,
де бастапқыда болғанды сақтаймыз.
Әр ProductField компонентінің әр данасы
өз стейтінің көмегімен режимді реттейді:
не өңдеу, не көрсету.
Осылайша, ата-аналық компонент деректермен стейтті сақтайды, ал біздің немере компоненті бұл деректерді пропстер арқылы алады және сонымен бірге өз режимін өзгерту үшін өз стейтіне ие болады.
Енді, сипатталғанды жүзеге асырайық.
Products компоненті
function Products() {
const [prods, setProds] = useState(initProds);
function changeField(id, field, event) {
setProds(prods.map(prod => {
if (prod.id === id) {
prod[field] = event.target.value;
}
return prod;
}));
}
const rows = prods.map(prod => {
return <Product
key ={prod.id}
id ={prod.id}
name={prod.name}
cost={prod.cost}
catg={prod.catg}
changeField={changeField}
/>;
});
return <div>
<table>
<tbody>
{rows}
</tbody>
</table>
</div>;
}
Product компоненті
function Product({ id, name, cost, catg, changeField }) {
return <tr>
<ProductField id={id} text={name} type="name" changeField={changeField} />
<ProductField id={id} text={cost} type="cost" changeField={changeField} />
<ProductField id={id} text={catg} type="catg" changeField={changeField} />
</tr>;
}
ProductField компоненті
function ProductField({ id, text, type, changeField }) {
const [isEdit, setIsEdit] = useState(false);
return <td>
{
isEdit
? <input
value={text}
onChange={event => changeField(id, type, event)}
onBlur={() => setIsEdit(false)}
/>
: <span onClick={() => setIsEdit(true)}>{text}</span>
}
</td>;
}
Практикалық тапсырмалар
Алдыңғы сабақтарда сіз жасаған Users және User
компоненттерімен де осындай операцияларды орындаңыз.