如何使用reactjs正确显示用户正在键入

时间:2019-02-17 11:57:16

标签: reactjs

下面的代码显示用户在某人开始在表单输入中输入内容时正在输入内容。

以下是现在要完成的工作:

请如何添加5秒之类的超时时间,以便应用程序仅在5秒内显示用户键入警报  每当用户开始输入表单输入时(就像在聊天输入通知中一样)。

我想这与下面的代码这样的超时功能有关

setTimeout(()=>{
  this.sate.data
},5000);

有人可以帮我吗,或者有更好的方法吗?

这是到目前为止的代码

class App extends React.Component {
  constructor(props) {
    super(props)
    this.state = { data: [], email: '' };
    this.handleChange1 = this.handleChange1.bind(this);
    this.onKeyPressed = this.onKeyPressed.bind(this);
  }

  handleChange1(event) {
    this.setState({ [event.target.name]: event.target.value });
  }

  onKeyPressed(event) {
    console.log(event.key);
    this.setState({
      data: [{ id: '1', name: 'Tony' }]
    });
  }

  render() {
    return (
      <div>
        <h1>Display User is Typing.....</h1>
        <label>
          <input
            onKeyDown={event => this.onKeyPressed(event)}
            value={this.state.email}
            onChange={this.handleChange1}
            name="email"
          />
        </label>
        <ul>
          {this.state.data.map((person, i) => {
            if (person.id == 1) {
              console.log('am typing.......');
              return (
                <div key={i}>
                  <div>{person.name} is typing.....</div>
                </div>
              );
            }
          })}
        </ul>
      </div>
    );
  }
}

2 个答案:

答案 0 :(得分:0)

您可以使用lodash的debounce函数,该函数会将动作延迟指定的ms数量。例如,如果用户正在键入,它将不断重置延迟。当用户停止键入时,延迟用完并触发操作。 (另外,请阅读示例代码下方的注释)

您可以通过将data映射到容器中并将其传递到可重复使用的组件,来放大下面的示例以包含用户名。

工作示例https://codesandbox.io/s/j3n6q98m0w

components / App / App.js

import debounce from "lodash/debounce";
import React, { Component } from "react";

export default class App extends Component {
  constructor() {
    super();
    this.state = { isTyping: false, test: "" };
    this.handleChange = this.handleChange.bind(this);
  }

  handleChange({ target: { name, value } }) {
    this.setState({ isTyping: true, [name]: value }, () => { // allows user input updates and continually sets "isTyping" to true
      this.handleTyping();
    });
  }

  handleTyping = debounce(function() { // continually delays setting "isTyping" to false for 500ms until the user has stopped typing and the delay runs out
    this.setState({ isTyping: false });
  }, 500);

  render() {
    return (
      <div className="app-container">
        <h1>Capturing User Input</h1>
        <input
          className="uk-input"
          placeholder="Type something..."
          type="text"
          name="test"
          value={this.state.test}
          onChange={this.handleChange}
        />
        <p className="user-typing">
          {this.state.isTyping && "User is typing..."}
        </p>
      </div>
    );
  }
}

注意:您无需在render方法内创建匿名函数:

onKeyDown={(event) => this.onKeyPressed(event)}

相反,它将是:

onKeyDown={this.onKeyPressed}

默认情况下,onKeyDown发送event到回调onKeyPressed

onKeyPressed(e){
  console.log(e.keyCode);
}

唯一需要创建匿名函数的时间是,除了event之外,还包括一个值:

onKeyDown={(event) => this.onKeyPressed(event, this.state.value)}

然后您的回调onKeyPressed将接受两个参数:

onKeyPressed(e, val){
  console.log(e.keyCode);
  console.log(val);
}

答案 1 :(得分:0)

这是这个答案的 Hooks 版本的一个版本......我发现这个答案非常有用

import { useState } from "react";
import { Form, Button, FormControl, InputGroup } from "react-bootstrap";
import debounce from "lodash/debounce";

const SendMessageForm = ({ sendMessage, messages }) => {
  const [message, setMessage] = useState("");
  const [isTyping, setIsTyping] = useState(false);
  // const [currentUserTyping, setCurrentUserTyping] = useState("");

  // useEffect(() => {
  //   checkUserTyping();
  // }, [messages]);

  const handleIsTyping = debounce(function () {
    // continually delays setting "isTyping" to false for 500ms until the user has stopped typing and the delay runs out
    setIsTyping(false);
  }, 500);

  // const checkUserTyping = () => {
  //   const user = messages.map((m) => m.user);
  //   setCurrentUserTyping(user);
  //   console.log(user);
  // };

  return (
    <Form
      onSubmit={(e) => {
        e.preventDefault();
        sendMessage(message);
        setMessage("");
      }}
    >
      <InputGroup>
        <FormControl
          type="user"
          placeholder="message..."
          onChange={(e) => {
            setMessage(e.target.value);
            setIsTyping(true);
            handleIsTyping();
          }}
          name="message"
          value={message}
        />
        <span className="user-typing">
          {isTyping && `a user is typing....`}
        </span>
        <InputGroup.Append>
          <Button variant="primary" type="submit" disabled={!message}>
            Send
          </Button>
        </InputGroup.Append>
      </InputGroup>
    </Form>
  );
};

export default SendMessageForm;
相关问题