Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/reactjs/21.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript 在react钩子之间传递数据_Javascript_Reactjs_Typescript_React Hooks - Fatal编程技术网

Javascript 在react钩子之间传递数据

Javascript 在react钩子之间传递数据,javascript,reactjs,typescript,react-hooks,Javascript,Reactjs,Typescript,React Hooks,如何将数据从一个React hooks表单(组件)传递到另一个组件。例如,如果我需要从Profile.js传递播放器名称和照片,并在Navigation.js中提供,我该怎么做 Player.js import React, { useContext , useEffect, useState } from "react"; import { useForm } from 'react-hook-form'; import { useHistory } from "react-router-do

如何将数据从一个
React hooks
表单(组件)传递到另一个组件。例如,如果我需要从
Profile.js
传递播放器
名称和照片,并在
Navigation.js
中提供,我该怎么做

Player.js

import React, { useContext , useEffect, useState } from "react";
import { useForm } from 'react-hook-form';
import { useHistory } from "react-router-dom";
import Axios from "axios";
import UserProfileContext from '../context';

const Profile = () => {

  const { setData } = useContext(UserProfileContext);
  const [email, setEmail] = useState('');
  const [picture, setPicture] = useState('');
  const [playerProfile, setPlayerProfile] = useState([]);
  const loginUserEmail = localStorage.getItem('loginEmail');
  const [updateProfile, setUpdateProfile] = useState({ _id: '', photo: '', name: '', email:'', phonenumber: '', position: '', password: '' })
  const [isSent, setIsSent] = useState(false);
  const [helperText, setHelperText] = useState('');
  const [disabled, setDisabled] = useState(true);
  const { handleSubmit, register, errors } = useForm();
  const history = useHistory();

  const onChangePicture = e => {
    console.log('picture: ', picture);
    if (e.target.files.length) {
      setPicture(URL.createObjectURL(e.target.files[0]));
    } else {
      return false;
    }
  };

  // If no profile image is being uploaded, to avoid the broken display of image, display a default image.
  const addDefaultSrc = e => {
    e.target.src = '/images/default-icon.png';
  }

  // Pass the id to the handler so you will know which item id changing.
  const handleChange = (e, id) => {
    e.persist();
    let itemIndex;
    const targetPlayer = playerProfile.find((player, index) => {
      console.log({ player, id, index });
      itemIndex = index; // Track the index so you can use it to update later.
      return player.id === id;
    });

    console.log({ targetPlayer, id, e });

    const editedTarget = {
      ...targetPlayer,
      [e.target.name]: e.target.value
    };
    const tempPlayers = Array.from(playerProfile);
    tempPlayers[itemIndex] = editedTarget;
    /*
    // Alternatively:: you can just  map over the array if you dont want to track the index
    const tempPlayers = playerProfile.map((profile, index) => {
      return profile.id === id ? editedTarget : profile;
    });
    */
    setPlayerProfile(tempPlayers);
    setUpdateProfile({ ...updateProfile, [e.target.name]: e.target.value }); // this is added just to see if its working
  };

  useEffect(() => {
    const fetchData = async () => {
      try {
        const params = {
          email: loginUserEmail,
        };
      const res = await Axios.get('http://localhost:8000/service/profile', {params});
        setPlayerProfile(res.data.playerProfile);
      } catch (e) {
        console.log(e);
      }
    }
    fetchData();
  }, []);

  const onSubmit = () => {
    setDisabled(disabled);
    const fetchData = async () => {
      try {
        const params = {
          email: loginUserEmail,
        };
        const data = {photo: updateProfile.photo, name: updateProfile.name, email: updateProfile.email, phonenumber: updateProfile.phonenumber, position: updateProfile.position, password: updateProfile.password}
        const res = await Axios.put('http://localhost:8000/service/profile', data, {params}); 
        console.log("Front End update message:" + res.data.success);
        if (res.data.success) {
          setIsSent(true);
          history.push('/')
        }
        else {
          console.log(res.data.message);
          setHelperText(res.data.message);
        }
      } catch (e) {
        setHelperText(e.response.data.message);
      }
    }
    fetchData();
  }

  return (
    <div className="register_wrapper">
      <div className="register_player_column_layout_one">
        <div className="register_player_Twocolumn_layout_two">
          <form onSubmit={handleSubmit(onSubmit)} className="myForm">
            {
              playerProfile.map(({ id, photo, name, email, phonenumber, position, privilege, password }) => (
                <div key={id}>
                  <div className="formInstructionsDiv formElement">
                    <h2 className="formTitle">Profile</h2>
                    <div className="register_profile_image">
                      <input id="profilePic" name="photo" type="file" onChange={onChangePicture} />
                    </div>
                    <div className="previewProfilePic" >
                      <img alt="" onError={addDefaultSrc} name="previewImage" className="playerProfilePic_home_tile" src={photo} onChange={e => handleChange(e, id)}></img>
                    </div>
                  </div>
                  <div className="fillContentDiv formElement">
                    <label>
                      <input className="inputRequest formContentElement" name="name" type="text" value={name} 
                      onChange={e => handleChange(e, id)}
                      maxLength={30}
                      ref={register({
                        required: "Full name is required", 
                        pattern: {
                          value: /^[a-zA-Z\s]{3,30}$/,
                          message: "Full name should have minimum of 3 letters"
                        }
                      })}
                      />
                      <span className="registerErrorTextFormat">{errors.name && errors.name.message}</span>
                    </label>
                    <label>
                      <input className="inputRequest formContentElement" name="email" type="text" value={email} 
                      onChange={e => handleChange(e, id)}
                      disabled={disabled}
                      />
                    </label>
                    <label>
                      <input className="inputRequest formContentElement" name="phonenumber" type="text" value={phonenumber} 
                      onChange={e => handleChange(e, id)}
                      maxLength={11}
                      ref={register({
                        required: "Phone number is required",
                        pattern: {
                          value: /^[0-9\b]+$/,
                          message: "Invalid phone number"
                        }
                       })}
                      />
                      <span className="registerErrorTextFormat">{errors.phonenumber && errors.phonenumber.message}</span>
                    </label>
                    <label>
                      <input className="inputRequest formContentElement" name="position" type="text" value={position} 
                      onChange={e => handleChange(e, id)}
                      maxLength={30}
                      ref={register({
                        pattern: {
                          value: /^[a-zA-Z\s]{2,30}$/,
                          message: "Position should have minimum of 2 letters"
                        }
                      })}
                      />
                      <span className="registerErrorTextFormat">{errors.position && errors.position.message}</span>
                    </label>
                    <label>
                      <div className="select" >
                        <select name="privilege" id="select" value={privilege} onChange={e => handleChange(e, id)}>
                          {/*<option selected disabled>Choose an option</option> */}
                          <option value="player">PLAYER</option>
                          {/*<option value="admin">ADMIN</option>*/}
                        </select>
                      </div>
                    </label>
                    <label>
                      <input className="inputRequest formContentElement" name="password" type="password" value={password} 
                      onChange={e => handleChange(e, id)}
                      minLength={4}
                      maxLength={30}
                      ref={register({
                      required: "Password is required",
                      pattern: {
                        value: /^(?=.*?\d)(?=.*?[a-zA-Z])[a-zA-Z\d]+$/,
                        message: "Password begin with a letter and includes number !"
                      }
                      })}
                      />
                      <span className="registerErrorTextFormat">{errors.password && errors.password.message}</span>
                    </label>
                  </div>
                  <label>
                    <span className="profileValidationText">{helperText}</span>
                  </label>
                  <div className="submitButtonDiv formElement">
                    <button type="submit" className="submitButton">Save</button>
                  </div>
                </div>
              ))
            }
          </form>

        </div>
      </div>
    </div>
  );
}
import React, { useContext } from 'react';
import { NavLink, useHistory } from 'react-router-dom';
import UserProfileContext from '../context';


const Navigation = () => {
    const history = useHistory();
    const { data } = useContext(UserProfileContext);

    const divStyle = {
        float:'left',
        color: '#64cad8', 
        padding: '0px 0px 0px 10px',
        font:'Lucida, sans-serif'
      };

    function logout() {
        localStorage.removeItem('loginEmail')
        localStorage.removeItem('Privilege')
        history.push('/login')
        window.location.reload(true);
      }

    return localStorage.getItem('loginEmail') &&
        <div className="App">
            <div className="wrapper">
                <nav className="siteNavigation_nav_links">
                <div className="clubLogo landing"style={divStyle}><b>Southside Soccer</b></div>
                    <NavLink className="mobile_register_link" to="/">Home</NavLink>
                    <NavLink className="mobile_register_link" to="/profile">Profile</NavLink>
                    <NavLink className="mobile_login_link" to="/login" onClick={logout}>Logout</NavLink>
                    <NavLink className="mobile_login_link" to='/aboutus'>About us</NavLink>
                <div className="profileImage nav menu">
                <span>{data.name}</span>|<img src=""></img>
                </div>
                </nav>
            </div>
        </div>
}

export default Navigation;
import React, { useState } from 'react';
import "./App.css";
import "./CSSModules/home.css";
import "./CSSModules/register.css";
import "./CSSModules/login.css";
import "./CSSModules/aboutus.css";
import { BrowserRouter, Route, Switch } from "react-router-dom";
import Home from "./components/Home";
import Register from "./components/Register";
import Login from "./components/Login";
import Aboutus from "./components/Aboutus";
import Navigation from "./components/Navigation";
import Profile from "./components/Profile";
import { ProtectedRoute } from "./components/protected.route";
import UserProfileContext from './context';

var ReactDOM = require("react-dom");

const App = () => {
  const [data, setData] = useState({
    id: '',
    name: '',
    email: '',
    photo: '',
  });

  return (
   <UserProfileContext.Provider value={{ data, setData }}>
      <BrowserRouter>
        <>
     <Navigation />
      <Switch>
          <ProtectedRoute exact path="/" component={Home} />
          <ProtectedRoute path="/profile" component={Profile} />
          <ProtectedRoute path="/aboutus" component={Aboutus} />
          <Route path="/register" component={Register} />
          <Route path="/login" component={Login} />
      </Switch>
    </>
   </BrowserRouter>
  </UserProfileContext.Provider>
  );
};
ReactDOM.render(
  React.createElement(App, null),
  document.getElementById("root")
);

export default App;
import React from 'react';

export default React.createContext();
App.js

import React, { useContext , useEffect, useState } from "react";
import { useForm } from 'react-hook-form';
import { useHistory } from "react-router-dom";
import Axios from "axios";
import UserProfileContext from '../context';

const Profile = () => {

  const { setData } = useContext(UserProfileContext);
  const [email, setEmail] = useState('');
  const [picture, setPicture] = useState('');
  const [playerProfile, setPlayerProfile] = useState([]);
  const loginUserEmail = localStorage.getItem('loginEmail');
  const [updateProfile, setUpdateProfile] = useState({ _id: '', photo: '', name: '', email:'', phonenumber: '', position: '', password: '' })
  const [isSent, setIsSent] = useState(false);
  const [helperText, setHelperText] = useState('');
  const [disabled, setDisabled] = useState(true);
  const { handleSubmit, register, errors } = useForm();
  const history = useHistory();

  const onChangePicture = e => {
    console.log('picture: ', picture);
    if (e.target.files.length) {
      setPicture(URL.createObjectURL(e.target.files[0]));
    } else {
      return false;
    }
  };

  // If no profile image is being uploaded, to avoid the broken display of image, display a default image.
  const addDefaultSrc = e => {
    e.target.src = '/images/default-icon.png';
  }

  // Pass the id to the handler so you will know which item id changing.
  const handleChange = (e, id) => {
    e.persist();
    let itemIndex;
    const targetPlayer = playerProfile.find((player, index) => {
      console.log({ player, id, index });
      itemIndex = index; // Track the index so you can use it to update later.
      return player.id === id;
    });

    console.log({ targetPlayer, id, e });

    const editedTarget = {
      ...targetPlayer,
      [e.target.name]: e.target.value
    };
    const tempPlayers = Array.from(playerProfile);
    tempPlayers[itemIndex] = editedTarget;
    /*
    // Alternatively:: you can just  map over the array if you dont want to track the index
    const tempPlayers = playerProfile.map((profile, index) => {
      return profile.id === id ? editedTarget : profile;
    });
    */
    setPlayerProfile(tempPlayers);
    setUpdateProfile({ ...updateProfile, [e.target.name]: e.target.value }); // this is added just to see if its working
  };

  useEffect(() => {
    const fetchData = async () => {
      try {
        const params = {
          email: loginUserEmail,
        };
      const res = await Axios.get('http://localhost:8000/service/profile', {params});
        setPlayerProfile(res.data.playerProfile);
      } catch (e) {
        console.log(e);
      }
    }
    fetchData();
  }, []);

  const onSubmit = () => {
    setDisabled(disabled);
    const fetchData = async () => {
      try {
        const params = {
          email: loginUserEmail,
        };
        const data = {photo: updateProfile.photo, name: updateProfile.name, email: updateProfile.email, phonenumber: updateProfile.phonenumber, position: updateProfile.position, password: updateProfile.password}
        const res = await Axios.put('http://localhost:8000/service/profile', data, {params}); 
        console.log("Front End update message:" + res.data.success);
        if (res.data.success) {
          setIsSent(true);
          history.push('/')
        }
        else {
          console.log(res.data.message);
          setHelperText(res.data.message);
        }
      } catch (e) {
        setHelperText(e.response.data.message);
      }
    }
    fetchData();
  }

  return (
    <div className="register_wrapper">
      <div className="register_player_column_layout_one">
        <div className="register_player_Twocolumn_layout_two">
          <form onSubmit={handleSubmit(onSubmit)} className="myForm">
            {
              playerProfile.map(({ id, photo, name, email, phonenumber, position, privilege, password }) => (
                <div key={id}>
                  <div className="formInstructionsDiv formElement">
                    <h2 className="formTitle">Profile</h2>
                    <div className="register_profile_image">
                      <input id="profilePic" name="photo" type="file" onChange={onChangePicture} />
                    </div>
                    <div className="previewProfilePic" >
                      <img alt="" onError={addDefaultSrc} name="previewImage" className="playerProfilePic_home_tile" src={photo} onChange={e => handleChange(e, id)}></img>
                    </div>
                  </div>
                  <div className="fillContentDiv formElement">
                    <label>
                      <input className="inputRequest formContentElement" name="name" type="text" value={name} 
                      onChange={e => handleChange(e, id)}
                      maxLength={30}
                      ref={register({
                        required: "Full name is required", 
                        pattern: {
                          value: /^[a-zA-Z\s]{3,30}$/,
                          message: "Full name should have minimum of 3 letters"
                        }
                      })}
                      />
                      <span className="registerErrorTextFormat">{errors.name && errors.name.message}</span>
                    </label>
                    <label>
                      <input className="inputRequest formContentElement" name="email" type="text" value={email} 
                      onChange={e => handleChange(e, id)}
                      disabled={disabled}
                      />
                    </label>
                    <label>
                      <input className="inputRequest formContentElement" name="phonenumber" type="text" value={phonenumber} 
                      onChange={e => handleChange(e, id)}
                      maxLength={11}
                      ref={register({
                        required: "Phone number is required",
                        pattern: {
                          value: /^[0-9\b]+$/,
                          message: "Invalid phone number"
                        }
                       })}
                      />
                      <span className="registerErrorTextFormat">{errors.phonenumber && errors.phonenumber.message}</span>
                    </label>
                    <label>
                      <input className="inputRequest formContentElement" name="position" type="text" value={position} 
                      onChange={e => handleChange(e, id)}
                      maxLength={30}
                      ref={register({
                        pattern: {
                          value: /^[a-zA-Z\s]{2,30}$/,
                          message: "Position should have minimum of 2 letters"
                        }
                      })}
                      />
                      <span className="registerErrorTextFormat">{errors.position && errors.position.message}</span>
                    </label>
                    <label>
                      <div className="select" >
                        <select name="privilege" id="select" value={privilege} onChange={e => handleChange(e, id)}>
                          {/*<option selected disabled>Choose an option</option> */}
                          <option value="player">PLAYER</option>
                          {/*<option value="admin">ADMIN</option>*/}
                        </select>
                      </div>
                    </label>
                    <label>
                      <input className="inputRequest formContentElement" name="password" type="password" value={password} 
                      onChange={e => handleChange(e, id)}
                      minLength={4}
                      maxLength={30}
                      ref={register({
                      required: "Password is required",
                      pattern: {
                        value: /^(?=.*?\d)(?=.*?[a-zA-Z])[a-zA-Z\d]+$/,
                        message: "Password begin with a letter and includes number !"
                      }
                      })}
                      />
                      <span className="registerErrorTextFormat">{errors.password && errors.password.message}</span>
                    </label>
                  </div>
                  <label>
                    <span className="profileValidationText">{helperText}</span>
                  </label>
                  <div className="submitButtonDiv formElement">
                    <button type="submit" className="submitButton">Save</button>
                  </div>
                </div>
              ))
            }
          </form>

        </div>
      </div>
    </div>
  );
}
import React, { useContext } from 'react';
import { NavLink, useHistory } from 'react-router-dom';
import UserProfileContext from '../context';


const Navigation = () => {
    const history = useHistory();
    const { data } = useContext(UserProfileContext);

    const divStyle = {
        float:'left',
        color: '#64cad8', 
        padding: '0px 0px 0px 10px',
        font:'Lucida, sans-serif'
      };

    function logout() {
        localStorage.removeItem('loginEmail')
        localStorage.removeItem('Privilege')
        history.push('/login')
        window.location.reload(true);
      }

    return localStorage.getItem('loginEmail') &&
        <div className="App">
            <div className="wrapper">
                <nav className="siteNavigation_nav_links">
                <div className="clubLogo landing"style={divStyle}><b>Southside Soccer</b></div>
                    <NavLink className="mobile_register_link" to="/">Home</NavLink>
                    <NavLink className="mobile_register_link" to="/profile">Profile</NavLink>
                    <NavLink className="mobile_login_link" to="/login" onClick={logout}>Logout</NavLink>
                    <NavLink className="mobile_login_link" to='/aboutus'>About us</NavLink>
                <div className="profileImage nav menu">
                <span>{data.name}</span>|<img src=""></img>
                </div>
                </nav>
            </div>
        </div>
}

export default Navigation;
import React, { useState } from 'react';
import "./App.css";
import "./CSSModules/home.css";
import "./CSSModules/register.css";
import "./CSSModules/login.css";
import "./CSSModules/aboutus.css";
import { BrowserRouter, Route, Switch } from "react-router-dom";
import Home from "./components/Home";
import Register from "./components/Register";
import Login from "./components/Login";
import Aboutus from "./components/Aboutus";
import Navigation from "./components/Navigation";
import Profile from "./components/Profile";
import { ProtectedRoute } from "./components/protected.route";
import UserProfileContext from './context';

var ReactDOM = require("react-dom");

const App = () => {
  const [data, setData] = useState({
    id: '',
    name: '',
    email: '',
    photo: '',
  });

  return (
   <UserProfileContext.Provider value={{ data, setData }}>
      <BrowserRouter>
        <>
     <Navigation />
      <Switch>
          <ProtectedRoute exact path="/" component={Home} />
          <ProtectedRoute path="/profile" component={Profile} />
          <ProtectedRoute path="/aboutus" component={Aboutus} />
          <Route path="/register" component={Register} />
          <Route path="/login" component={Login} />
      </Switch>
    </>
   </BrowserRouter>
  </UserProfileContext.Provider>
  );
};
ReactDOM.render(
  React.createElement(App, null),
  document.getElementById("root")
);

export default App;
import React from 'react';

export default React.createContext();

您可以利用
react redux
进行全局状态处理,或者将回调函数从
Navigation.js
传递到
Profile.js

您可以利用
react redux
进行全局状态处理,或者将回调函数从
Navigation.js
传递到
Profile.js

使用React的内置上下文API。在上下文提供程序中包装您的应用程序,然后您可以使用useContext钩子访问状态,在组件之间分派状态更新

应用程序级设置-一次

// Define Context
const AppContext = React.createContext()

// Define initial state
const initialState = {}

// Define Reducer
const Reducer = (state, dispatch) => {
  switch(action.type) {
    case "ACTION_TYPE": return {...state, prop: action.payload}
    default: return state
  }
}


//Wrap main App in context, pass state from React's useReducer hook
const [state, dispatch] = useReducer(Reducer, initialState)
<AppContext.Provider data={{
  state,
  dispatch
}}>
  <ReactAppMainWrapper />
</AppContext.Provider>
解释

该州充当类似redux的商店,可在整个应用程序中使用

在任何组件中,导入AppContext并使用React的内置useContext钩子与组件中的存储进行交互


在上面的上下文提供程序中传递的数据对象可从此访问。

使用React的内置上下文API。在上下文提供程序中包装您的应用程序,然后您可以使用useContext钩子访问状态,在组件之间分派状态更新

应用程序级设置-一次

// Define Context
const AppContext = React.createContext()

// Define initial state
const initialState = {}

// Define Reducer
const Reducer = (state, dispatch) => {
  switch(action.type) {
    case "ACTION_TYPE": return {...state, prop: action.payload}
    default: return state
  }
}


//Wrap main App in context, pass state from React's useReducer hook
const [state, dispatch] = useReducer(Reducer, initialState)
<AppContext.Provider data={{
  state,
  dispatch
}}>
  <ReactAppMainWrapper />
</AppContext.Provider>
解释

该州充当类似redux的商店,可在整个应用程序中使用

在任何组件中,导入AppContext并使用React的内置useContext钩子与组件中的存储进行交互


上面的上下文提供程序中传递的数据对象可从此处获得。

与注释中提到的一样,一个选项是to(这应该是简单状态的首选选项)

实际上,这看起来像:

App.js

import React, { useState } from 'react';

import Navigation from './Navigation';
import Profile from './Profile';

function App() {
  const [name, setName] = useState('');

  return (
    <div className="App">
      <Navigation name={name} />
      <hr />
      <Profile name={name} setName={setName} />
    </div>
  );
}

export default App;
import React from 'react';

export default React.createContext();
import React, { useState } from 'react';
import { BrowserRouter, Route, Switch } from 'react-router-dom';

import './styles.css';
import Profile from './components/Profile';
import Navigation from './components/Navigation';
import UserProfileContext from './context';

const App = () => {
  const [data, setData] = useState({
    id: 'player-1',
    name: 'Player One',
    age: 25,
    photo: 'rose.JPG',
  });

  return (
    <UserProfileContext.Provider value={{ data, setData }}>
      <BrowserRouter>
        <Navigation />
        <Switch>
          <Route path="/profile" component={Profile} />
        </Switch>
      </BrowserRouter>
    </UserProfileContext.Provider>
  );
};

export default App;
import React, { useContext } from 'react';
import { NavLink } from 'react-router-dom';

import UserProfileContext from '../context';

const Navigation = () => {
  const { data } = useContext(UserProfileContext);

  const divStyle = {
    float: 'left',
    color: '#64cad8',
    padding: '0px 0px 0px 10px',
    font: 'Lucida, sans-serif',
  };

  return (
    <div className="App">
      <div className="wrapper">
        <nav className="siteNavigation_nav_links">
          <div className="clubLogo landing" style={divStyle}>
            <b>Soccer</b>
          </div>

          <NavLink className="mobile_register_link" to="/profile">
            Profile
          </NavLink>

          <div className="profileImage nav menu">
            <span>{data.name}</span> | <img alt="" src={data.photo} />
          </div>
        </nav>
      </div>
    </div>
  );
};

export default Navigation;
import React, { useContext } from 'react';
import { useForm } from 'react-hook-form';

import UserProfileContext from '../context';

const Profile = () => {
  const { setData } = useContext(UserProfileContext);
  const { register, handleSubmit } = useForm();

  return (
    <div>
      <form onSubmit={handleSubmit(setData)}>
        <b>Profile</b>
        <input name="id" ref={register} />
        <input name="name" ref={register} />
        <input name="age" ref={register} />
        <button type="submit" className="submitButton">
          Click
        </button>
      </form>
    </div>
  );
};

export default Profile;
App.js

import React, { useState } from 'react';

import Navigation from './Navigation';
import Profile from './Profile';

function App() {
  const [name, setName] = useState('');

  return (
    <div className="App">
      <Navigation name={name} />
      <hr />
      <Profile name={name} setName={setName} />
    </div>
  );
}

export default App;
import React from 'react';

export default React.createContext();
import React, { useState } from 'react';
import { BrowserRouter, Route, Switch } from 'react-router-dom';

import './styles.css';
import Profile from './components/Profile';
import Navigation from './components/Navigation';
import UserProfileContext from './context';

const App = () => {
  const [data, setData] = useState({
    id: 'player-1',
    name: 'Player One',
    age: 25,
    photo: 'rose.JPG',
  });

  return (
    <UserProfileContext.Provider value={{ data, setData }}>
      <BrowserRouter>
        <Navigation />
        <Switch>
          <Route path="/profile" component={Profile} />
        </Switch>
      </BrowserRouter>
    </UserProfileContext.Provider>
  );
};

export default App;
import React, { useContext } from 'react';
import { NavLink } from 'react-router-dom';

import UserProfileContext from '../context';

const Navigation = () => {
  const { data } = useContext(UserProfileContext);

  const divStyle = {
    float: 'left',
    color: '#64cad8',
    padding: '0px 0px 0px 10px',
    font: 'Lucida, sans-serif',
  };

  return (
    <div className="App">
      <div className="wrapper">
        <nav className="siteNavigation_nav_links">
          <div className="clubLogo landing" style={divStyle}>
            <b>Soccer</b>
          </div>

          <NavLink className="mobile_register_link" to="/profile">
            Profile
          </NavLink>

          <div className="profileImage nav menu">
            <span>{data.name}</span> | <img alt="" src={data.photo} />
          </div>
        </nav>
      </div>
    </div>
  );
};

export default Navigation;
import React, { useContext } from 'react';
import { useForm } from 'react-hook-form';

import UserProfileContext from '../context';

const Profile = () => {
  const { setData } = useContext(UserProfileContext);
  const { register, handleSubmit } = useForm();

  return (
    <div>
      <form onSubmit={handleSubmit(setData)}>
        <b>Profile</b>
        <input name="id" ref={register} />
        <input name="name" ref={register} />
        <input name="age" ref={register} />
        <button type="submit" className="submitButton">
          Click
        </button>
      </form>
    </div>
  );
};

export default Profile;
import React,{useState}来自“React”;
从“react router dom”导入{BrowserRouter,Route,Switch};
导入“./styles.css”;
从“./components/Profile”导入配置文件;
从“./components/Navigation”导入导航;
从“./context”导入UserProfileContext;
常量应用=()=>{
const[data,setData]=useState({
id:‘玩家1’,
名字:'玩家一',
年龄:25岁,
照片:“rose.JPG”,
});
返回(
);
};
导出默认应用程序;
组件/Navigation.js

import React, { useState } from 'react';

import Navigation from './Navigation';
import Profile from './Profile';

function App() {
  const [name, setName] = useState('');

  return (
    <div className="App">
      <Navigation name={name} />
      <hr />
      <Profile name={name} setName={setName} />
    </div>
  );
}

export default App;
import React from 'react';

export default React.createContext();
import React, { useState } from 'react';
import { BrowserRouter, Route, Switch } from 'react-router-dom';

import './styles.css';
import Profile from './components/Profile';
import Navigation from './components/Navigation';
import UserProfileContext from './context';

const App = () => {
  const [data, setData] = useState({
    id: 'player-1',
    name: 'Player One',
    age: 25,
    photo: 'rose.JPG',
  });

  return (
    <UserProfileContext.Provider value={{ data, setData }}>
      <BrowserRouter>
        <Navigation />
        <Switch>
          <Route path="/profile" component={Profile} />
        </Switch>
      </BrowserRouter>
    </UserProfileContext.Provider>
  );
};

export default App;
import React, { useContext } from 'react';
import { NavLink } from 'react-router-dom';

import UserProfileContext from '../context';

const Navigation = () => {
  const { data } = useContext(UserProfileContext);

  const divStyle = {
    float: 'left',
    color: '#64cad8',
    padding: '0px 0px 0px 10px',
    font: 'Lucida, sans-serif',
  };

  return (
    <div className="App">
      <div className="wrapper">
        <nav className="siteNavigation_nav_links">
          <div className="clubLogo landing" style={divStyle}>
            <b>Soccer</b>
          </div>

          <NavLink className="mobile_register_link" to="/profile">
            Profile
          </NavLink>

          <div className="profileImage nav menu">
            <span>{data.name}</span> | <img alt="" src={data.photo} />
          </div>
        </nav>
      </div>
    </div>
  );
};

export default Navigation;
import React, { useContext } from 'react';
import { useForm } from 'react-hook-form';

import UserProfileContext from '../context';

const Profile = () => {
  const { setData } = useContext(UserProfileContext);
  const { register, handleSubmit } = useForm();

  return (
    <div>
      <form onSubmit={handleSubmit(setData)}>
        <b>Profile</b>
        <input name="id" ref={register} />
        <input name="name" ref={register} />
        <input name="age" ref={register} />
        <button type="submit" className="submitButton">
          Click
        </button>
      </form>
    </div>
  );
};

export default Profile;
import React,{useContext}来自“React”;
从'react router dom'导入{NavLink};
从“../context”导入UserProfileContext;
常量导航=()=>{
const{data}=useContext(UserProfileContext);
常量divStyle={
浮动:'左',
颜色:“#64cad8”,
填充:“0px 0px 0px 10px”,
字体:“Lucida,无衬线”,
};
返回(
足球
轮廓
{data.name}|
);
};
导出默认导航;
组件/Profile.js

import React, { useState } from 'react';

import Navigation from './Navigation';
import Profile from './Profile';

function App() {
  const [name, setName] = useState('');

  return (
    <div className="App">
      <Navigation name={name} />
      <hr />
      <Profile name={name} setName={setName} />
    </div>
  );
}

export default App;
import React from 'react';

export default React.createContext();
import React, { useState } from 'react';
import { BrowserRouter, Route, Switch } from 'react-router-dom';

import './styles.css';
import Profile from './components/Profile';
import Navigation from './components/Navigation';
import UserProfileContext from './context';

const App = () => {
  const [data, setData] = useState({
    id: 'player-1',
    name: 'Player One',
    age: 25,
    photo: 'rose.JPG',
  });

  return (
    <UserProfileContext.Provider value={{ data, setData }}>
      <BrowserRouter>
        <Navigation />
        <Switch>
          <Route path="/profile" component={Profile} />
        </Switch>
      </BrowserRouter>
    </UserProfileContext.Provider>
  );
};

export default App;
import React, { useContext } from 'react';
import { NavLink } from 'react-router-dom';

import UserProfileContext from '../context';

const Navigation = () => {
  const { data } = useContext(UserProfileContext);

  const divStyle = {
    float: 'left',
    color: '#64cad8',
    padding: '0px 0px 0px 10px',
    font: 'Lucida, sans-serif',
  };

  return (
    <div className="App">
      <div className="wrapper">
        <nav className="siteNavigation_nav_links">
          <div className="clubLogo landing" style={divStyle}>
            <b>Soccer</b>
          </div>

          <NavLink className="mobile_register_link" to="/profile">
            Profile
          </NavLink>

          <div className="profileImage nav menu">
            <span>{data.name}</span> | <img alt="" src={data.photo} />
          </div>
        </nav>
      </div>
    </div>
  );
};

export default Navigation;
import React, { useContext } from 'react';
import { useForm } from 'react-hook-form';

import UserProfileContext from '../context';

const Profile = () => {
  const { setData } = useContext(UserProfileContext);
  const { register, handleSubmit } = useForm();

  return (
    <div>
      <form onSubmit={handleSubmit(setData)}>
        <b>Profile</b>
        <input name="id" ref={register} />
        <input name="name" ref={register} />
        <input name="age" ref={register} />
        <button type="submit" className="submitButton">
          Click
        </button>
      </form>
    </div>
  );
};

export default Profile;
import React,{useContext}来自“React”;
从“react hook form”导入{useForm};
从“../context”导入UserProfileContext;
常量配置文件=()=>{
const{setData}=useContext(UserProfileContext);
常量{register,handleSubmit}=useForm();
返回(
轮廓
点击
);
};
导出默认配置文件;

与评论中提到的一样,一个选项是to(这应该是简单状态的首选选项)

实际上,这看起来像:

App.js

import React, { useState } from 'react';

import Navigation from './Navigation';
import Profile from './Profile';

function App() {
  const [name, setName] = useState('');

  return (
    <div className="App">
      <Navigation name={name} />
      <hr />
      <Profile name={name} setName={setName} />
    </div>
  );
}

export default App;
import React from 'react';

export default React.createContext();
import React, { useState } from 'react';
import { BrowserRouter, Route, Switch } from 'react-router-dom';

import './styles.css';
import Profile from './components/Profile';
import Navigation from './components/Navigation';
import UserProfileContext from './context';

const App = () => {
  const [data, setData] = useState({
    id: 'player-1',
    name: 'Player One',
    age: 25,
    photo: 'rose.JPG',
  });

  return (
    <UserProfileContext.Provider value={{ data, setData }}>
      <BrowserRouter>
        <Navigation />
        <Switch>
          <Route path="/profile" component={Profile} />
        </Switch>
      </BrowserRouter>
    </UserProfileContext.Provider>
  );
};

export default App;
import React, { useContext } from 'react';
import { NavLink } from 'react-router-dom';

import UserProfileContext from '../context';

const Navigation = () => {
  const { data } = useContext(UserProfileContext);

  const divStyle = {
    float: 'left',
    color: '#64cad8',
    padding: '0px 0px 0px 10px',
    font: 'Lucida, sans-serif',
  };

  return (
    <div className="App">
      <div className="wrapper">
        <nav className="siteNavigation_nav_links">
          <div className="clubLogo landing" style={divStyle}>
            <b>Soccer</b>
          </div>

          <NavLink className="mobile_register_link" to="/profile">
            Profile
          </NavLink>

          <div className="profileImage nav menu">
            <span>{data.name}</span> | <img alt="" src={data.photo} />
          </div>
        </nav>
      </div>
    </div>
  );
};

export default Navigation;
import React, { useContext } from 'react';
import { useForm } from 'react-hook-form';

import UserProfileContext from '../context';

const Profile = () => {
  const { setData } = useContext(UserProfileContext);
  const { register, handleSubmit } = useForm();

  return (
    <div>
      <form onSubmit={handleSubmit(setData)}>
        <b>Profile</b>
        <input name="id" ref={register} />
        <input name="name" ref={register} />
        <input name="age" ref={register} />
        <button type="submit" className="submitButton">
          Click
        </button>
      </form>
    </div>
  );
};

export default Profile;
App.js

import React, { useState } from 'react';

import Navigation from './Navigation';
import Profile from './Profile';

function App() {
  const [name, setName] = useState('');

  return (
    <div className="App">
      <Navigation name={name} />
      <hr />
      <Profile name={name} setName={setName} />
    </div>
  );
}

export default App;
import React from 'react';

export default React.createContext();
import React, { useState } from 'react';
import { BrowserRouter, Route, Switch } from 'react-router-dom';

import './styles.css';
import Profile from './components/Profile';
import Navigation from './components/Navigation';
import UserProfileContext from './context';

const App = () => {
  const [data, setData] = useState({
    id: 'player-1',
    name: 'Player One',
    age: 25,
    photo: 'rose.JPG',
  });

  return (
    <UserProfileContext.Provider value={{ data, setData }}>
      <BrowserRouter>
        <Navigation />
        <Switch>
          <Route path="/profile" component={Profile} />
        </Switch>
      </BrowserRouter>
    </UserProfileContext.Provider>
  );
};

export default App;
import React, { useContext } from 'react';
import { NavLink } from 'react-router-dom';

import UserProfileContext from '../context';

const Navigation = () => {
  const { data } = useContext(UserProfileContext);

  const divStyle = {
    float: 'left',
    color: '#64cad8',
    padding: '0px 0px 0px 10px',
    font: 'Lucida, sans-serif',
  };

  return (
    <div className="App">
      <div className="wrapper">
        <nav className="siteNavigation_nav_links">
          <div className="clubLogo landing" style={divStyle}>
            <b>Soccer</b>
          </div>

          <NavLink className="mobile_register_link" to="/profile">
            Profile
          </NavLink>

          <div className="profileImage nav menu">
            <span>{data.name}</span> | <img alt="" src={data.photo} />
          </div>
        </nav>
      </div>
    </div>
  );
};

export default Navigation;
import React, { useContext } from 'react';
import { useForm } from 'react-hook-form';

import UserProfileContext from '../context';

const Profile = () => {
  const { setData } = useContext(UserProfileContext);
  const { register, handleSubmit } = useForm();

  return (
    <div>
      <form onSubmit={handleSubmit(setData)}>
        <b>Profile</b>
        <input name="id" ref={register} />
        <input name="name" ref={register} />
        <input name="age" ref={register} />
        <button type="submit" className="submitButton">
          Click
        </button>
      </form>
    </div>
  );
};

export default Profile;
import React,{useState}来自“React”;
从“react router dom”导入{BrowserRouter,Route,Switch};
导入“./styles.css”;
从“./components/Profile”导入配置文件;
从“./components/Navigation”导入导航;
从“./context”导入UserProfileContext;
常量应用=()=>{
const[data,setData]=useState({
id:‘玩家1’,
名字:'玩家一',
年龄:25岁,
照片:“rose.JPG”,
});
返回(
);
};
导出默认应用程序;
组件/Navigation.js

import React, { useState } from 'react';

import Navigation from './Navigation';
import Profile from './Profile';

function App() {
  const [name, setName] = useState('');

  return (
    <div className="App">
      <Navigation name={name} />
      <hr />
      <Profile name={name} setName={setName} />
    </div>
  );
}

export default App;
import React from 'react';

export default React.createContext();
import React, { useState } from 'react';
import { BrowserRouter, Route, Switch } from 'react-router-dom';

import './styles.css';
import Profile from './components/Profile';
import Navigation from './components/Navigation';
import UserProfileContext from './context';

const App = () => {
  const [data, setData] = useState({
    id: 'player-1',
    name: 'Player One',
    age: 25,
    photo: 'rose.JPG',
  });

  return (
    <UserProfileContext.Provider value={{ data, setData }}>
      <BrowserRouter>
        <Navigation />
        <Switch>
          <Route path="/profile" component={Profile} />
        </Switch>
      </BrowserRouter>
    </UserProfileContext.Provider>
  );
};

export default App;
import React, { useContext } from 'react';
import { NavLink } from 'react-router-dom';

import UserProfileContext from '../context';

const Navigation = () => {
  const { data } = useContext(UserProfileContext);

  const divStyle = {
    float: 'left',
    color: '#64cad8',
    padding: '0px 0px 0px 10px',
    font: 'Lucida, sans-serif',
  };

  return (
    <div className="App">
      <div className="wrapper">
        <nav className="siteNavigation_nav_links">
          <div className="clubLogo landing" style={divStyle}>
            <b>Soccer</b>
          </div>

          <NavLink className="mobile_register_link" to="/profile">
            Profile
          </NavLink>

          <div className="profileImage nav menu">
            <span>{data.name}</span> | <img alt="" src={data.photo} />
          </div>
        </nav>
      </div>
    </div>
  );
};

export default Navigation;
import React, { useContext } from 'react';
import { useForm } from 'react-hook-form';

import UserProfileContext from '../context';

const Profile = () => {
  const { setData } = useContext(UserProfileContext);
  const { register, handleSubmit } = useForm();

  return (
    <div>
      <form onSubmit={handleSubmit(setData)}>
        <b>Profile</b>
        <input name="id" ref={register} />
        <input name="name" ref={register} />
        <input name="age" ref={register} />
        <button type="submit" className="submitButton">
          Click
        </button>
      </form>
    </div>
  );
};

export default Profile;
import React,{useContext}来自“React”;
从'react router dom'导入{NavLink};
从“../context”导入UserProfileContext;
常量导航=()=>{
const{data}=useContext(UserProfileContext);
常量divStyle={
浮动:'左',
颜色:“#64cad8”,
填充:“0px 0px 0px 10px”,
字体:“Lucida,无衬线”,
};
返回(
足球
轮廓
{data.name}|
);
};
导出默认导航;
组件/Profile.js

import React, { useState } from 'react';

import Navigation from './Navigation';
import Profile from './Profile';

function App() {
  const [name, setName] = useState('');

  return (
    <div className="App">
      <Navigation name={name} />
      <hr />
      <Profile name={name} setName={setName} />
    </div>
  );
}

export default App;
import React from 'react';

export default React.createContext();
import React, { useState } from 'react';
import { BrowserRouter, Route, Switch } from 'react-router-dom';

import './styles.css';
import Profile from './components/Profile';
import Navigation from './components/Navigation';
import UserProfileContext from './context';

const App = () => {
  const [data, setData] = useState({
    id: 'player-1',
    name: 'Player One',
    age: 25,
    photo: 'rose.JPG',
  });

  return (
    <UserProfileContext.Provider value={{ data, setData }}>
      <BrowserRouter>
        <Navigation />
        <Switch>
          <Route path="/profile" component={Profile} />
        </Switch>
      </BrowserRouter>
    </UserProfileContext.Provider>
  );
};

export default App;
import React, { useContext } from 'react';
import { NavLink } from 'react-router-dom';

import UserProfileContext from '../context';

const Navigation = () => {
  const { data } = useContext(UserProfileContext);

  const divStyle = {
    float: 'left',
    color: '#64cad8',
    padding: '0px 0px 0px 10px',
    font: 'Lucida, sans-serif',
  };

  return (
    <div className="App">
      <div className="wrapper">
        <nav className="siteNavigation_nav_links">
          <div className="clubLogo landing" style={divStyle}>
            <b>Soccer</b>
          </div>

          <NavLink className="mobile_register_link" to="/profile">
            Profile
          </NavLink>

          <div className="profileImage nav menu">
            <span>{data.name}</span> | <img alt="" src={data.photo} />
          </div>
        </nav>
      </div>
    </div>
  );
};

export default Navigation;
import React, { useContext } from 'react';
import { useForm } from 'react-hook-form';

import UserProfileContext from '../context';

const Profile = () => {
  const { setData } = useContext(UserProfileContext);
  const { register, handleSubmit } = useForm();

  return (
    <div>
      <form onSubmit={handleSubmit(setData)}>
        <b>Profile</b>
        <input name="id" ref={register} />
        <input name="name" ref={register} />
        <input name="age" ref={register} />
        <button type="submit" className="submitButton">
          Click
        </button>
      </form>
    </div>
  );
};

export default Profile;
import React,{useContext}来自“React”;
从“react hook form”导入{useForm};
从“../context”导入UserProfileContext;
常量配置文件=()=>{
const{setData}=useContext(UserProfileContext);
常量{register,handleSubmit}=useForm();
返回(
轮廓
点击
);
};
导出默认配置文件;

你需要
提升你的状态
——或者使用类似于
上下文
——你需要
提升你的状态
——或者使用类似于
上下文
——除了使用redux?Ofc还有其他方法吗。对于这一次的使用,我建议你提升你的状态reactjs.org/docs/lifting-state-up.html,除非你更经常地使用它。除了使用redux?Ofc,还有其他方法吗。对于这一次使用,我建议您提升您的状态reactjs.org/docs/lifting-state-up.html,而不是更频繁地使用它