【问题标题】:How to send value from one component, to another如何将价值从一个组件发送到另一个组件
【发布时间】:2020-07-30 16:17:43
【问题描述】:

我的一个组件中有这个道具,我想将它传递给另一个组件并在那里用作变量:

const VerContinentToolbar = (props) => {


   return (
     <Menu className="nav-icon">
       <CountryList displayFields={["countryName"]} />
     </Menu>
   );
 };

如果我使用 console.log(props.props),我会得到: https://imgur.com/a/HnRHDcH 这是我要传递给 useCountries 的值。 接收组件如下所示:

const useCountries = (props) => {
    const [countries, setCountries] = useState([])


    useEffect(() => {
        firebase
            .firestore()
            .collection("Africa")
            .onSnapshot((snapshot) => {
                const newCountries = snapshot.docs.map((doc) => ({
                    id: doc.id,
                    ...doc.data()
                }))
                setCountries(newCountries)
            })
    }, [])
    return countries
}



const CountryList = ({ displayFields = [] }) => {
    const countries = useCountries();
    console.log(countries)

    return (
        <div className="countries">
            {countries.map(country => (
                <div key={country.id}>

                    <div className="entry">

                        {displayFields.includes("continent") && (
                            <div>Name of continent: {country.continent}</div>

                        )}
                        {displayFields.includes("revName") && (
                            <div>{country.revName}</div>
                        )}
                        {displayFields.includes("countryName") && (
                            <div><Link to={"./Jumbotron"}>{country.countryName}</Link></div>
                        )}
                        {displayFields.includes("dest1") && (
                            <div>Destination 1: {country.dest1}</div>
                        )}
                        {displayFields.includes("dest2") && (
                            <div>Destination 2: {country.dest2}</div>
                        )}
                        {displayFields.includes("dest3") && (
                            <div>Destination 3: {country.dest3}</div>
                        )}
                        {displayFields.includes("beerPrice") && (
                            <div>Beer price: {country.beerPrice}</div>
                        )}
                        {displayFields.includes("foodPrice") && (
                            <div>Food price: {country.foodPrice}</div>
                        )}
                        {displayFields.includes("hostelPrice") && (
                            <div>Hostel price: {country.hostelPrice}</div>
                        )}
                        {displayFields.includes("review") && <div>Review: {country.review}</div>}
                        {displayFields.includes("imgUrl") && <img src={country.url} alt="no-img" />}
                    </div>
                </div>
            ))}
        </div>
    );
};

我已经尝试并尝试理解上下文,但我无法真正理解它。我想将道具的价值放入“.collection(“Africa”)”,但我不知道如何去做。我已经阅读了它的文档,但是我太笨了,无法正确理解它。

如果有其他解决方案,我会全力以赴。

我想传递的道具是:我为每个大陆创建了一个组件。在每个组件中,我调用 VerContinentToolbar,传递大陆的属性/名称,如下所示:

const Africa = ({}) => {

  return (
    <div>
      <VerContinentToolbar props={["Africa"]} />
This means, that

 const VerContinentToolbar = (props) => {

   return (
     <Menu className="nav-icon">
       <CountryList displayFields={["countryName"]} />
     </Menu>
   );
 };

包含“非洲”一词。

我想将“Africa”传递给我的组件,该组件会获取大陆(在本例中为非洲)的集合。

我想将道具持有的信息传递给这个:

const useCountries = (props) => {
    const [countries, setCountries] = useState([])


    useEffect(() => {
        firebase
            .firestore()
            .collection("Africa") <---- I WANT PROP FROM VERCONT HERE
            .onSnapshot((snapshot) => {
                const newCountries = snapshot.docs.map((doc) => ({
                    id: doc.id,
                    ...doc.data()
                }))
                setCountries(newCountries)
            })
    }, [])
    return countries
}

为了更清楚地说明这一点,我附上了两张图片。亚洲:在这里,我想渲染集合“亚洲”,以显示属于亚洲大陆内一个国家的每条评论。

https://imgur.com/a/bZhQAwz

到目前为止,我已经在 Firebase 中创建了“Imagination land”并将其附加到“Africa”。我只想在非洲部分展示这一点。显然,我想在 Asia 组件中显示所有带有 Asia 标签的国家/地区。

谢谢

编辑: 问题解决了。

import React, { Component, useState, useEffect } from 'react'
import { Link } from 'react-router-dom';
import firebase from '../config'
import './Countries.css'
import props from './Navbar/VerContinentToolbar';



const useCountries = continent => {
    const [countries, setCountries] = useState([]);
      console.log('continent', continent) // <--- Get it as your first argument
      console.log(continent.toString())

    useEffect(() => {
        firebase
            .firestore()
            .collection(continent.toString())
            .onSnapshot((snapshot) => {
                const newCountries = snapshot.docs.map((doc) => ({

                    id: doc.id,

                    ...doc.data()

                }))
                setCountries(newCountries)

            })
    }, [])

    return countries
}



const CountryList = ({ continent, displayFields = []  }) => {
    const countries = useCountries(continent); // <--- Pass it in here

    return (
        <div className="countries">
            {countries.map(country => (
                <div key={country.id}>

                    <div className="entry">

                        {displayFields.includes("continent") && (
                            <div>Name of continent: {country.continent}</div>

                        )}
                        {displayFields.includes("revName") && (
                            <div>{country.revName}</div>
                        )}
                        {displayFields.includes("countryName") && (
                            <div><Link to={"./Jumbotron"}>{country.countryName}</Link></div>
                        )}
                        {displayFields.includes("dest1") && (
                            <div>Destination 1: {country.dest1}</div>
                        )}
                        {displayFields.includes("dest2") && (
                            <div>Destination 2: {country.dest2}</div>
                        )}
                        {displayFields.includes("dest3") && (
                            <div>Destination 3: {country.dest3}</div>
                        )}
                        {displayFields.includes("beerPrice") && (
                            <div>Beer price: {country.beerPrice}</div>
                        )}
                        {displayFields.includes("foodPrice") && (
                            <div>Food price: {country.foodPrice}</div>
                        )}
                        {displayFields.includes("hostelPrice") && (
                            <div>Hostel price: {country.hostelPrice}</div>
                        )}
                        {displayFields.includes("review") && <div>Review: {country.review}</div>}
                        {displayFields.includes("imgUrl") && <img src={country.url} alt="no-img" />}



}
                    </div>
                </div>

            ))}
        </div>
    );
};


export default CountryList
const VerContinentToolbar = (props) => {

  return (
    <Menu className="nav-icon">
      <CountryList
        continent={props.continent}
        displayFields={["countryName"]}
      />
    </Menu>
  );
};

感谢您的所有帮助。

【问题讨论】:

    标签: javascript reactjs firebase-realtime-database react-props


    【解决方案1】:

    据我了解您的问题是,您想在CountryList 内调用useCountries 挂钩来指定您想要的集合。

    const useCountries = (collection) => {
      const [countries, setCountries] = useState([])
    
      useEffect(() => {
        firebase
          .firestore()
          .collection(collection) // <-- pass collection argument here
          .onSnapshot((snapshot) => {
            const newCountries = snapshot.docs.map((doc) => ({
              id: doc.id,
              ...doc.data()
            }))
            setCountries(newCountries)
          })
      }, [])
      return countries
    }
    

    CountryList 中将你想要的值传递给useCountries

    const countries = useCountries('Africa');
    

    【讨论】:

    • 是的,类似的。谢谢!但是,我不想手动将值传递给 useCountries。如果我在组件“非洲”中,我希望将“非洲”传递给该钩子。如果我在“欧洲”组件中,我希望通过“欧洲”。你明白我的意思吗?
    • @Jannemannen 那么,将“收集”道具传递给CountryList 以传递给钩子?
    【解决方案2】:
    1. 将它作为来自您的大陆组件的道具(大陆)传递

      const Africa = () => {
        return (
          <div>
            <VerContinentToolbar continent="Africa" />
          </div>
        );
      };
      
    2. &lt;VerContinentToolbar /&gt; 中,获取道具并将其传递给&lt;CountryList /&gt;。您可以使用 context API 或 Redux 来代替将 props 传递给孙子组件。

      const VerContinentToolbar = props => {
        console.log('continent prop is now here', props.continent)
        return (
          <Menu className="nav-icon">
            <CountryList continent={props.continent} displayFields={["countryName"]} />
          </Menu>
        );
      };
      
    3. &lt;CountryList /&gt; 中,获取道具 (continent) 并将其传递到您的 useCountries 钩子中。

      const CountryList = props => {
        const countries = useCountries(props.continent); // <--- Pass it in here
        console.log(countries)
      
        return (
          <div className="countries">
            {countries.map(country => (
              {/* ...code */}
            ))}
          </div>
        );
      };
      
    4. 最后在你的钩子里把它作为第一个参数

      const useCountries = continent => {
        const [countries, setCountries] = useState([]);
        console.log('continent', continent) // <--- Get it as your first argument
      
        // ...code
        return countries
      }
      

    【讨论】:

    • 感谢您的回答。我试过了,在我将它传递给 CountryList 之前一切正常。在这里我收到错误“TypeError:无法读取未定义的属性'大陆'”。因为: const countries = useCountries(props.continent); //
    • 你能把你当前的代码粘贴到 github gist gist.github.com/new 吗?我将更快地调试问题以了解您为什么会收到 TypeError。我认为问题可能是在将 prop 传递到 &lt;CountryList /&gt; 组件时出现拼写错误。
    • 在你的国家&lt;CountryList /&gt; 组件中,你能用console.log(props) 告诉我结果吗?
    • 啊哈哈,很高兴能帮上忙。我已经完成了创建一个代码笔,向您展示它的工作原理。 codepen.io/RB_Projects/pen/BaoKxNW。无论如何,欢迎你:)
    猜你喜欢
    • 1970-01-01
    • 2016-04-20
    • 2023-01-16
    • 2021-08-07
    • 1970-01-01
    • 2021-05-02
    • 2021-10-04
    • 2020-12-06
    • 1970-01-01
    相关资源
    最近更新 更多