React.js-使用JSX有条件地呈现和可编辑输入

时间:2018-07-15 12:44:15

标签: javascript reactjs conditional react-state-management

我有一张这样的桌子:

enter image description here

当用户单击Edit按钮时,应在其位置出现<input>

如果用户单击另一个Edit按钮,则该按钮也将替换为<input>,并且以前的<input>应该消失并再次显示Edit按钮

简而言之,一次只能将一个字段置于编辑模式。

这是我最初的state

state = {
    editnameEnable: false,
    editemailEnable: false,
    editaddressEnable: false,
    edittelephone_noEnable: false,
}

这是我的edit()方法:

edit = value => {
    var address_element = ['name','address','email','telephone_no']; 
    address_element = address_element.filter(element => element !== value); 
    address_element.map( val => this.setState({[`edit${val}Enable`]: false}));

    this.setState({[`edit${value}Enable`]: true}, ()=>{
        console.log(this.state);
    });
}

这是我的render方法中JSX的一部分:

<td>{
    this.state[`edit${this.props.item}Enable`] ? ( <input type="text"/> ) : (
        <span
            className="edit"
            onClick={ () => this.edit(this.props.item) }>Edit</span>
    )
}</td>

问题是,当我单击Edit按钮时,会出现<input>,但是当我单击另一个Edit按钮时,前一个<input>不会消失。

1 个答案:

答案 0 :(得分:3)

如何使用最初设置为editableField的单个null属性?

然后,当您单击Edit按钮时,将editableField设置为该字段的名称,然后在render内检查每个字段的{{1} }是否匹配其名称,以呈现editableField按钮或输入字段。

类似这样的东西:

Edit
class FieldCell extends React.Component {

  constructor(props) {
    super(props);
  }
  
  focusField = (element) => element && element.focus();
  
  render() {
    const editElement = this.props.isEditable ? (
      <input type="text" ref={ this.focusField }/>
    ) : (
      <button onClick={ () => this.props.onEdit() }>EDIT</button>
    );
    
    return (<td className="textLeft">{ editElement }</td>);
  }
}

class UserData extends React.Component {

  constructor(props) {
    super(props);
    
    this.state = {
      editableField: null,
    };
  }
  
  render() {
    const editableField = this.state.editableField;
    
    const rows = ['Name', 'Address', 'Telephone No.', 'E-Mail'].map((field) => {
      const isEditable = field === editableField;
      
      return (
        <tr key={ field }>
          <td>{ field }</td>
          <FieldCell isEditable={ isEditable } onEdit={ () => this.setState({ editableField: field })}></FieldCell>
        </tr>
      );
    });

    return (<table>{ rows }</table>);
  }
}

ReactDOM.render(<UserData />, document.getElementById('app'));
body {
  font-family: monospace;
  font-size: 13px;
}

table {
  border: 2px solid #000;
  border-collapse: collapse;
  text-align: right;
  width: 100%;
}

td {
  border: 2px solid #000;
  padding: 4px;
  width: 50%;
  overflow: hidden;
}

.textLeft {
  text-align: left;
  user-select: none;
}

button,
input {
  border: 2px solid black;
  padding: 4px 8px;
  margin: 0;
  font-family: monospace;
  font-size: 13px;
  box-sizing: border-box;
  background: none;
  outline: none;
}

button:hover,
button:focus,
input:hover,
input:focus {
  border-color: blue;
  color: blue;
}

button {
  font-weight: bold;
}

input {
  width: 50%;
}