簡體   English   中英

React 將子對象發送到父數組並提交表單

[英]React send child object into parent array and submit form

新手問題:構建購物車,我有一個模態表單。
提交按鈕是模態按鈕(在表單標簽之外),但似乎將表單發送到 handleOnSubmit 處理程序。 但是,除了關閉模式之外,我無法更新 productBought 和 productName 狀態值。
理想情況下,我想將籃子 [] 內容(來自 InputList 類)推送到父級 (AsyncAwaitLocalhost) 中的一個新數組,之后我可以將整個購買提交給 API。
refs 已被棄用,其他各種共享數據的方式讓我失望。 我的挑戰是:
(i) 如何將推籃對象共享給等待的父狀態對象? 和 (ii) 在控制台記錄表單對象后如何提交表單?
謝謝。

AsyncAwaitLocalhost.jsx

import React from 'react'
import "./App.css"
import { Modal, Button } from "react-bootstrap"
import Form from "./Form.jsx"

class AsyncAwaitLocalhost extends React.Component {

    constructor(props) {
        super(props);
        this.state = {
            sharedVar: "init",
            jsonContent: [],
            isOpen: null,
            productBought: 0,
            productName: "anItem"

        }
        this.handleOnSubmit = this.handleOnSubmit.bind(this)
    }

    updateShared(shared_value) {
        this.setState({ sharedVar: shared_value });
    }

    async componentDidMount() {
        // GET request using fetch with async/await
        const response = await fetch('http://localhost:8080/cakes');
        const data = await response.json();
        this.setState({ jsonContent: data.cakes, greeting: this.state.greeting, newGreeting: this.state.newGreeting })
    }

    openModal = (index) => () => this.setState({ isOpen: index });

    closeModal = () => this.setState({ isOpen: null });

    handleCloseModal() {
        this.setState({ isOpen: null });
    }

    handleOnSubmit(event) {
        event.preventDefault()
        this.setState({ productBought: event.target.name.value })
        this.setState({ productName: event.target.name.value })
        console.log("Inside handleOnSubmit: " + this.state.productBought)
        this.handleCloseModal();
    }

    render() {

        const { jsonContent } = this.state;
        const { sharedVar } = this.state;
        const { productBought } = this.state;
        const { productName } = this.state;
        console.log("shared var in parent: " + sharedVar)
        console.log("productBought in parent: " + productBought)

        const Cake = ({ name, id, text, image, comment, price, dbutton, dmodal }) => (
            <div className="rounded-well">
                <div>
                    <img src={image} width="120px" alt={name} />
                </div>
                <div>
                    <p>{name}</p>
                    <p>{text}</p>
                    <p>{comment}</p>
                    <p>{id}</p>
                    <p>{price}</p>
                    <div> {this.state.sharedVar}</div>
                    <div>{dbutton}</div>
                    <div id="dModal" className="dModalClosed">{dmodal}</div>
                </div>
            </div>
        );

        return (
            <div className="card text-center m-3">
                Showing HTTP Requests, CSS , Data Transfer &amp; Modals
                <h5 className="card-header">See Cakes</h5>
                <div className="card-body">
                    <div>
                        {this.state.jsonContent.map((cake, index) => (
                            <Cake
                                image={cake.image}
                                text={cake.text}
                                key={index}
                                price={"£" + cake.price + ".00"}
                                dbutton={<Button onClick={this.openModal(index)}>See more</Button>}
                                dmodal={
                                    <Modal id={cake.name} show={this.state.isOpen === index}
                                        onHide={this.closeModal} className="image-container">
                                        <Modal.Header closeButton>
                                            <Modal.Title>{cake.text}</Modal.Title>
                                        </Modal.Header>
                                        <Modal.Body>
                                            <div>
                                                <img src={cake.image} width="300px" alt={cake.name} />
                                            </div>
                                            <br />
                                            <p>{cake.text}</p>
                                            <p>{cake.comment}</p>
                                            <div>
                                                <form id={cake.name} method="POST" action="#" onSubmit={this.handleOnSubmit} >
                                                    {<Form dataFromParent={this.state.jsonContent[index]} onChange />}
                                                </form>
                                            </div>
                                        </Modal.Body>
                                        <Modal.Footer>
                                            <Button variant="primary" onClick={this.closeModal}>
                                                Cancel
                                            </Button>
                                            <Button form={cake.name} type="submit" variant="secondary" onClick={this.handleOnSubmit}>
                                                Add to basket
                                            </Button>
                                        </Modal.Footer>
                                    </Modal>
                                }
                            />
                        ))}
                        <div>
                        </div>
                    </div>
                </div>
            </div>
        );
    }
}

export { AsyncAwaitLocalhost };

Form.jsx

import React from 'react';
class InputList extends React.Component {

  constructor(props) {
    super(props)
    this.state = {     
      bought: 0,
      sharedVar: "input field",
      cakeItems:{},
      basket: [],
      input: 0,
      item: ""
    }
  }

    handleChange(index, e) {
      const value = e.target.value
      this.props.onChange(index, {...this.props.data[index], buy: value})
      this.state.bought = value
      this.state.cakeItems = {item: this.props.data[0].name, number: this.state.bought}
      this.state.basket.push(this.state.cakeItems)
    }
    
    render() { 

      const { bought } = this.state;
      const {cakeItems}  = this.state;
      const {basket}  = this.state;
      const { sharedVar } = this.state;
      const { item } = this.state;
      // this.state.sharedVar = this.props.dataFromParent[0].name
      console.log("pre-bought: " + bought);
      console.log("Shared var in input class: " + sharedVar);
      console.log("basket in InputClass: " + JSON.stringify(basket))
      return (
        <div>
          

            Buy: &nbsp;
            {this.props.data.map((d, i) => <input key="0" value={d.buy} name="productBought" onChange={this.handleChange.bind(this, i)} />)}
            {this.props.data.map((d, i) => <input key="1" type="hidden" value={d.name} name="productName" />)}
            
            <>
              &nbsp; To buy: {bought}
            </>
            
        
        </div>
        
      )
    }
  }
  
  class Form extends React.Component {
    constructor(props) {
      super(props)
      this.state = {
        data: [],
        basket: [],
        sharedVar: "form field",
        usrBasket: {
          buy: 1,
          id: "randomStr",
          items: [{buy: 1, item: ""}],
          value_key: "",
          nuArry: []
        },
        input: {}
      }
    }

    loadStuff() {
      this.setState({
        data: [this.props.dataFromParent]
      })
        // console.log('got some stuff from the server in Form: ' + JSON.stringify(this.props.dataFromParent))
    }
    
    handleChange(index, value) {
      console.log('data changed!', value)
      const data = [...this.state.data]
      data.splice(index, 1, value)
      this.setState({
        data, 
      })
      
      this.state.basket = this.state.cakeItems
      console.log("basket in FormClass: " + JSON.stringify(this.state.basket))
    }
    componentDidMount() {
      this.loadStuff()
    }
    render() {

      const {basket}  = this.state;
      const { value_key } = this.state;
      this.state.value_key = "new vk";
      console.log("value_key in Form: " + value_key);

      const { sharedVar } = this.state;
      this.state.sharedVar = "Hello greeting";
      console.log("sharedVar in Form: " + sharedVar); 
      
      return (
        <div>
              <InputList data={this.state.data} onChange={this.handleChange.bind(this)} />
        </div>
      );
    
    }
  }

export default Form```

<br>

哈,新手生活……!

因此,經過更多研究並更好地學習整個框架后,解決方案就是這樣。

(i) 如何將推籃對象共享給等待的父狀態對象?

  • 創建不同的類——(有些人主張功能組件),它們可以很好地完成一件事。 Form 組件呈現模態,收集表單值並通過 props 將這些值提交給父級。

在Parent中,准備接收子道具

<Cakes onSubmitChild={this.getFormValues} />

然后將值從 Child 發送到父組件,如下所示:

this.props.onSubmitChild(this.state.productField)

(ii) 如何在控制台記錄表單對象后提交表單? 父級有提交到服務器按鈕。 在 Child 將表單值提交給 Parent 之后,剩下的工作是創建一個 JSON 對象並使用 AJAX(或任何編碼人員喜歡的方式)將其提交給服務器。 請注意,服務器端會出現 CORS 問題以解決此問題,但我建議使用 npm 中的cors 庫

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM