简体   繁体   中英

How to 'reset' a ReactJS element?

I'm trying to 'reset' a ReactJS element.

In this case, the element is 90%+ of the contents of the page.

I'm using replaceState to replace the state of the element with with its initial state.

Unfortunately, sub-elements which have their own 'state' do not reset. In particular, form fields keep their contents.

Is there a way of forcing a re-render of an element, which will also cause sub-elements to re-render, as if the page had just loaded?

Adding a key to the element forces the element (and all its children) to be re-rendered when that key changes.

(I set the value of 'key' to simply the timestamp of when the initial data was sent.)

render: function() {
  return (
    <div key={this.state.timestamp} className="Commissioning">
      ...

The this.replaceState(this.getInitialState()) method doesn't actually reset children that are inputs, if that's what you're looking for. For anyone looking to just reset their form fields, there is a standard DOM reset() function that will clear all the inputs in a given element.

So with React, it'd be something like this:

this.refs.someForm.getDOMNode().reset();

Doumentation:

https://developer.mozilla.org/en-US/docs/Web/API/HTMLFormElement/reset

If it is a form you want to reset, you simply can use this

// assuming you've given {ref: 'form'} to your form element
React.findDOMNode(this.refs.form).reset();

While I don't personally think you should store local, interim component state (like in-progress input boxes) in a centralized location (like a flux store) in most cases, here it may make sense, depending on how many you have, especially since it sounds like the inputs already have some server interaction/validation around them. Pushing that state up the component hierarchy or into some other central location may help a lot in this case.

One alternative idea off the top of my head is to use a mixin in components that might need to reset local state, and do some kind of event triggering, etc. to make it happen. For example, you could use Node's EventEmitter or a library like EventEmitter3 with a mixin like this (warning: not tested, maybe best this as pseudocode :)

var myEmitter = new EventEmitter(); // or whatever

var ResetStateMixin = {
  componentWillMount: function() {
    myEmitter.on("reset", this._resetState);
  },

  componentWillUnmount: function() {
    myEmitter.off("reset", this._resetState);
  },

  _resetState: function() {
    this.replaceState(this.getInitialState());
  },

  triggerReset: function() {
    myEmitter.emit("reset");
  }
};

Then you could use it in components like so:

React.createClass({
  mixins: [ResetStateMixin],

  getInitialState: function() {
    return { ... };
  },

  onResetEverything: function() {
    // Call this to reset every "resettable" component
    this.triggerReset();
  }
});

This is very basic and pretty heavy handed (you can only reset all components, every component calls replaceState(this.getInitialState()) , etc.) but those problems could be solved by extending the mixin a bit (eg having multiple event emitters, allowing component-specific resetState implementations, and so forth).

It's worth noting that you do have to use controlled inputs for this to work; while you won't need to push your state all the way up the component hierarchy, you'll still want all your inputs to have value and onChange (etc.) handlers.

You could also use

document.forms[0].reset()

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM