Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/javascript/426.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/256.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript 需要帮助使用Gatsby.js实现react-hook表单:form-won';我甚至不能将值发布到控制台_Javascript_Reactjs_React Hook Form - Fatal编程技术网

Javascript 需要帮助使用Gatsby.js实现react-hook表单:form-won';我甚至不能将值发布到控制台

Javascript 需要帮助使用Gatsby.js实现react-hook表单:form-won';我甚至不能将值发布到控制台,javascript,reactjs,react-hook-form,Javascript,Reactjs,React Hook Form,我在Gatsby.js中有一个表单,它为它的输入加载组件——输入文本、文本区域、下拉列表等。这些组件并不完全是哑的,因为它们的类应该在焦点、单击或悬停时改变,所以我有一些函数使其工作 然而,它并没有那么好(我是一个在这里尽力做到最好的前端人员),经过一些研究,我发现react-hook表单不仅可以处理组件背后的逻辑(使用formState.touch和formState.isDirty),还可以为我做验证。听起来像个计划 所以我剥离了它们逻辑中的这些组件,这样它们就更简单了,我正试图在这种形式上

我在Gatsby.js中有一个表单,它为它的输入加载组件——输入文本、文本区域、下拉列表等。这些组件并不完全是哑的,因为它们的类应该在焦点、单击或悬停时改变,所以我有一些函数使其工作

然而,它并没有那么好(我是一个在这里尽力做到最好的前端人员),经过一些研究,我发现react-hook表单不仅可以处理组件背后的逻辑(使用formState.touch和formState.isDirty),还可以为我做验证。听起来像个计划

所以我剥离了它们逻辑中的这些组件,这样它们就更简单了,我正试图在这种形式上使用它。但我甚至不能将字段值发布到控制台,这意味着我走错了方法。我相信我没有正确注册组件,已经尝试了很多方法

我非常感谢任何帮助,让我了解这种方法有什么问题,以及我能做些什么使它起作用。这东西好几天都在折磨我

更新:经过一点研究,我已设法使其部分工作-至少文本输入。我会回答这个问题,这样我可以就剩下的问题再回答一个问题

下面是我现在拥有的组件代码

Input.js

// Input.js - from where <Input> and <TextArea> components come from
import React from "react";

import "../../sass/components/forms/input.sass"

export function Input({ className, label, name, onChange, value, register, required, type }) {
  
  return (
    <div 
      className={`inputContainer ${className}`}>
      <div
        className={`
        inputHeader 
        `}>
        <span className="inputLabel" >{label}</span>
        <input 
          id={name}
          className="field"
          onChange={onChange} 
          value={value}
          ref={register({ required })}
          type={type}/>
      </div>
    </div>
  )
}
  

export function TextArea({ className, label, name, onChange, value, register, required, type }) {

  return (
    <div 
      className={`
      textAreaContainer ${className}
      `}>
      <span className="textAreaLabel">{label}</span>
      <textarea 
        id={name}
        className="field" 
        onChange={onChange} 
        ref={register({ required })}
        type={type} />
    </div>
  )
}
// Dropdown.js - from where <Dropdown> comes. Notice that it's not a <select> tag but a list with containers around. That was the only way I was able to customize it the way we need it.

import React, { useState } from "react";
import "../../sass/components/forms/dropdown.sass"


export function Dropdown(props) {
  const [isOpen, setIsOpen] = useState(false);
  const [selectedOption, setSelectedOption] = useState(null);
    
  const toggling = () => setIsOpen(!isOpen);

  const onOptionClicked = value => () => {
    setSelectedOption(value);
    setIsOpen(false);
  };

  return (
    <div className="dropdownContainer">
      <span>{props.preambulo}</span>
      <div 
        className={`
          dropdownHeader 
          ${isOpen === true ? 'open' : 'closed'} 
          `} 
          onClick={toggling}
          >
        {selectedOption || props.placeholder}
      </div>
      {isOpen && (
        <div 
          className="dropdownListContainer">
            <ul 
              className="dropdownList"
              ref={props.ref}
              name={props.name}
              id={props.name}
              >
              {props.options.map((option, i) => (
                <li 
                  className={`dropdownListItem item-${i}`} 
                  key={i} 
                  onClick={onOptionClicked(option)}>
                  {option}
                </li>
              ))}
              <hr />
            </ul>
        </div>
        )}
    </div>
  );
}
import React from "react";
import { useForm } from "react-hook-form";

//Form Components
import { Dropdown } from "../../components/forms/Dropdown"
import { Input, TextArea } from "../../components/forms/Input"

const ContatoFull = ({ className }) => {
 
  const cargos = [
    "Chefe",
    "Diretor",
    "Gerente",
    "Funcionário",
    "Outros"
  ]

  const estados = [
    "Acre",
    "Alagoas",
    "Amazonas",
    "Amapá",
    "Bahia",
    "Ceará",
    "Distrito Federal",
    "Espírito Santo",
    "Goiás",
    "Maranhão",
    "Minas Gerais",
    "Mato Grosso do Sul",
    "Mato Grosso",
    "Pará",
    "Paraíba",
    "Pernambuco",
    "Piauí",
    "Paraná",
    "Rio de Janeiro",
    "Rio Grande do Norte",
    "Rondônia",
    "Roraima",
    "Rio Grande do Sul",
    "Santa Catarina",
    "Sergipe",
    "São Paulo",
    "Tocantins"
  ]
  const { register, handleSubmit } = useForm();
  const onSubmit = data => console.log(data);

  return (
    <form 
      method="post"
      className={`${className !== 0 ? className : ''}`} 
      onSubmit={handleSubmit(onSubmit)}>

      <Dropdown 
        options={cargos}
        ref={register} 
        className="cargo dropdown" 
        preambulo="Eu sou" 
        placeholder="Tomador(a) de decisão" />

      <Dropdown 
        options={estados}
        ref={register} 
        className="estado dropdown" 
        preambulo="Estou no" 
        placeholder="Acre" />

      <Input 
        register={register}
        required
        className="empresa" 
        label="Nome da minha empresa" 
        type="text " />
        
      
      <Input 
        register={register}
        required
        className="primeiro nome" 
        label="Nome" 
        type="text" />
      <Input 
        register={register}
        required
        className="segundo nome" 
        label="Sobrenome" 
        type="text" />
      <Input 
        register={register({
          required: true, 
          pattern: /^\S+@\S+$/i
        })}
        required
        className="email" 
        label="E-mail de contato" 
        type="email" 
        />
        
      <Input
        register={register({
          required: true, minLength: 6, maxLength: 12
        })}
        required
        className="telefone" 
        label="Telefone de contato" 
        type="tel" />

      <TextArea
        register={register}
        required
        className="mensagem" 
        label="Escreva sua mensagem"/>

      <button 
        type="submit" 
        className="simpleButton primary submit button">Enviar</button>
    </form>
  )
}

export default ContatoFull
//Input.js-来自何处和组件
从“React”导入React;
导入“../../sass/components/forms/input.sass”
导出函数输入({className,label,name,onChange,value,register,required,type}){
返回(
{label}
)
}
导出函数TextArea({className,label,name,onChange,value,register,required,type}){
返回(
{label}
)
}
Dropdown.js

// Input.js - from where <Input> and <TextArea> components come from
import React from "react";

import "../../sass/components/forms/input.sass"

export function Input({ className, label, name, onChange, value, register, required, type }) {
  
  return (
    <div 
      className={`inputContainer ${className}`}>
      <div
        className={`
        inputHeader 
        `}>
        <span className="inputLabel" >{label}</span>
        <input 
          id={name}
          className="field"
          onChange={onChange} 
          value={value}
          ref={register({ required })}
          type={type}/>
      </div>
    </div>
  )
}
  

export function TextArea({ className, label, name, onChange, value, register, required, type }) {

  return (
    <div 
      className={`
      textAreaContainer ${className}
      `}>
      <span className="textAreaLabel">{label}</span>
      <textarea 
        id={name}
        className="field" 
        onChange={onChange} 
        ref={register({ required })}
        type={type} />
    </div>
  )
}
// Dropdown.js - from where <Dropdown> comes. Notice that it's not a <select> tag but a list with containers around. That was the only way I was able to customize it the way we need it.

import React, { useState } from "react";
import "../../sass/components/forms/dropdown.sass"


export function Dropdown(props) {
  const [isOpen, setIsOpen] = useState(false);
  const [selectedOption, setSelectedOption] = useState(null);
    
  const toggling = () => setIsOpen(!isOpen);

  const onOptionClicked = value => () => {
    setSelectedOption(value);
    setIsOpen(false);
  };

  return (
    <div className="dropdownContainer">
      <span>{props.preambulo}</span>
      <div 
        className={`
          dropdownHeader 
          ${isOpen === true ? 'open' : 'closed'} 
          `} 
          onClick={toggling}
          >
        {selectedOption || props.placeholder}
      </div>
      {isOpen && (
        <div 
          className="dropdownListContainer">
            <ul 
              className="dropdownList"
              ref={props.ref}
              name={props.name}
              id={props.name}
              >
              {props.options.map((option, i) => (
                <li 
                  className={`dropdownListItem item-${i}`} 
                  key={i} 
                  onClick={onOptionClicked(option)}>
                  {option}
                </li>
              ))}
              <hr />
            </ul>
        </div>
        )}
    </div>
  );
}
import React from "react";
import { useForm } from "react-hook-form";

//Form Components
import { Dropdown } from "../../components/forms/Dropdown"
import { Input, TextArea } from "../../components/forms/Input"

const ContatoFull = ({ className }) => {
 
  const cargos = [
    "Chefe",
    "Diretor",
    "Gerente",
    "Funcionário",
    "Outros"
  ]

  const estados = [
    "Acre",
    "Alagoas",
    "Amazonas",
    "Amapá",
    "Bahia",
    "Ceará",
    "Distrito Federal",
    "Espírito Santo",
    "Goiás",
    "Maranhão",
    "Minas Gerais",
    "Mato Grosso do Sul",
    "Mato Grosso",
    "Pará",
    "Paraíba",
    "Pernambuco",
    "Piauí",
    "Paraná",
    "Rio de Janeiro",
    "Rio Grande do Norte",
    "Rondônia",
    "Roraima",
    "Rio Grande do Sul",
    "Santa Catarina",
    "Sergipe",
    "São Paulo",
    "Tocantins"
  ]
  const { register, handleSubmit } = useForm();
  const onSubmit = data => console.log(data);

  return (
    <form 
      method="post"
      className={`${className !== 0 ? className : ''}`} 
      onSubmit={handleSubmit(onSubmit)}>

      <Dropdown 
        options={cargos}
        ref={register} 
        className="cargo dropdown" 
        preambulo="Eu sou" 
        placeholder="Tomador(a) de decisão" />

      <Dropdown 
        options={estados}
        ref={register} 
        className="estado dropdown" 
        preambulo="Estou no" 
        placeholder="Acre" />

      <Input 
        register={register}
        required
        className="empresa" 
        label="Nome da minha empresa" 
        type="text " />
        
      
      <Input 
        register={register}
        required
        className="primeiro nome" 
        label="Nome" 
        type="text" />
      <Input 
        register={register}
        required
        className="segundo nome" 
        label="Sobrenome" 
        type="text" />
      <Input 
        register={register({
          required: true, 
          pattern: /^\S+@\S+$/i
        })}
        required
        className="email" 
        label="E-mail de contato" 
        type="email" 
        />
        
      <Input
        register={register({
          required: true, minLength: 6, maxLength: 12
        })}
        required
        className="telefone" 
        label="Telefone de contato" 
        type="tel" />

      <TextArea
        register={register}
        required
        className="mensagem" 
        label="Escreva sua mensagem"/>

      <button 
        type="submit" 
        className="simpleButton primary submit button">Enviar</button>
    </form>
  )
}

export default ContatoFull
//Dropdown.js-来自何处。请注意,它不是一个标记,而是一个包含容器的列表。这是我能够按照我们需要的方式定制它的唯一方法。
从“React”导入React,{useState};
导入“../../sass/components/forms/dropdown.sass”
导出功能下拉列表(道具){
常量[isOpen,setIsOpen]=useState(false);
const[selectedOption,setSelectedOption]=useState(null);
常量切换=()=>setIsOpen(!isOpen);
const onOptionClicked=value=>()=>{
设置选择选项(值);
setIsOpen(假);
};
返回(
{序言部分}
{selectedOption | | props.placeholder}
{isOpen&&(
    {props.options.map((option,i)=>(
  • {option}
  • ))}
)} ); }
然后是表格

contatoFull.js

// Input.js - from where <Input> and <TextArea> components come from
import React from "react";

import "../../sass/components/forms/input.sass"

export function Input({ className, label, name, onChange, value, register, required, type }) {
  
  return (
    <div 
      className={`inputContainer ${className}`}>
      <div
        className={`
        inputHeader 
        `}>
        <span className="inputLabel" >{label}</span>
        <input 
          id={name}
          className="field"
          onChange={onChange} 
          value={value}
          ref={register({ required })}
          type={type}/>
      </div>
    </div>
  )
}
  

export function TextArea({ className, label, name, onChange, value, register, required, type }) {

  return (
    <div 
      className={`
      textAreaContainer ${className}
      `}>
      <span className="textAreaLabel">{label}</span>
      <textarea 
        id={name}
        className="field" 
        onChange={onChange} 
        ref={register({ required })}
        type={type} />
    </div>
  )
}
// Dropdown.js - from where <Dropdown> comes. Notice that it's not a <select> tag but a list with containers around. That was the only way I was able to customize it the way we need it.

import React, { useState } from "react";
import "../../sass/components/forms/dropdown.sass"


export function Dropdown(props) {
  const [isOpen, setIsOpen] = useState(false);
  const [selectedOption, setSelectedOption] = useState(null);
    
  const toggling = () => setIsOpen(!isOpen);

  const onOptionClicked = value => () => {
    setSelectedOption(value);
    setIsOpen(false);
  };

  return (
    <div className="dropdownContainer">
      <span>{props.preambulo}</span>
      <div 
        className={`
          dropdownHeader 
          ${isOpen === true ? 'open' : 'closed'} 
          `} 
          onClick={toggling}
          >
        {selectedOption || props.placeholder}
      </div>
      {isOpen && (
        <div 
          className="dropdownListContainer">
            <ul 
              className="dropdownList"
              ref={props.ref}
              name={props.name}
              id={props.name}
              >
              {props.options.map((option, i) => (
                <li 
                  className={`dropdownListItem item-${i}`} 
                  key={i} 
                  onClick={onOptionClicked(option)}>
                  {option}
                </li>
              ))}
              <hr />
            </ul>
        </div>
        )}
    </div>
  );
}
import React from "react";
import { useForm } from "react-hook-form";

//Form Components
import { Dropdown } from "../../components/forms/Dropdown"
import { Input, TextArea } from "../../components/forms/Input"

const ContatoFull = ({ className }) => {
 
  const cargos = [
    "Chefe",
    "Diretor",
    "Gerente",
    "Funcionário",
    "Outros"
  ]

  const estados = [
    "Acre",
    "Alagoas",
    "Amazonas",
    "Amapá",
    "Bahia",
    "Ceará",
    "Distrito Federal",
    "Espírito Santo",
    "Goiás",
    "Maranhão",
    "Minas Gerais",
    "Mato Grosso do Sul",
    "Mato Grosso",
    "Pará",
    "Paraíba",
    "Pernambuco",
    "Piauí",
    "Paraná",
    "Rio de Janeiro",
    "Rio Grande do Norte",
    "Rondônia",
    "Roraima",
    "Rio Grande do Sul",
    "Santa Catarina",
    "Sergipe",
    "São Paulo",
    "Tocantins"
  ]
  const { register, handleSubmit } = useForm();
  const onSubmit = data => console.log(data);

  return (
    <form 
      method="post"
      className={`${className !== 0 ? className : ''}`} 
      onSubmit={handleSubmit(onSubmit)}>

      <Dropdown 
        options={cargos}
        ref={register} 
        className="cargo dropdown" 
        preambulo="Eu sou" 
        placeholder="Tomador(a) de decisão" />

      <Dropdown 
        options={estados}
        ref={register} 
        className="estado dropdown" 
        preambulo="Estou no" 
        placeholder="Acre" />

      <Input 
        register={register}
        required
        className="empresa" 
        label="Nome da minha empresa" 
        type="text " />
        
      
      <Input 
        register={register}
        required
        className="primeiro nome" 
        label="Nome" 
        type="text" />
      <Input 
        register={register}
        required
        className="segundo nome" 
        label="Sobrenome" 
        type="text" />
      <Input 
        register={register({
          required: true, 
          pattern: /^\S+@\S+$/i
        })}
        required
        className="email" 
        label="E-mail de contato" 
        type="email" 
        />
        
      <Input
        register={register({
          required: true, minLength: 6, maxLength: 12
        })}
        required
        className="telefone" 
        label="Telefone de contato" 
        type="tel" />

      <TextArea
        register={register}
        required
        className="mensagem" 
        label="Escreva sua mensagem"/>

      <button 
        type="submit" 
        className="simpleButton primary submit button">Enviar</button>
    </form>
  )
}

export default ContatoFull
从“React”导入React;
从“react hook form”导入{useForm};
//表单组件
从“./../components/forms/Dropdown”导入{Dropdown}
从“./../components/forms/Input”导入{Input,TextArea}
常量ContatoFull=({className})=>{
常量货物=[
“切夫”,
“导演”,
“格伦特”,
“Funcionário”,
“奥特罗斯”
]
常数estados=[
“英亩”,
“阿拉戈斯”,
“亚马逊”,
“阿马帕”,
“巴伊亚”,
“塞阿拉”,
“联邦行政区”,
“Espírito Santo”,
“戈亚斯”,
“马兰霍”,
“米纳斯吉拉斯”,
“南马托格罗索州”,
“马托格罗索”,
“帕拉”,
“Paraíba”,
“伯南布哥”,
“票”,
“巴拉那”,
“里约热内卢”,
“北里奥格兰德”,
“隆多尼亚”,
“Roraima”,
“南里奥格兰德”,
“圣卡塔琳娜”,
“塞尔吉佩”,
“圣保罗”,
“托坎廷斯”
]
常量{register,handleSubmit}=useForm();
const onSubmit=data=>console.log(数据);
返回(
羡慕
)
}
导出默认连续

本问题中的代码问题是这些字段的注册,
。我使用的方式,将道具
寄存器
传递给组件,是错误的

使用
在完成一些工作后,使字段的注册工作正常进行。以下是我所做的:

import { useForm, Controler } from 'react-hook-form' 

const ContatoForm = () => {

  (...)

  const { handleSubmit, control } = useForm();
  const onSubmit = data => console.log(data);

  return (
    <form 
      method="post"
      onSubmit={handleSubmit(onSubmit)}>
      <Controller
        control={control}
        name="firstName"
        render={props =>
          <Input
            name="firstName"
            type="text"
            label="label here"
            value={value}
            onChange={e => onChange(e.target.value)}
        }
      />
    </form>
  )
}
但是,例如,对必填字段应用验证会将错误置于此结构之外。大概是这样的:

      <Controller
        control={control}
        name="firstName"
        render={props =>
          <Input
            name="firstName"
            type="text"
            label="label here"
            value={value}
            onChange={e => onChange(e.target.value)}
        }
      />
      {errors.firstName && <span>Field is required</span>}


onChange(e.target.value)}
}
/>
{errors.firstName&&字段是必需的}
这没什么错,但对于设计选择,我已经将容器从组件转移到父组件,这样它就会包含显示的错误

// New input component
export function Input({ label, name, onChange, value, type }) {
  
  return (
    <div
      className={`
      inputHeader 
      `}>
      <span className="inputLabel" >{label}</span>
      <input 
        id={name}
        className="field"
        onChange={onChange} 
        value={value}
        type={type}/>
    </div>
  )
}
//新的输入组件
导出函数输入({label,name,onChange,value,type}){
返回(
{label}
)
}
//新父级
(...)
const{handleSubmit,control,errors}=useForm();
const onSubmit=data=>console.log(数据);
返回(
onChange(e.target.value)}
value={value}
label={label}
name={name}
类型={type}/>
}
/>
{errors.firstName&&字段是必需的。}
)
这样,我可以在提交时通过适当的验证获取输入值