**1. 组件 **
**2. state **
- state 不能直接赋值,比如以下的代码 :
//wrong
this.state.comment = 'Hello';
// Correct
this.setState({comment: 'Hello'});
- state是异步的,因此你不能用某个state计算得到下个state:
// Wrong
this.setState({ counter: this.state.counter + this.props.increment,});
// Correct
this.setState((prevState, props) => ({ counter: prevState.counter + props.increment}));
注意上面setState方法,它不仅仅可以接收一个对象,还可接收一个方法,这个方法的参数分别是上一个state,和当前的props。
**3. 事件 **
- 阻止事件冒泡,必须显式指定
//js
Click me
//react
function ActionLink() {
function handleClick(e) {
e.preventDefault();
console.log('The link was clicked.');
}
return ( Click me );
}
- react事件作用域问题:
import React, {Component} from 'react'
export default class Toggle extends Component{
constructor(props){
super(props);
this.state={isToggleOn : true};
// 必须bind(this),否则报错(this值window对象)
this.handleClick = this.handleClick.bind(this);
}
handleClick() {
this.setState(prevState=>({
isToggleOn : !prevState.isToggleOn
}));
}
render(){
return (
)
}
}
如果把上面的 this.handleClick = this.handleClick.bind(this);这句去掉,就会报错,解决办法3种:
You have to be careful about the meaning of this in JSX callbacks. In JavaScript, class methods are not bound by default. If you forget to bind this.toggle and pass it to onClick, this will be undefined when the function is actually called.
This is not React-specific behavior; it is a part of how functions work in JavaScript. Generally, if you refer to a method without () after it, such as onClick={this.handleClick}, you should bind that method.
If calling bind annoys you, there are two ways you can get around this. If you are using the experimental property initializer syntax, you can use property initializers to correctly bind callbacks:
- 用Lambda表达式定义函数
handleClick=()=> {
this.setState(prevState=>({
isToggleOn : !prevState.isToggleOn
}));
}
- jsx调用时bind:
render(){
return (
)
}
- jsx用Lambda调用
render(){
return (
)
}
**4. 条件渲染 **
function Mailbox(props) {
const unreadMessages = props.unreadMessages;
return (
Hello!
//此处若length>0 则会渲染h2
{unreadMessages.length > 0 &&
You have {unreadMessages.length} unread messages.
}
);
}
const messages = ['React', 'Re: React', 'Re:Re: React'];
ReactDOM.render(
,
document.getElementById('root')
);
5. List
- 列表循环必须要提供key:
import React, {Component} from 'react'
export default class List extends Component{
render(){
const stus = this.props.stus;
const stuListElements = stus.map((stu)=>{stu} );
return (
{stuListElements}
);
}
}
//报错:warning.js:36 Warning: Each child in an array or iterator should have a unique "key" prop.
// Check the render method of `List`. See https://fb.me/react-warning-keys for more information.
Keys help React identify which items have changed, are added, or are removed. Keys should be given to the elements inside the array to give the elements a stable identity:
The best way to pick a key is to use a string that uniquely identifies a list item among its siblings. Most often you would use IDs from your data as keys:
解决办法是给每个列表项提供一个唯一key,一般可以是id
let testStu = [
{id:1,name:'aaa'},
{id:2,name:'bbb'},
{id:3,name:'ccc'}
];
...
const stuListElements = stus.map((stu)=>{stu.name} );
...
要是列表项没有key怎么办?官方给出的答案是使用数组下标,万不得已采用,因为这个会减慢渲染速度:
// Only do this if items have no stable IDs
const todoItems = todos.map((todo, index) =>
{todo.text} );
- key 始终应该在Array内部定义!
function Number(props) {
// Correct! There is no need to specify the key here:
return {props.value} ;
}
function NumberList(props) {
const numbers = props.numbers;
const listItems = numbers.map((number) =>
// Correct! Key should be specified inside the array.
);
return (
{listItems}
);
}
const numbers = [1, 2, 3, 4, 5];
ReactDOM.render(
,
document.getElementById('root')
);
** 6. Form **
- Two types of form components:
Controlled Components (有value属性的)
Uncontrolled Components(没有value属性的)
import React, {Component} from 'react'
export default class Form extends Component{
constructor (props){
super(props);
this.state = {formValue: "hello react"};
}
handleInput=(event)=>{
//target.formValue取到input的值
//这样限制用户输入的长度
this.setState({formValue: event.target.value.substr(0,10)})
}
render(){
return (
{this.state.formValue}
这是一个Controlled Components
这是一个UnControlled Components
);
}
}
可以看到Controlled Component的value是受控制的
- 使用Checkboxes 和 Radio Buttons时注意:preventDefault
Be aware that, in an attempt to normalize change handling for checkbox and radio inputs, React uses a click event in place of a change event. For the most part this behaves as expected, except when calling preventDefault
in a change handler. preventDefault stops the browser from visually updating the input, even if checked gets toggled. This can be worked around either by removing the call to preventDefault , or putting the toggle ofchecked in a setTimeout
- 非空初始值用default value:
render() { return ; }