1.从hello,world开始
<body>
<div id="reactContainer"></div>
<script src="./react.js"></script>
<script src="./react-dom.js"></script>
<script>
var HelloComponent =React.createClass({
render:function(){
return React.createElement('h1',null,'Hello world');
}
});
ReactDOM.render(
React.createElement(HelloComponent,null),
document.getElementById('reactContainer')
)
</script>
</body>
我们引入了react.js和react-dom.js两个文件。定义了React类HelloComponent,并且将HelloComponent渲染到了id为‘reactContainer’的dom上
2.使用jsx语法
jsx语法是指能在js使用html标签
<body>
<div id="reactContainer"></div>
<script src="./react.js"></script>
<script src="./react-dom.js"></script>
<script src="http://cdn.bootcss.com/babel-core/5.8.38/browser.min.js"></script>
<script type="text/babel">
var HelloComponent =React.createClass({
render:function(){
return (
<div>
<h1>Hello,world</h1>
</div>
)
}
});
var app = document.getElementById('reactContainer');
ReactDOM.render(
<HelloComponent/>,
app
)
</script>
</body>
3.嵌套组件
组件是可以被复用的,我们定义了A组件和B组件,那么就可以在A组件中引用B组件
<body>
<div id="reactContainer"></div>
<script type="text/babel">
var HelloComponent =React.createClass({
render:function(){
return (
<div>
<h1>Hello,world</h1>
</div>
)
}
});
var Hellos = React.createClass({
render:function(){
var hellos = [];
for(let i=0;i<10;i++){
hellos.push(<HelloComponent/>);
}
return (
<div>
{hellos}
</div>
)
}
});
var app = document.getElementById('reactContainer');
ReactDOM.render(
<Hellos/>,
app
)
</script>
</body>
4.状态管理
有了组件的躯壳,还要有state状态管理才能使整个页面动起来,以一个小例子为例:
点击 ‘+’ count 加一;点击 ‘-’ count减一
改变state必须要this.setState({count: this.state.count + num });
,不能这样this.state.count+=num
这里如果不需要传递参数,直接this.changeCount
就好了,如果要传递参数,需要this.changeCount.bind(this,param)
var Box = React.createClass({
render: function(){
return (
<div>
<button onClick={this.changeCount.bind(this,-1)}>-</button>
<h1>{this.state.count}</h1>
<button onClick={this.changeCount.bind(this,1)}>+</button>
</div>
)
},
getInitialState: function(){
return {
count: 5
}
},
changeCount: function(num){
this.setState({
count: this.state.count + num
});
}
});
5.属性传递
说到state,就不得不说说他的好基友
props
了
props
是由外向内传递的值,这个设定决定了他有两个特性:props
的值不能被改变 并且props
可以指定传参类型
var SubBox = React.createClass({
render: function() {
return (
<div>
<h2>{this.state.msg}</h2>
<p>{this.props.say}</p>
</div>
)
},
getInitialState: function() {
return {
msg: '我是子组件'
}
},
getDefaultProps: function(){
return {
say: 'no word' //这是默认值
}
}
});
var SuperBox = React.createClass({
render: function() {
return (
<div>
<h1>{this.state.msg}</h1>
<SubBox say={this.state.say}/>
</div>
)
},
getInitialState: function(){
return {
msg: '我是父组件',
say: 'just a word'
}
}
});
6.双向数据流
我们希望
React
能像Vue
一样数据是双向绑定的,看下面这个例子:
我们希望:输入框和段落同时绑定了同一个值,输入框输入时,段落里的值也会跟着相应改变。
var Box = React.createClass({
render: function(){
return (
<div>
<p>{this.state.msg}</p>
<input type="text" value={this.state.msg} />
</div>
)
},
getInitialState: function(){
return {
msg: 'just a word'
}
}
});
然而实际不是这样子的,如果我们想要实现上面的需求,我们需要这样做:
输入框用onChange
方法监听输入,输入变化后执行inputChange
方法,给msg重新赋值,从而实现数据同步
var Box = React.createClass({
render: function(){
return (
<div>
<p>{this.state.msg}</p>
<input type="text" value={this.state.msg} onChange={this.inputChange}/>
</div>
)
},
getInitialState: function(){
return {
msg: 'just a word'
}
},
inputChange: function(e){
this.setState({
msg: e.target.value
});
}
});
这样子处理实现不够优雅,
react
为了解决这个问题,提供了mixins
var Box = React.createClass({
mixins:[React.addons.LinkedStateMixin],
render: function(){
return (
<div>
<p>{this.state.msg}</p>
<input type="text" valueLink={this.linkState('msg')} />
</div>
)
},
getInitialState: function(){
return {
msg: 'just a word'
}
}
});