اذهب إلى المحتوى
  • 0

تغير مكون بناءًا على حالة مكون React آخر؟

Adam Ebrahim

السؤال

 

لدي بعض المكونات داخل بعضها البعض بالإضافة إلى مكون آخر منفصل عنهم، بنيه المكونات كما بالشكل التالي:

- Component 1  
 -|- Component 2
 ----|- Component 3
 -------|- Component 4 

- Component 5

كما تلاحظ المكون الأول يحتوي مكون بداخله وهذا الأخير يحتوي على مكون آخر Compnent 3 وهكذا ، الآن أريد أن يعرض المكون 5 بعض البيانات اعتمادًا على حالة  state الخاصة بالمكون 4. نظرًا لأن الخاصيات props غير قابلة للتغيير immutable، لا يمكنني ببساطة حفظ حالتها في المكون 1 وإعادة توجيهها للمكون 5.

رابط هذا التعليق
شارك على الشبكات الإجتماعية

Recommended Posts

  • 1

مرحبا 

للاستفادة من البيانات بين المكونات في react يجب علينا أولا تجميعها في مكان واحد بحيث كل المكونات لديها القابلية للوصول لتلك البيانات وتوجد عدة طرق لتحقيق ذلك وأشهر طريقتين هما اما استخدام مكتبة redux أو استخدام the contect api  و لغرض الشرح المبسط سنعيد بناء هيكلة لمشروعك باستخدام context api حيث يمكنك استخدامها دون تثبيت أي مكتبات خارجية 

حسنا لنفترض أنه لديك مكون App.js

import React from 'react';

export default function App() {
  return (
   
      <div>
        <h1>am the app component</h1>
        <Component1></Component1>
        <Component3></Component3>
      </div>
    
  );
}

يحتوي على مكونين Component1 و Component3 

function Component2() {

  return (
    <div style={{ marginLeft: 50 }}>
      <h1>---am component 2</h1>
    </div>
  );
}

function Component1() {
  return (
    <div style={{ marginLeft: 50 }}>
      <h1>am component 1</h1>
      <Component2></Component2>
    </div>
  );
}
function Component3() {

  return (
    <div style={{ marginLeft: 50 }}>
      <h1>am component 3</h1>
     
    </div>
  );
}

و كما تلاحظ ال Component1 يحتوي على Component2 داخله وغرضنا في هذه الحالة الوصول الى بيانات ال Component2 من المكون Component3 والذي هو مكون خارجي في هذه الحالة نقوم بانشاء context بهذه الطريقة في ملف خارجي ولنسمه context.js

import React, { useState, createContext } from 'react';

// انشاء الكونتيكست
export const Component2Context = createContext();

// انشاء موفر البيانات للمكونات للاستهلاك ومتابعة تغيير البيانات
export const CounterContextProvider = (props) => {
  const [count, setCount] = useState(0);

  return (
    <Component2Context.Provider value={[count, setCount]}>
      {props.children}
    </Component2Context.Provider>
  );
};

يمكننا الان استخدام ال context باجراء تغييؤات بسيطة في المكونات السابقة أولا لنستهلك البيانات في ال Component3

import React, { useContext } from 'react';
import { Component2Context } from './context'; //استريراد الكونتيكست

function Component3() {
  const [count] = useContext(Component2Context); //الدخول للبانات

  return (
    <div style={{ marginLeft: 50 }}>
      <h1>am component 3</h1>
      <p>{count}</p> //استهلاك البيانات
    </div>
  );
}

ثانيا لنقوم بتغيير البيانات من المكون Component2

function Component2() {
  const [count, setCount] = useContext(Component2Context);

  const increment = () => {
    setCount(count + 1);
  };

  const decrement = () => {
    setCount(count - 1);
  };

  return (
    <div style={{ marginLeft: 50 }}>
      <h1>---am component 2</h1>
      <button onClick={increment}>Add</button>
      <button onClick={decrement}>Minus</button>
    </div>
  );
}

والخطوة الاخيرة ستكون باستيراد ال Provider و ونقوم باحتواء المشروع كاملا داخله 

import React, { useContext } from 'react';
import { Component2Context, Component2Provider } from './context';

export default function App() {
  return (
    <Component2Provider>//الموفر
      <div>
        <h1>am the app component</h1>
        <Component1></Component1>
        <Component3></Component3>
      </div>
    </Component2Provider>
  );
}

وهكذا سنكون حققنا النتيجة المرغوبة 

context.gif.7b6e9962f375fdcc44e3fec2c2d4a370.gif

رابط هذا التعليق
شارك على الشبكات الإجتماعية

  • 0

مرحباً أحمد: 

  1. إذا كانت هذه الحالة الوحيدة من نوعها فيمكنك رفع حالة المكون component4 إلى المكون component 1 عن طريق ال props  وبعد ذلك إعطاء القيمة للمكون الخامس عن طريق ال prop ولكن هذ الطريقة غير محببة لأنه قد يكون لديك أكثر  من ٤ مكونات بداخل بعضهم 
  2. الطريقة الثانية : هي أن تقوم باستعمال ال stateManagement بحيث تقوم في المكون ٤ بإعطاء القيمة لل store ومن ثم استخدامها في المكون الخامس
  3. الطريقة الثالثة : هي عن طريق عمل context يخزن فيه الحالة التي تريد استخدامها ودالة تقوم بتغيير هذه الحالة (. state ) وفي المكون الرابع تستخدم الدالة لتغيير الحالة كما تريد والمكون الخامس يستخدم الحالة نفسها (.يقرأها )
رابط هذا التعليق
شارك على الشبكات الإجتماعية

  • 0

يمكنك استخدام Redux مع React-Redux بهذا الشكل البسيط:

import React from 'react';
import { Provider, connect } from 'react-redux';
import { createStore } from 'redux';

// هذا الكائن يحتوي على الحالة المبدئية للتطبيق
const initialState = {
	color: 'red',
	theme: 'dark',
	activeRoute: '/home'
};

// نستخدم هذه الدالة لعمل تعديلات على الحالة
// لتبسيط المثال، سنقوم فقط بقراءة اللون
// لذا سنكتفي بارجاع الحالة كاملة
function reducer(state = initialState, action) {
	return state;
}

// هنا نربط الـ state مع reducer
const store = createStore(reducer);


// فلنفترض ان هذا المكون يريد الحصول على قيمة اللون
// اذا قمنا باستخدامة هكذا، لن نحصل على اللوت في الحالة الأساسية
// علينا اولاً ان نربطه بالحالة عن طريق connect
function Component({ color, children }) {
	return (
		<div>The color is: {color}</div>
	);
}

// أولاً
// سنكتب دالة get بسيطة
// تأخذ الدالة كائن الحالة وتعيد لنا اللون
function getColor(state) {
	return {
		color: state.color
	};
}

// ثانياً
// الآن سنقوم بربط الحالة مع المكون مع الدالة التي
// تعيد لنا اللون هكذا
const ConnectedComponent = connect(getColor)(Component);

// الآن أصبح ConnectedComponent قادراً على الحصول على اللون
function App() {
	return (
		<div>
			<ConnectedComponent />
		</div>
	);
}

ReactDOM.render(
	<Provider store={store}>
		<App />
	</Provider>
);

 

رابط هذا التعليق
شارك على الشبكات الإجتماعية

انضم إلى النقاش

يمكنك أن تنشر الآن وتسجل لاحقًا. إذا كان لديك حساب، فسجل الدخول الآن لتنشر باسم حسابك.

زائر
أجب على هذا السؤال...

×   لقد أضفت محتوى بخط أو تنسيق مختلف.   Restore formatting

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   جرى استعادة المحتوى السابق..   امسح المحرر

×   You cannot paste images directly. Upload or insert images from URL.

  • إعلانات

  • تابعنا على



×
×
  • أضف...