将两个常量从一个组件导出到另一个组件

Export two constants from one component to another

所以我试图将两个常量纬度和经度导出到另一个组件,它不是具有常量的组件的子组件或父组件,所以我不能使用上下文或道具。我尝试导出为命名变量,但因为常量是在 Header 组件中定义的,所以它们超出了导出语句的范围。有人请帮我解决这个问题,如果我再花时间尝试解决它,我会哭的。

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

function Header() {

    const [text, setText] = useState("");
    const [latitude, setLatitude] = useState(0);
    const [longitude, setLongitude] = useState(0);


    function handleChange(event) {
        setText(event.target.value);
    }

    function handleClick() {
        const geoCoderURL = "http://api.openweathermap.org/geo/1.0/direct?q=" + text + "&limit=5&appid={apikey}"
        function getCoordinates(url) {
            axios.get(url).then((response) => {
                setLatitude(response.data[0].lat);
                setLongitude(response.data[0].lon);
            });
        } 
        getCoordinates(geoCoderURL);        
    }

    return (
        <div>
            <h1>Five Day Forecast</h1> 
            <input onChange={handleChange} type="text" name="name" autoFocus placeholder="Enter location here."/>
            <button type="submit" onClick={handleClick}>Forecast</button> 
        </div>
    )
}

export const locationLat = latitude;
export const locationLon = longitude;
export default Header;


这是上下文的基本设置。这个特定的例子展示了上下文的创建,一个将状态保存在上下文中的包装器,以及一个用于从任何组件访问上下文值的自定义挂钩。

除了 Context.Provider 部分外,提供程序组件看起来就像一个常规组件。这是将上下文的值公开给其后代的上下文的一部分。

// coordinates-context.js
import { createContext, useContext, useState } from 'react';

/**
 * Create a new context.
 */
const CoordinatesContext = createContext();

/**
 * Create a provider wrapper which is responsible for the state 
 * and children of the context. In a lot of ways it works just like
 * a normal component, except for the Provider part, which is special
 * for the Context API.
 */
export const CoordinatesProvider = ({ children }) => {
  const [coordinates, setCoordinates] = useState({ lat: null, lng: null });

  return (
    <CoordinatesContext.Provider value={[coordinates, setCoordinates]}>
      {children}
    </CoordinatesContext.Provider>
  );
};

/**
 * This custom hook will allow us you use the context in any component.
 */
export const useCoordinatesContext = useContext(CoordinatesContext);

提供者组件应该有需要数据的组件作为后代,如下例所示。

<App>
  <CoordinatesProvider>
    <Header/>
    <OtherComponent/>
  </CoordinatesProvider>
</App>

现在所有后代都可以访问了,我们可以使用自定义挂钩来使用和操作暴露的值。

我们的上下文只是公开了一个状态,因此实现就像使用 useState 挂钩一样。

现在唯一的区别是,只要任何组件更新上下文内部的状态,所有使用上下文的组件都会更新。

import React, { useState } from 'react';
import { useCoordinatesContext } from '../your-path-to/coordinates-context.js';
import axios from 'axios'; 

function Header() {
  const [text, setText] = useState("");

  /**
   * The hook exposes the useState values from the context provider.
   */
  const [coordinates, setCoordinates] = useCoordinatesContext();

  function handleChange(event) {
    setText(event.target.value);
  }

  function handleClick() {
    const geoCoderURL = "http://api.openweathermap.org/geo/1.0/direct?q=" + text + "&limit=5&appid={apikey}";

    function getCoordinates(url) {
      axios.get(url).then((response) => {

        /**
         * Update context state.
         */
        setCoordinates({
          lat: response.data[0].lat,
          lng: response.data[0].lon
        });
      });
    } 
    getCoordinates(geoCoderURL);        
  }

  return (
    <div>
      <h1>Five Day Forecast</h1> 
      <input onChange={handleChange} type="text" name="name" autoFocus placeholder="Enter location here."/>
      <button type="submit" onClick={handleClick}>Forecast</button> 
    </div>
  );
}

您不能将功能组件外部的状态作为常量导出,但是您可以采用多种解决方案来解决您的问题。

  1. 使用 React.createContext 和 React.useContext 挂钩。如果你在所有需要它的组件的父组件中定义钩子,你就不会有访问问题(大多数时候这个父组件是 App 组件)。

  2. 使用状态管理器,比如 Redux。这使您可以在应用程序的任何位置访问 getter 和 setter。 注意:Redux 在应用程序中添加了一些样板文件,因此如果您还没有使用它,请首选第一种解决方案。

  3. 在本地存储中保存坐标。 IMO 这几乎不是一个好的解决方案,因为不允许您在坐标更新时收到通知,但在某些情况下很适合。