簡體   English   中英

在 React 中,為什么輸入框在輸入字符后會失去焦點?

[英]In React , why does the input field lose focus after typing a character?

我正在對組件使用 React Mui,在 chrome 檢查器或終端中沒有出現任何錯誤,我該如何解決這個問題

我從 eslint 和 Chrome Inspector 都沒有收到任何錯誤。

提交表單本身的工作方式與實際輸入字段一樣,當它位於渲染的返回中或作為單獨的組件導入時,但不是我在下面對其進行編碼的方式。

為什么會這樣? 這是我的代碼:

import React, { useState } from "react";
import {
  Box,
  Container,
  Stack,
  TextField,
  Typography,
  Button,
  Divider,
} from "@mui/material";
import { styled } from "@mui/material/styles";
import { Link, useNavigate } from "react-router-dom";
const Register = () => {
  const Curve = styled("div")(({ theme }) => ({
    height: "35vh",
    position: "absolute",
    top: 0,
    left: 0,
    width: "100%",
    background: `linear-gradient(120deg,${theme.palette.secondary.light},${theme.palette.secondary.main})`,
    zIndex: -1,
    borderBottomLeftRadius: "30px",
    borderBottomRightRadius: "30px",
  }));
  const ProfileBox = styled(Box)(({ theme }) => ({
    // margin: theme.spacing(18, 1),
    background: theme.palette.primary.dark,
    border: `solid 0.8px ${theme.palette.primary.light}`,
    borderRadius: "10px",
    padding: theme.spacing(3),
  }));
  const navigate = useNavigate();
  const handleRegister = (e) => {
    e.preventDefault();
    navigate("/");
  };

  const [values, setValues] = useState({
    name: "",
    email: "",
    password: "",
    conpassword: "",
    phone: "",
    proffesion: "",
  });
  const [err, setErr] = useState({});
  const [valid, setValid] = useState(false);

  const handleChange = (e) => {
    const { id, value } = e.target;
    setValues(() => ({
      [id]: value,
    }));
    setValid(() => true);
  };

  const validate = () => {
    return setErr(checkErr());
    function checkErr() {
      const error = {};
      if (values.name.length === 0) error.name = "Name nedded";
      if (values.password.length === 0) error.password = "Password nedded";
      if (!values.email.match(/^[^\s@]+@[^\s@]+\.[^\s@]+$/))
        error.email = "Invalid email";
      if (values.password.length < 6)
        error.password = "Password must be longer than 6 charectors";
      if (values.password !== values.conpassword)
        error.conpassword = "Password doesn't match";
      if (values.email.length === 0) error.email = "Email nedded";
      if (values.phone.length === 0) error.phone = "Phone number nedded";
      if (values.phone.length < 10) error.phone = "Invalid number";
      if (values.proffesion.length === 0)
        error.proffesion = "Proffesion nedded ex: lawyer ,student";
      return error;
    }
  };

  return (
    <Container maxWidth="sm">
      <Curve></Curve>
      <Box
        sx={{
          display: "flex",
          flexDirection: "column",
          justifyContent: "center",
          height: "30vh",
          alignItems: "center",
        }}
      >
        <Typography variant="h6" algin="center">
          Register
        </Typography>
        <Typography variant="caption" algin="center">
          your data is secured with us
        </Typography>
      </Box>
      <ProfileBox>
        <Stack spacing={2}>
          <TextField
            variant="standard"
            label="Name"
            color="secondary"
            value={values.name}
            onChange={handleChange}
            onBlur={validate}
            id="name"
            error={err.name}
            helperText={err.name}
          />
          <TextField
            type="email"
            variant="standard"
            label="Email"
            color="secondary"
            id="email"
            value={values.email}
            onChange={handleChange}
            onBlur={validate}
            error={err.email}
            helperText={err.email}
          />
          <TextField
            type="password"
            variant="standard"
            label="Password"
            color="secondary"
            value={values.password}
            onChange={handleChange}
            onBlur={validate}
            id="password"
            error={err.password}
            helperText={err.password}
          />
          <TextField
            type="password"
            variant="standard"
            label="Conform password"
            color="secondary"
            value={values.conpassword}
            onChange={handleChange}
            onBlur={validate}
            id="conpassword"
            error={err.conpassword}
            helperText={err.conpassword}
          />
          <TextField
            type="tel"
            variant="standard"
            label="Phone"
            color="secondary"
            value={values.phone}
            onChange={handleChange}
            onBlur={validate}
            id="phone"
            error={err.phone}
            helperText={err.phone}
          />
          <TextField
            variant="standard"
            label="Proffestion"
            color="secondary"
            value={values.proffesion}
            onChange={handleChange}
            onBlur={validate}
            id="proffesion"
            error={err.proffesion}
            helperText={err.proffesion}
          />
          <Button
            variant="contained"
            color="secondary"
            sx={{
              color: "primary.main",
            }}
            onClick={handleRegister}
          >
            Signup
          </Button>
          <Divider />
          <Typography variant="caption" algin="center">
            Allready have account{" "}
            <span>
              <Link to="/login" style={{ color: "var(--secondary)" }}>
                Login
              </Link>
            </span>
          </Typography>
        </Stack>
      </ProfileBox>
    </Container>
  );
};

export default Register;

嘗試像這樣更改您的handleChange函數:

const handleChange = (e) => {
    const { id, value } = e.target;
    setValues(() => (prevState => {
      return {
        ...prevState,
        [id]: value,
      }
    }));
    setValid(true);
  };

發生這種情況是因為您正在Register組件內創建組件。 這種模式對性能非常不利,並且容易出現與您的問題完全一樣的錯誤。

在您更改Register組件狀態的每種類型上,它都會重新呈現自身,並從頭開始重新創建CurveProfileBox ,包括它們的子項(輸入字段)。 這導致他們重置所有他們和他們孩子的狀態,包括焦點。

您需要將CurveProfileBox移出它,它將解決問題。

const Curve = styled('div')(({ theme }) => ({
  ... // the same
}));

const ProfileBox = styled(Box)(({ theme }) => ({
 ... // the same
}));

const Register = () => {

暫無
暫無

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

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