Burada sunulan çözümlerin hiçbirinden memnun kalmadım. Aslında, temel sahne nesnesi dışındaki bazı React işlevlerine dayanmadan saf Javascript kullanılarak yapılabilecek çok basit bir çözüm vardır - ve size her iki yönde (ebeveyn -> çocuk, çocuk -> ebeveyn) iletişim kurma avantajı sağlar. Bir nesneyi üst bileşenden alt bileşene geçirmeniz gerekir. Bu nesne kısaca "iki yönlü referans" veya biRef olarak adlandırdığım şeydir. Temel olarak, nesne üst öğede üst öğenin göstermek istediği yöntemlere bir başvuru içerir. Alt bileşen, üst öğenin çağırabileceği nesneye yöntemler ekler. Bunun gibi bir şey:
// Parent component.
function MyParentComponent(props) {
function someParentFunction() {
// The child component can call this function.
}
function onButtonClick() {
// Call the function inside the child component.
biRef.someChildFunction();
}
// Add all the functions here that the child can call.
var biRef = {
someParentFunction: someParentFunction
}
return <div>
<MyChildComponent biRef={biRef} />
<Button onClick={onButtonClick} />
</div>;
}
// Child component
function MyChildComponent(props) {
function someChildFunction() {
// The parent component can call this function.
}
function onButtonClick() {
// Call the parent function.
props.biRef.someParentFunction();
}
// Add all the child functions to props.biRef that you want the parent
// to be able to call.
props.biRef.someChildFunction = someChildFunction;
return <div>
<Button onClick={onButtonClick} />
</div>;
}
Bu çözümün diğer avantajı, ebeveyn ve çocukta yalnızca tek bir özellik kullanarak ebeveynlerden çocuğa geçirirken çok daha fazla işlev ekleyebilmenizdir.
Yukarıdaki kod üzerinde yapılan bir iyileştirme, üst ve alt işlevleri doğrudan biRef nesnesine değil alt üyelere eklemektir. Üst işlevler "üst" adlı bir üyeye eklenmelidir; alt işlevler ise "alt" adlı bir üyeye eklenmelidir.
// Parent component.
function MyParentComponent(props) {
function someParentFunction() {
// The child component can call this function.
}
function onButtonClick() {
// Call the function inside the child component.
biRef.child.someChildFunction();
}
// Add all the functions here that the child can call.
var biRef = {
parent: {
someParentFunction: someParentFunction
}
}
return <div>
<MyChildComponent biRef={biRef} />
<Button onClick={onButtonClick} />
</div>;
}
// Child component
function MyChildComponent(props) {
function someChildFunction() {
// The parent component can call this function.
}
function onButtonClick() {
// Call the parent function.
props.biRef.parent.someParentFunction();
}
// Add all the child functions to props.biRef that you want the parent
// to be able to call.
props.biRef {
child: {
someChildFunction: someChildFunction
}
}
return <div>
<Button onClick={onButtonClick} />
</div>;
}
Ebeveyn ve çocuk işlevlerini biRef nesnesinin ayrı üyelerine yerleştirerek, ikisi arasında temiz bir ayrım olur ve hangilerinin ebeveyn veya çocuğa ait olduğunu kolayca görürsünüz. Ayrıca, her ikisinde de aynı işlev görünürse, bir alt bileşenin yanlışlıkla bir üst işlevin üzerine yazmasını önlemeye yardımcı olur.
Son bir şey, not ederseniz, üst bileşenin var ile biRef nesnesini oluşturması, alt bileşenin ise props nesnesi üzerinden erişmesidir. Üst öğedeki biRef nesnesini tanımlamamak ve bu öğeye kendi sahne parametresi (üst öğe öğelerinin hiyerarşisinde geçerli olabilir) aracılığıyla üst öğesinden erişmemek cazip gelebilir. Bu risklidir çünkü çocuk ebeveyn üzerinde çağırdığı bir fonksiyonun aslında bir büyükbaba veya büyükanneye ait olabileceği durumlarda ebeveyne ait olduğunu düşünebilir. Farkında olduğunuz sürece bununla ilgili yanlış bir şey yok. Bir üst / alt ilişkinin ötesinde bir hiyerarşiyi desteklemek için bir nedeniniz olmadıkça, üst bileşeninizde biRef oluşturmak en iyisidir.