Pesquisa de site

Manipulação de mudança de input REACTJS + bug do TypeScript


export default class triangleArea extends React.Component<triangleInfo> {
    constructor(props:triangleInfo) {
        super(props);

        //initializing variables to undefined
        this.handleChange = this.handleChange.bind(this);

  this.state = {
      base: 0,
      height: 0,
      area: undefined,
      error: ""
    };
  }

  //Handling change of input Base and HEIGHT

  handleChange = (event: React.ChangeEvent<HTMLInputElement>)=> 
  {
       this.setState({
       name : event.target.value
  });
  }//getArea function to calculate Area

  getArea = async (triangleInfo) => {
      triangleInfo.preventDefault();

      const base = triangleInfo.target.elements.base.value;
      const height = triangleInfo.target.elements.height.value;

      if(base > 0 && height > 0)
      {
          this.setState ({
             base: triangleInfo.target.elements.base.value,
             height : triangleInfo.target.elements.height.value,
             area: (base*height)/2
          })
      }
      else
      {
          this.setState ({
              base: undefined,
              height: undefined,
              area: undefined,
              error: "Please enter the values correctly."
          })
      }
  }

render() {
    return (
       //...
      <div>
        <form>
           <p>Calculate the base of a triangle!</p>
           <input type="text" id="base" placeholder = "base" value={this.state.base} onChange={this.handleChange}></input>
           <input type="text" id="height" placeholder = "height" value={this.state.height} onChange={this.handleChange}></input>
           <button type="submit">Get Area</button>
        </form>
     </div>
    //...
  );
}
};

Atualmente estou preso aqui, recebendo esta mensagem de erro:

A propriedade 'height' não existe no tipo 'Readonly<{}>'.ts(2339)

O mesmo com a entrada base. Alguma ajuda?

Resposta #1

  1. Onde você chama getArea?

  2. Já que você quer reutilizar a lógica do método handleChange (o que é bom), você quer parametrizar o handleChange corretamente adicionando um argumento que informe a qual controle ele está ligado, assim:

/* Where the first param could be "base" or "height" */
handleChange = (field: "base" | "height", value) => {
  this.setState({
    [field]: value
  });
  ...

/* and call it in input "onChange" like so: */
 onChange={(e) => this.handleChange("base", e.target.value)}

 // ... do the same for "height" field

  1. No seu código, triangleInfo deve ser apenas o "type" (em TypeScript), então você não deve acessar propriedades dele como se fossem valores que vêm de variáveis de estado. Acho que a definição é algo assim:
type triangleInfo = {
  base: number;
  height: number;
  area: number;
};

/* usage
const t: triangleInfo = { base: 5, height: 6, area: 15 };
*/

  1. Finalmente, no seu método getArea, eu acho que você quer que isso seja chamado ao enviar o formulário: <form onSubmit={this.getArea}>, também provavelmente você quer usar os valores atuais do "estado" para calcular a area do "estado" em vez disso:
// remember that you set state "base" and "height" from your handleChange method.
const { base, height } = this.state;

if(base > 0 && height > 0) {
  this.setState ({
    // you probably only want to calculate area, so you can leave base and height as it is.
    area: (base*height)/2
  })
}
...

P.S: No seu caso de uso, você não precisa usar props, e "triangleInfo" pode ser usado no seu "state" em vez disso.