p,pre,span,code,div { font-size: 16px }
一、JSX in Depth
1.1 choosing the type at runtime
import React from ‘react‘; import { PhotoStory, VideoStory } from ‘./stories‘; const components = { photo: PhotoStory, video: VideoStory }; function Story(props) { // Wrong! JSX type can‘t be an expression. return <components[props.storyType] story={props.story} />; }
为了解决这个问题,我们将其赋值给首字母大写的变量
import React from ‘react‘; import { PhotoStory, VideoStory } from ‘./stories‘; const components = { photo: PhotoStory, video: VideoStory }; function Story(props) { // Correct! JSX type can be a capitalized variable. const SpecificStory = components[props.storyType]; return <SpecificStory story={props.story} />; }
1.2 props in JSX
有多种方法指定JSX的props属性
1)JS表达式
可以传递任何大括号包裹的JS表达式作为props。
<MyComponent foo={1 + 2 + 3 + 4} />
对于MyComponent组件,props.foo属性等于10. if语句和for循环不是JS表达式,因此不能直接用于JSX。
2)字符串
可以传递一个字符串作为prop,因此下面的两条语句是等价的。
<MyComponent message="hello world" /> <MyComponent message={‘hello world‘} />
3)prop默认为true
下面两种表述是等价的
<MyTextBox autocomplete /> <MyTextBox autocomplete={true} />
4)扩展运算符
展开对象的形式,使用...+对象名,React自动看成是多个属性名
var props={ one:‘123‘, two:321 } <HelloWorld {...props}/>
1.3 children in JSX
在拥有开闭标签的JSX表达式中,开闭标签之间的内容传递给了props.children属性,有多种不同的方法来传递children。
1)字符串
开闭标签之间可以是字符串,因此props.children就是这个字符串
<MyComponent>Hello world!</MyComponent>
在这里props.children=Hello world!
JSX会移除空格,因此下面的几种表述是等价的:
<div>Hello World</div> <div> Hello World </div> <div> Hello World </div> <div> Hello World </div>
2)JSX children
你也可以提供更多的JSX元素作为children,这在嵌套组件中很有用:
<MyContainer> <MyFirstComponent /> <MySecondComponent /> </MyContainer>
你可以混合不同类型的children,因此你可以混合使用字符串和JSX children
<div> Here is a list: <ul> <li>Item 1</li> <li>Item 2</li> </ul> </div>
3)javascript children
可以使用任何大括号括起来的JS表达式作为children,比如下面这两种表述是相同的
<MyComponent>foo</MyComponent> <MyComponent>{‘foo‘}</MyComponent>
这通常用于呈现JSX任意长度列表,比如下面这种呈现一个HTML列表
function Item(props) { return <li>{props.message}</li>; } function TodoList() { const todos = [‘finish doc‘, ‘submit pr‘, ‘nag dan to review‘]; return ( <ul> {todos.map((message) => <Item key={message} message={message} />)} </ul> ); }
JS表达式还可以跟其他类型的children一起混用,这通常用于字符串模板
function Hello(props) { return <div>Hello {props.addressee}!</div>; }
4)函数
props.children可以传递任何数据,比如你有一个custom组件,你可以使用一个回调函数作为props.children.
function ListOfTenThings() { return ( <Repeat numTimes={10}> {(index) => <div key={index}>This is item {index} in the list</div>} </Repeat> ); } // Calls the children callback numTimes to produce a repeated component function Repeat(props) { let items = []; for (let i = 0; i < props.numTimes; i++) { items.push(props.children(i)); } return <div>{items}</div>; }
5)booleans,null,undefined are ignored
false,true,null,undefined都是合法的children,他们只是不渲染,下面这些表达式将渲染成同样的
<div /> <div></div> <div>{false}</div> <div>{null}</div> <div>{true}</div>
当需要有条件的渲染某个react组件时,这是很有用的,
<div> {showHeader && <Header />} <Content /> </div>