0

I'm trying to build a web page which listens for any keypresses and sends a POST request to a server to obtain some data. Using the data returned back, I wanted to render that onto the webpage.

Originally, to get keypresses, I had an HTML file and in the header, I had a script tag which looked something like this:

<script type="text/javascript">
      document.onkeypress = function(evt) {
        evt = evt || window.event;
        var charCode = evt.keyCode || evt.which;
        var charStr = String.fromCharCode(charCode);
        console.log(charStr);

        var params = {
          key: charStr
        };

        var form = document.createElement("form");
        console.log(form);
        form.method = "post";
        form.action = "http://localhost:8888/";

        for (var key in params) {
          if (params.hasOwnProperty(key)) {
            var hiddenField = document.createElement("input");
            hiddenField.type = "hidden";
            hiddenField.name = key;
            hiddenField.value = params[key];
            console.log(hiddenField);

            form.appendChild(hiddenField);
          }
        }

        document.body.appendChild(form);
        form.submit();
      };
    </script>

Now I'm using React as I want to listen for any keypresses and render the returned data onto the webpage without having to refresh. I have a component which looks something like this

class myComponent extends React.Component {
  constructor() {
    super();
    this.state = {
      x: null,
      y: null,
      z: null
    };
  }

  componentDidMount() {
    fetch("/some-endpoint")
      .then(res => res.json())
      .then(
        returnData => this.setState(returnData),
        () => console.log("State has been set to the return data")
      );
  }

  render() {
    return (
      <div>
        <h1>{this.state.x}</h1>
        <h2>{this.state.y}</h2>
        <h2>{this.state.z}</h2>
      </div>
    );
  }
}

What I want to do is basically have that script that I was running in the HTML snippet above running somewhere in this component, but I'm unable to simply copy paste it into a script tag in my div and return it along with the HTML as I get errors saying stuff like "')' expected" and I'm really not sure what they mean in this context. I feel like I may be approaching this the wrong way, but basically, I want to be able to add that functionality into my web page with React. I think it would have to be in the same component as myComponent to tell this component to update its state, but I could be wrong about that. If anyone can point me along the right path or give me some guidelines, that would be immensely helpful. Thanks in advance!

1
  • I have not built your code, but that then is definitely super wrong. This part is fine: returnData => this.setState(returnData). I'm not sure what you want to do with the other function, but your syntax is busted. Commented Jul 26, 2019 at 3:36

2 Answers 2

1

In React, you'll want to add your event listener inside componentDidMount and destroy the listener inside componentWillUnmount.

You'll also want to move your handler into a seperate function within the class to reference when you're destorying the listener.

It should look something like this:

class myComponent extends React.Component {
  ...

  componentDidMount() {
    document.addEventListener('keypress', this.handleKeyPress.bind(this))
  }

  componentWillUnmount() {
    document.removeEventListener('keypress', this.handleKeyPress)
  }

  handleKeyPress() {
    fetch('/some-endpoint', { method: 'POST' })
      .then(resp => resp.json())
      .then(respJson => this.setState(respJson))
  }
}

One thing to note, is that in your code snippet, the syntax for handling the response of the fetch is invalid.


A helpful resource is this documentation page on the React website:

https://react-cn.github.io/react/tips/dom-event-listeners.html

Sign up to request clarification or add additional context in comments.

2 Comments

Implemented this solution. The other solution was similar as well and was helpful too but this is the one I went with as it was neat. Thank you! The link was handy as well
I'm happy to hear it helped :)
1

It sounds like you're trying to add the script tags to render, you can just add the code inside the script tags to componentDidMount:

componentDidMount() {
  document.onkeypress = evt => {
    ...
  };

  fetch("/some-endpoint")
    .then(res => res.json())
    .then(
      returnData => this.setState(returnData,
      () => console.log("State has been set to the return data")
    ));
}

Also, I notice that your parentheses are in the wrong place, which could be the reason for the error you're seeing. See the second .then above, you should move the right paren from returnData to after the setState callback.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.