Original address: North Cloud Software-first knowledge react
Focus on the UI
In the MVC layered design pattern, react is often taken to implement the view layer (V).
React does not depend on other parts of the technology stack, so it is easy to try it out in an existing project to implement a small feature.
Virtual DOM
React is abstracted from the DOM, giving a more concise programming model and performing better. Enable server-side rendering via Nodejs and develop native apps through react native.
Data flow
REACT enables one-way, responsive data flow, reducing boilerplate and easier to understand than traditional data binding.
Simple components
The react component implements a render () method that receives the input data and returns the content to be displayed. In this example we use JSX (class XML syntax) to write code. The render () method accesses the input data through the This.props property.
React does not mandate developers to use JSX. In compiled JS, you can view the original JavaScript code generated by JSX.
// JSX code
var HelloMessage = React.createClass({
render: function() {
return <div>Hello {this.props.name}</div>;
}
});
React.render(<HelloMessage name="John" />, mountNode);
// compiled javascript code
var HelloMessage = React.createClass({displayName: "HelloMessage",
render: function() {
return React.createElement("div", null, "Hello ", this.props.name);
}
});
React.render(React.createElement(HelloMessage, {name: "John"}), mountNode);
Component with state
In addition to accessing input data through this.props, the component can also maintain its internal state data through this.state. When the state data of a component changes, the component will call the render () method again to redraw.
// JSX code
var Timer = React.createClass({
getInitialState: function() {
return {secondsElapsed: 0};
},
tick: function() {
this.setState({secondsElapsed: this.state.secondsElapsed + 1});
},
componentDidMount: function() {
this.interval = setInterval(this.tick, 1000);
},
componentWillUnmount: function() {
clearInterval(this.interval);
},
render: function() {
return (
<div>Seconds Elapsed: {this.state.secondsElapsed}</div>
);
}
});
React.render(<Timer />, mountNode);
// compiled javascript code
var Timer = React.createClass({displayName: "Timer",
getInitialState: function() {
return {secondsElapsed: 0};
},
tick: function() {
this.setState({secondsElapsed: this.state.secondsElapsed + 1});
},
componentDidMount: function() {
this.interval = setInterval(this.tick, 1000);
},
componentWillUnmount: function() {
clearInterval(this.interval);
},
render: function() {
return (
React.createElement("div", null, "Seconds Elapsed: ", this.state.secondsElapsed)
);
}
});
React.render(React.createElement(Timer, null), mountNode);
React application
Using properties and states together, you can build a basic to-do application. In this example, the state is used to track the list of items and the new item names entered by the user, and even though the event handlers appear to be inline, they will still be collected and implemented through the proxy.
// JSX code
var TodoList = React.createClass({
render: function() {
var createItem = function(itemText, index) {
return <li key={index + itemText}>{itemText}</li>;
};
return <ul>{this.props.items.map(createItem)}</ul>;
}
});
var TodoApp = React.createClass({
getInitialState: function() {
return {items: [], text: ‘‘};
},
onChange: function(e) {
this.setState({text: e.target.value});
},
handleSubmit: function(e) {
e.preventDefault();
var nextItems = this.state.items.concat([this.state.text]);
var nextText = ‘‘;
this.setState({items: nextItems, text: nextText});
},
render: function() {
return (
<div>
<h3>TODO</h3>
<TodoList items={this.state.items} />
<form onSubmit={this.handleSubmit}>
<input onChange={this.onChange} value={this.state.text} />
<button>{‘Add #‘ + (this.state.items.length + 1)}</button>
</form>
</div>
);
}
});
React.render(<TodoApp />, mountNode);
// compiled javascript code
var TodoList = React.createClass({displayName: "TodoList",
render: function() {
var createItem = function(itemText, index) {
return React.createElement("li", {key: index + itemText}, itemText);
};
return React.createElement("ul", null, this.props.items.map(createItem));
}
});
var TodoApp = React.createClass({displayName: "TodoApp",
getInitialState: function() {
return {items: [], text: ‘‘};
},
onChange: function(e) {
this.setState({text: e.target.value});
},
handleSubmit: function(e) {
e.preventDefault();
var nextItems = this.state.items.concat([this.state.text]);
var nextText = ‘‘;
this.setState({items: nextItems, text: nextText});
},
render: function() {
return (
React.createElement("div", null,
React.createElement("h3", null, "TODO"),
React.createElement(TodoList, {items: this.state.items}),
React.createElement("form", {onSubmit: this.handleSubmit},
React.createElement("input", {onChange: this.onChange, value: this.state.text}),
React.createElement("button", null, ‘Add #‘ + (this.state.items.length + 1))
)
)
);
}
});
React.render(React.createElement(TodoApp, null), mountNode);
Components can use third-party plugins
React is very flexible, allowing hooking to other libraries and frameworks via hooks. This example uses an external Markdown library to transform the content in the text field in real time.
// JSX code
var MarkdownEditor = React.createClass({
getInitialState: function() {
return {value: ‘Type some *markdown* here!‘};
},
handleChange: function() {
this.setState({value: React.findDOMNode(this.refs.textarea).value});
},
render: function() {
return (
<div className="MarkdownEditor">
<h3>Input</h3>
<textarea onChange={this.handleChange} ref="textarea" defaultValue={this.state.value} />
<h3>Output</h3>
<div className="content" dangerouslySetInnerHTML={{
__html: marked(this.state.value, {sanitize: true})
}}/>
</div>
);
}
});
React.render(<MarkdownEditor />, mountNode);
// compiled javascript code
var MarkdownEditor = React.createClass({displayName: "MarkdownEditor",
getInitialState: function() {
return {value: ‘Type some *markdown* here!‘};
},
handleChange: function() {
this.setState({value: React.findDOMNode(this.refs.textarea).value});
},
render: function() {
return (
React.createElement("div", {className: "MarkdownEditor"},
React.createElement("h3", null, "Input"),
React.createElement("textarea", {
onChange: this.handleChange,
ref: "textarea",
defaultValue: this.state.value
}),
React.createElement("h3", null, "Output"),
React.createElement("div", {
className: "content",
dangerouslySetInnerHTML: {
__html: marked(this.state.value, {sanitize: true})
}
})
)
);
}
});
React.render(React.createElement(MarkdownEditor, null), mountNode);