Reputation:
i wanna edit my p
element's text when i press edit button
.
When i click edit button
, i display a textarea
and get keyed text with alert but can't put that text to my p
element.
What is the simple way to do it with React.js ?
When i press edit button, editing state changing and textarea shows up.The code below.
renderNormal: function() {
return (
<div>
<p>Edit me</p>
<button onClick={this.edit}>Edit</button>
</div>
)
},
renderForm: function() {
return (
<div>
<textarea ref="newText" defaultValue="Edit me"></textarea>
<button onClick={this.save}>Save</button>
</div>
)
},
render: function() {
if (this.state.editing) {
return this.renderForm()
} else {
return this.renderNormal()
}
}
Upvotes: 5
Views: 40713
Reputation: 1
I actually had this same problem, here was my solution:
{editableSubTasks.filter(id => id === subTask.Id).length > 0 ? <input type="text" /> : <span>{subTask.Name}</span>}
So basically, you have an array, in my case it was editableSubTasks
. Whenever I would trigger the text element to change to a textarea, I would simply add that guy to the edtiableSubTasks
array. And then in my map
function, if the Id of the correspnding item was in the editableSubTasks
array, I would use a ternary operator to tell it to be a <input type="text">
, otherwise just a span
. In your case obviously you can use a textarea. This worked out wonderfully. Here was my SO with the answer that I ended up using:
How to dynamically show/hide a list of items in react
If you don't need the array, then the answer is even simpler, just have a bool and change it to true when you want it to be a text area.
Upvotes: 1
Reputation: 5927
You need to store and retrieve the text from a state variable. Modifying the state causes a re-render, which will then display the updated text. Copied from your JSFiddle... note where I've added a "text" property to your state
var MyCom = React.createClass({
getInitialState: function() {
return {
editing: false,
// ** Initialize "text" property with empty string here
text: ''
}
},
edit: function() {
this.setState({
editing: true
})
},
save: function() {
var val = this.refs.newText.value;
alert(val)
this.setState({
// ** Update "text" property with new value (this fires render() again)
text: val,
editing: false
})
},
renderNormal: function() {
// ** Render "state.text" inside your <p> whether its empty or not...
return (
<div>
<p>{this.state.text}</p>
<button onClick={this.edit}>Edit</button>
</div>
)
},
renderForm: function() {
return (
<div>
<textarea ref="newText" defaultValue="Edit me"></textarea>
<button onClick={this.save}>Save</button>
</div>
)
},
render: function() {
if (this.state.editing) {
return this.renderForm()
} else {
return this.renderNormal()
}
}
})
ReactDOM.render(
<div>
<MyCom/>
<MyCom/>
</div>,
document.querySelector(".box")
)
Upvotes: 8
Reputation: 5917
You have to set a value on the state
on the button is clicked, and then read that on render.
Example:
handler : function () {
this.setState({ value : 'hey' });
},
render : function () {
return <p>{ this.state && this.state.value ? this.state.value : 'hoy' }</p>;
}
Everytime you want the render method to change according to something that can happen, the action that triggers it must trigger a state change, and change the state object, and the object will be rerendered, so the render method should check the current state.
If you want to change the value of a input (or in your case, a textarea), you can use the linkedstate pattern as a two way databinding (more here).
I particularly use this lib. There are plenty of examples there.
Upvotes: 1