隐藏和显示导入组件上的 onSubmit 事件数据

Hide and show data onSubmit event on imported Component

如果有人搜索我的列表项,我想隐藏我的数据。我已经在主页上导入了我的搜索栏,尽管我使用带有 useState 的条件变量,但似乎数据没有重新呈现。

我想要实现的是这样一个事实,即在开始时用户看到的是带有项目列表的搜索栏。每当用户搜索字符串时,我想隐藏我的项目列表,因为新数据将显示。目前,每当用户搜索时,都会检索搜索项 + 初始项列表,这是不正确的。

请找到我的代码:

import React, {useState} from 'react'
import { Link } from 'react-router-dom'
import { useQuery, gql } from '@apollo/client'
import SearchReviews from "./SearchReviews"

const REVIEWS = gql`
  query GetReviews {
    reviews (sort: "createdAt:desc") {
        data{
            ...
                }
              }
            }
        }
    }
  }
`

export default function Homepage() {
    const { loading, error, data } = useQuery(REVIEWS)
    const [ show, setShow] = useState(true)

    if (loading) return <p>Loading...</p>
    if (error) return <p>`Error! ${error}`</p>

    // console.log(data)
    return (
        <div>
            <SearchReviews onSubmit={e => {
                e.preventDefault()
                // console.log(e.target[0].value)
                setShow(false). <==================HERE
            }}/>

            {show && (
                <div>
                        {data.reviews.data.map(review => (
                            <div key={review.id} className="review-card">
                                <div className="rating">{review.attributes.rating}</div>
                                <h2>{review.attributes.title}</h2>
                                <h5>{review.attributes.createdAt.substring(0, 10)}</h5>

                                {review.attributes.categories.data.map(c => (
                                    <small key={c.id}>{c.attributes.name}</small>
                                ))}

                                <p>{review.attributes.body.substring(0, 200)}... </p>
                                <Link to={`/details/${review.id}`}>Read more</Link>
                            </div>
                        ))}
                </div>
                )}
            </div>
    )
}

和 SearchReviews.js


export default function SearchReviews() {
    const [ first, setFirst ] = useState(false)
    const [ query, setQuery] = useState("")

    const { loading, error, data } = useQuery(SEARCH, {skip: !first,variables: {my_query: query}})
    if (loading) return <p>Loading data...</p>
    if (error) return <p>`Error! ${error}`</p>
    // console.log(data)
    return (
        <div>

            <div className="wrap">
                <div className="search">
                    <form onSubmit={e => {
                        e.preventDefault()
                        // console.log(e.target[0].value)
                        setQuery(e.target[0].value)
                        setFirst(true)


                    }}>

                        <input type="search"
                               placeholder="Search Malware"
                               className="searchTerm"
                               id="input_text"
                               autoComplete="off"
                                />
                        <br/>
                        {/*<button type="submit" className="searchButton">Submit</button>*/}
                    </form>
                </div>
            </div>

            {first && (

            <div className="dataResult">
                    {data.reviews.data.map(review => (
                        <div key={review.id} className="review-card">
                        <div className="rating">{review.attributes.rating}</div>
                        <h2>{review.attributes.title}</h2>
                        <h5>{review.attributes.createdAt.substring(0, 10)}</h5>

                        {review.attributes.categories.data.map(c => (
                            <small key={c.id}>{c.attributes.name}</small>
                            ))}

                            <p>{review.attributes.body.substring(0, 200)}... </p>
                            <Link to={`/details/${review.id}`}>Read more</Link>
                            </div>
                            ))}

            </div>
                )}
        </div>
    )
}

目前,尽管提交了表单,但旧数据并未被删除,这意味着尽管变量已更改,但新状态不会在 DOM 中重新呈现。我想我需要 return 从子组件 <SearchReviews /> 到父组件的布尔值并更改状态。

我尝试过这样的事件:

    const updateShow = () => {
        setShow(false)
    }

return (
        <div>
            <SearchReviews onChange={updateShow}/>
            <Link to={`/search/`}>Search Library</Link>
            <button> | </button>
            <Link to={`/create`}>Create</Link>
            <button> | </button>
            <Link to={`/new`}>New</Link>
            {show && (
                <div>
                        {data.reviews.data.map(review => (
                            <div key={review.id} className="review-card">
                                <div className="rating">{review.attributes.rating}</div>
                                <h2>{review.attributes.title}</h2>
                                <h5>{review.attributes.createdAt.substring(0, 10)}</h5>

                                {review.attributes.categories.data.map(c => (
                                    <small key={c.id}>{c.attributes.name}</small>
                                ))}

                                <p>{review.attributes.body.substring(0, 200)}... </p>
                                <Link to={`/details/${review.id}`}>Read more</Link>
                            </div>
                        ))}
                </div>
                )}
            </div>
    )

非常感谢任何帮助!

您可以将 setShow 作为 props 传递给 SearchReviews 组件。

export default function SearchReviews({setShow}) {
    const [ first, setFirst ] = useState(false)
    const [ query, setQuery] = useState("")

    // Call the parent function (passed by props) within the child handler
     <form onSubmit={e => {
         e.preventDefault()
         // console.log(e.target[0].value)
         setQuery(e.target[0].value)
         setFirst(true)
         setShow(false)
     }}>

然后在父组件中:

   <SearchReviews setShow={setShow}/>