首页 > 解决方案 > 我正在尝试从最低级别组件的输入字段中捕获数据

问题描述

我的状态位于我的 APP 级别组件中,并且我正在尝试捕获放入我的表单组件中的数据。我正在使用钩子,但我无法弄清楚我做错了什么!

我尝试将状态置于表单级别,但它返回未定义,我的最终目标是将此数据发送到 firebase,并将其显示在我的应用程序另一个页面上的表格中。

应用程序

import React, { useState, createRef } from "react";
import { render } from "react-dom";

import Header from "./components/Header";
import About from "./components/About";

const App = () => {
  const [date, setDate] = useState("");
  const [name, setName] = useState("");
  const [hours, setHours] = useState("");
  const [description, setDescription] = useState("");

  return (
    <div>
      <Header />
    </div>
  );
};

render(<App />, document.getElementById("root"));

**头/路由器组件

import React from "react";
import { render } from "react-dom";
import {
  BrowserRouter as Router,
  Switch,
  Route,
  NavLink,
  Link
} from "react-router-dom";

import Home from "./pages/home/Home";
import Data from "./pages/data/Data";
import About from "./pages/about/About";
import Contact from "./pages/contact/Contact";


import "../style.css";

const Header = () => {
  return (
    <Router>
      <div>
        <nav className="navbar">
          <NavLink className="link nav-item" to="/entry">
            Time Entry
          </NavLink>
          <NavLink className="link nav-item" to="/data">
            Data
          </NavLink>
          <NavLink className="link nav-item-right" to="/about">
            About
          </NavLink>
          <NavLink className="link nav-item-right" to="/contact">
            Contact
          </NavLink>
        </nav>

        {/* A <Switch> looks through its children <Route>s and
            renders the first one that matches the current URL. */}
        <Switch>
          <Route exact path="/entry" component={Home} />
          <Route exact path="/data" component={Data} />
          <Route exact path="/about" component={About} />
          <Route exact path="/contact" component={Contact} />
        </Switch>
      </div>
    </Router>
  );
};

export default Header;

主页组件

import React, { Fragment } from "react";

import InputForm from "./Form";

const Home = props => {
  return (
    <Fragment>
      <InputForm />
    </Fragment>
  );
};

export default Home;

表单组件

import React, { Fragment, useState, createRef } from "react";
import { Button, Form, FormGroup, Label, Input, FormText } from "reactstrap";

const InputForm = props => {


  const dateEntry = createRef();
  const nameEntry = createRef();
  const hourEntry = createRef();
  const descriptionEntry = createRef();

  const handleClick = e => {
    e.preventDefault();
    setDate(dateEntry.current.value);
    setName(nameEntry.current.value);
    setHours(hourEntry.current.value);
    setDescription(descriptionEntry.current.value);
    // console.log(nameEntry.current.value);
  };

  return (
    <Form className="data-entry">
      <FormGroup className="form-entry-items">
        <Label className="label">Date</Label>
        <Input type="date" className="input" ref={dateEntry} />
      </FormGroup>
      <FormGroup className="form-entry-items">
        <Label className="label">Lease Acconting Manager Name</Label>{" "}
        <Input type="text" className="input" ref={nameEntry} />
      </FormGroup>
      <FormGroup className="form-entry-items">
        <Label className="label">Hours Worked</Label>{" "}
        <Input className="input" ref={hourEntry}/>
      </FormGroup>
      <FormGroup className="form-entry-items">
        <Label className="label">Description</Label>{" "}
        <Input type="textarea" className="input" ref={descriptionEntry}/>
      </FormGroup>
      <Button onClick={handleClick}>Submit</Button>
    </Form>
  );
};

export default InputForm;

标签: javascriptreactjsstatereact-propsreactstrap

解决方案


首先,您应该质疑为什么要使用仅由InputForm使用的值来设置APP的状态。如果您只是打算在InputForm中使用它们,您应该将您的状态移动到该组件。

也许只需在InputFormstate内部设置而不是iof使用,这样您就可以在那里处理它们而无需进行钻孔或其他操作。createRef

import React, { Fragment, useState, createRef } from "react";
import { Button, Form, FormGroup, Label, Input, FormText } from "reactstrap";

const InputForm = props => {

  const [date, setDate] = useState("");
  const [name, setName] = useState("");
  const [hours, setHours] = useState("");
  const [description, setDescription] = useState("");

  /* Im not sure How this works inside your component Input, but why dont just use a onChange?*/
  const dateEntry = createRef();
  const nameEntry = createRef();
  const hourEntry = createRef();
  const descriptionEntry = createRef();

  const handleInput = ( e, type)  => {
    switch( type ){
     case'name':
       setName( e.target.value );
     break;
     case'date':
       setDate( e.target.value );
     break;
    case'description':
       setDescription( e.target.value );
     break;
     case'hours':
       setHours( e.target.value );
     break;
    }
  }

  const handleClick = e => {
    e.preventDefault();
    //Just submit your data or something...  
  };

  return (
    <Form className="data-entry">
      <FormGroup className="form-entry-items">
        <Label className="label">Date</Label>
        <Input type="date" className="input" ref={dateEntry} onChange={ e => {handleChange( e, 'date') } } />
      </FormGroup>
      <FormGroup className="form-entry-items">
        <Label className="label">Lease Acconting Manager Name</Label>{" "}
        <Input type="text" className="input" ref={nameEntry} onChange={ e => {handleChange( e, 'name' ) } } />
      </FormGroup>
      <FormGroup className="form-entry-items">
        <Label className="label">Hours Worked</Label>{" "}
        <Input className="input" ref={hourEntry} onChange={ e => {handleChange( e, 'hours') } }/>
      </FormGroup>
      <FormGroup className="form-entry-items">
        <Label className="label">Description</Label>{" "}
        <Input type="textarea" className="input" ref={descriptionEntry} onChange={ e => {handleChange( e, 'description') } }/>
      </FormGroup>
      <Button onClick={handleClick}>Submit</Button>
    </Form>
  );
};

export default InputForm;

如果您需要访问来自任何其他组件的值,请尝试使用上下文Form实现相同的功能,并可能尝试为它们添加一些操作减速器

如果您需要更多信息,请查看: Context DocsReducer Docs


推荐阅读