React onClick只触发一次

React onClick firing only once

本文关键字:一次 onClick React      更新时间:2023-09-26

React onClick在ServiceView中只在显示组件后触发一次。当我点击添加图标时,添加了新的组件。但在第二次点击添加图标不做任何输出,没有错误,没有警告。我在chrome控制台看到组件,在控制台组件有绑定功能,但为什么它的功能不火我不明白。你能告诉我怎么了吗?谢谢。

var Textarea = React.createClass({
  getInitialState: function(){
    return {
      value: '',
    };
  },
  getDefaultProps: function(){
    return {
      disabled: false
    };
  },
  componentWillMount: function(){
    if(this.props.value){
      this.setState({value: this.props.value});
    }
  },
  onChange: function(e){
    if(this.props.onChange){
      this.props.onChange(e.target.value);
    }
    this.setState({value: e.target.value});
  },
  render: function(){
    var value = this.state.value;
    return (
      <div className="form-group">
        <label className={this.props.label_class}>{ this.props.label_name }</label>
        <div className={this.props.input_class}>
          <textarea disabled={this.props.disabled} className='form-control' value={value} onChange={this.onChange} />
        </div>
      </div>);
  }
});
var List = React.createClass({
    getDefaultProps: function(){
        return {
            size: "6",
            disabled: false,
            groupClass: '',
            labelClass: '',
            inputClass: ''
        };
    },
    onChange: function(e){
        var key = e.target.value;
        if(this.props.onChange){
            if (key === undefined){
                this.props.onChange(null);
            } else {
                this.props.onChange(key);
            }
        }
    },
    renderOption: function(key){
        return <option value={key}>{this.props.options[key]}</option>;
    },
    render: function(){
        return <div className={this.props.groupClass}>
                 <label className={this.props.labelClass}>{ this.props.labelName }</label>
                 <div className={this.props.inputClass}>
                   <select onChange={this.onChange} disabled={this.props.disabled} className='form-control' value={this.props.value}>
                     <option></option>
                     {Object.keys(this.props.options).map(this.renderOption)}
                   </select>
                 </div>
               </div>;
    },
});
var Input = React.createClass({
  getInitialState: function(){
    return {
      value: '',
      valid: true,
      groupClass: '',
      labelClass: '',
      inputClass: ''
    };
  },
  getDefaultProps: function(){
    return {
      disabled: false,
      type: 'text'
    };
  },
  componentWillMount: function(){
    if(this.props.value) {
      this.setState({value: this.props.value});
    }
  },
  onChange: function(e) {
    if(this.props.onChange) {
      this.props.onChange(e.target.value);
    }
    var dataStr = e.target.value;
    var pattern = / /;
    var valueType = this.props.valueType;
    switch (valueType) {
      case 'integer':
        pattern =  /^[0-9]+$/;
        break;
      case 'float':
        pattern = /^[0-9]+'.[0-9]+$/;
        break;
      default:
        pattern = /'w/;
    }
    if(pattern.test(dataStr) === true || dataStr === '') {
      this.setState({valid: true});
    } else {
      this.setState({valid: false});
    }
    this.setState({value: e.target.value});
  },
  render: function() {
    var value = this.state.value;
    if (this.state.valid) {
      this.state.formClass = 'form-control valid';
    } else {
      this.state.formClass = 'form-control invalid';
    }
    return (
      <div className={this.props.groupClass}>
        <label className={this.props.labelClass}>{ this.props.labelName }</label>
        <div className={this.props.inputClass}>
          <input disabled={this.props.disabled} type={this.props.type} className={this.state.formClass} value={value} placeholder={this.props.placeholder} onChange={this.onChange} valueType={this.props.valueType} />
        </div>
      </div>
    );
  }
});
function zeroPad(num, places) {
    var zero = places - num.toString().length + 1;
    return Array(+(zero > 0 && zero)).join("0") + num;
}
function append(postfix) {
    return function(prefix) {
        return prefix + postfix;
    };
}
var PointView = React.createClass({
    render: function() {
        var time = [],
            icon = '',
            val,
            postfix = append(':00');
        for(var i=0; i < 24; ++i) {
            val = postfix(zeroPad(i));
            time.push({val: val});
        }
        if (this.props.icon) {
            var className = 'icon glyphicon glyphicon-'+this.props.icon;
            icon = (
                <div className="col-md-2">
                  <a id={'id_'+this.props.index} onClick={this.props.onClick}>
                    <i className={className}></i>
                  </a>
                </div>)
        }
        return (
            <div className="row form-group">
                <label className="control-label col-md-2 requiredField">{this.props.pointName}</label>
                <div className="main">
                  <div className="col-md-4">
                    <div className="row">
                      <Input groupClass="col-md-6"
                        labelName="state"
                        labelClass="control-label"
                        inputClass="controls"/>
                      <Input groupClass="col-md-6"
                        labelName="address"
                        labelClass="control-label"
                        inputClass="controls"/>
                    </div>
                  </div>
                  <div className="col-md-2 col-md-offset-2">
                    <div className="row">
                      <List groupClass="col-md-6"
                        labelName="from"
                        labelClass="control-label"
                        inputClass="controls"
                        options={time}/>
                      <List groupClass="col-md-6"
                        labelName="to"
                        labelClass="control-label"
                        inputClass="controls"
                        options={time}/>
                    </div>
                  </div>
                  {icon}
                </div>
                <div className="contacts">
                  <Input groupClass="col-md-4 col-md-offset-2 additional"
                        labelName="name"
                        labelClass="control-label"
                        inputClass="controls"/>
                  <Input groupClass="col-md-2 col-md-offset-2"
                        labelName="phone"
                        labelClass="control-label"
                        inputClass="controls"/>
                </div>
            </div>
        );
    }
});
var ServiceView = React.createClass({
    getInitialState: function() {
        return {
            points: [{icon: ''}, {icon: 'plus'}],
            minimum: 2
        };
    },
    findNode: function(node) {
        return React.findDOMNode(this.refs[node]).value.trim();
    },
    handleSubmit: function(e) {
        var description = this.findNode('description'),
        date = this.findNode('date');
        e.preventDefault();
    },
    handleClick: function(index) {
        var points = this.state.points.slice(),
            child = points[index];
        if (child.icon === 'minus') {
            points.splice(index, 1);
        } else if (child.icon === 'plus') {
            points.splice(points.length-1, 0, {icon: 'minus'});
        }
        this.setState({points: points});
    },
    render: function() {
        var self = this,
            categories = ['one', 'two', 'three'].map(function (item, index) {
                return {index: item};
            }),
            points = this.state.points.map(function (item, index) {
                return <PointView index={index} icon={item.icon} onClick={this.handleClick.bind(this, index).toString()}/>
            }, this);
        return (
            <div className="form-panel">
                <h2 className="mb"><i className="fa fa-angle-right"></i> New order</h2>
                <form className="form-horizontal style-form" method="post" action="." onSubmit={this.handleSubmit}>
                    <input id="id_points-TOTAL_FORMS" name="points-TOTAL_FORMS" type="hidden" value={this.state.points.length}/>
                    <input id="id_points-INITIAL_FORMS" name="points-INITIAL_FORMS" type="hidden" value="0"/>
                    <input id="id_points-MIN_NUM_FORMS" name="points-MIN_NUM_FORMS" type="hidden" value={this.state.minimum}/>
                    <input id="id_points-MAX_NUM_FORMS" name="points-MAX_NUM_FORMS" type="hidden" value="1000"/>
                    <List label_class="control-label col-lg-2 requiredField"
                        label_name="category"
                        input_class="controls col-lg-8"
                        options={categories}/>
                    <Input label_class="control-label col-lg-2 requiredField"
                        label_name="date"
                        input_class="controls col-lg-8"/>
                    <Textarea label_class="control-label col-lg-2 requiredField"
                        label_name="description"
                        input_class="controls col-lg-8"/>
                    {points}
                </form>
            </div>
        );
    }
});

看起来您已经附加了一个字符串表示的事件处理程序作为您的onClick:

onClick={this.handleClick.bind(this, index).toString()}

那可能不是你的意思。如果你只做onClick={this.handleClick.bind(this, index)},它会工作吗?