React文档(五)组件和props

时间:2022-07-04 19:19:03

组件可以让你将UI分割成独立的,可复用的模块,然后考虑将每个模块彼此隔离。
从概念上理解,组件就像js中的函数。他们接受随意的输入(被称为props)然后返回React元素来描述屏幕上应该出现什么。

函数式和类式组件

定义一个组件最简单的方法是写一个js函数:

function Welcome(props) {
return <h1>Hello, {props.name}</h1>;
}

这个函数是一个有效的React组件因为它接受一个props对象作为参数然后返回一个React元素。我们把这样的叫做函数式组件因为他们就是字面意思上js函数。

你也可以使用ES6的class来定义一个组件:

class Welcome extends React.Component {
render() {
return <h1>Hello, {this.props.name}</h1>;
}
}

从React的角度来看,以上两种方式定义的组件是一样的。

类定义这种方法有一些额外的特性我们在下一章节会讨论。在此之前,我们会使用函数来定义组件因为这样比较简洁。

渲染一个组件

先前,我们只遇到React元素代表DOM标签的情况:

const element = <div />;

然而,React元素也可以代表用户自定义组件:

const element = <Welcome name="Sara" />;

当React认为一个元素代表用户自定义组件时,它通过单个对象传递JSX属性到这个组件。我们叫这个对象为“props”。

举个例子,这段代码渲染“Hello, Sara”到页面上:

function Welcome(props) {
return <h1>Hello, {props.name}</h1>;
} const element = <Welcome name="Sara" />;
ReactDOM.render(
element,
document.getElementById('root')
);

在CodePen中试一试

让我们概括一下在这个例子中到底发生了什么:

  1. 我们调用了ReactDOM.render()来渲染<Welcome name="Sara"/>元素。
  2. React调用Welcome组件并将{name: 'Sara'}这个对象作为props传入。
  3. Welcome组件返回了一个<h1>Hello, Sara</h1>元素作为结果。
  4. React DOM高效地更新了DOM来匹配<h1>Hello, Sara</h1>。

附加说明:

总是将组件名的首字母大写。

举个例子,<div/>代表一个DOM标签,但是<Welcome />代表一个一个组件并且需要Welcome定义或引入。

组合组件

组件可以在它的输出中引用其他组件。这样我们可以使用同一个组件抽象出任意等级的细节。一个按钮,一个表单,一个目录,一个对话框,整个屏幕内容:在React应用中,所有这些都同样表示为组件。

举个例子,我们创建一个渲染Welcome组件多次的App组件:

function Welcome(props) {
return <h1>Hello, {props.name}</h1>;
} function App() {
return (
<div>
<Welcome name="Sara" />
<Welcome name="Cahal" />
<Welcome name="Edite" />
</div>
);
} ReactDOM.render(
<App />,
document.getElementById('root')
);

在CodePen中试一试

通常,新的React应用有一个单独的App组件在最顶端。然而,如果你整合React到一个已经存在的应用里,也许你会从底开始通过小组件类似Button逐渐替换一直到*别。

附加说明:

组件必须返回一个单个的根元素。这就是为什么我们添加了一个<div>去包含所有<Welcome />元素。

提取组件

不要害怕将组件分割成更小的组件。

举个例子,看看这个Comment组件:

function Comment(props) {
return (
<div className="Comment">
<div className="UserInfo">
<img className="Avatar"
src={props.author.avatarUrl}
alt={props.author.name}
/>
<div className="UserInfo-name">
{props.author.name}
</div>
</div>
<div className="Comment-text">
{props.text}
</div>
<div className="Comment-date">
{formatDate(props.date)}
</div>
</div>
);
}

在CodePen里试一试

Comment组件接受了author(一个对象),text(一个字符串)和date(一个日期对象)作为属性,它在一个社会媒体网站上描述一段评论。

这个组件可以被简化因为嵌套的东西太多,它很难被复用。让我们从这里提取出一些组件。

首先,我们将提取Avatar:

function Avatar(props) {
return (
<img className="Avatar"
src={props.user.avatarUrl}
alt={props.user.name}
/>
);
}

Avatar组件不需要知道自己将要被渲染到Comment内部。这就是为什么我们给他的属性一个更通用的名字:user而不是author。

建议在命名属性名的时候从组件自己的角度来命名而不要从使用时的上下文环境来命名。

现在可以将Comment组件简化为更小的部分:

function Comment(props) {
return (
<div className="Comment">
<div className="UserInfo">
<Avatar user={props.author} />
<div className="UserInfo-name">
{props.author.name}
</div>
</div>
<div className="Comment-text">
{props.text}
</div>
<div className="Comment-date">
{formatDate(props.date)}
</div>
</div>
);
}
接下来,我们将提取UserInfo组件,它内部渲染了一个Avatar旁边的用户名:
function UserInfo(props) {
return (
<div className="UserInfo">
<Avatar user={props.user} />
<div className="UserInfo-name">
{props.user.name}
</div>
</div>
);
}

这允许我们更进一步地简化Comment:

function Comment(props) {
return (
<div className="Comment">
<UserInfo user={props.author} />
<div className="Comment-text">
{props.text}
</div>
<div className="Comment-date">
{formatDate(props.date)}
</div>
</div>
);
}

在CodePen中试一试

提取组件也许看起来像很枯燥的工作,但是拥有一系列可复用的组件会在大型应用中起到很好的效果。有一个很好的经验法则就是如果有一部分UI已经被使用多次(如Button,Panel,Avatar),或者组件本身已经足够复杂(如APP,FeedStory,Comment),那么使它成为一个可复用的组件会更合适。

props是只读的

如果你声明了一个组件使用函数或者类,那么它永远不能修改它自己的props。看看这个sum函数:

function sum(a, b) {
return a + b;
}

这样的函数被称为“纯函数”因为它们不尝试改变它们的输入,而且在输入同样的情况下一直返回一样的结果。

相比之下,这个函数就不是纯函数因为它改变了输入:

function withdraw(account, amount) {
account.total -= amount;
}
React是很灵活的但是它有一个严格的规定:
所有React组件必须是纯粹的函数不能改变props。
当然,应用的UI是随着时间动态变化的。在下一章节,我们会介绍一个新的概念叫做“state”。state允许React组件随着时间变化去改变他们的输出作为对用户动作的响应,网络的响应或者其他东西。state并没有违反这个规定。

React文档(五)组件和props的更多相关文章

  1. React文档(十三)思考React

    在我们的看来,React是使用js创建大型快速网站应用的首要方法.它在Facebook和Instagram的使用已经为我们展现了它自己. React的一个很好的地方就在于当你创建应用的时候它使你思考如 ...

  2. 朱晔的互联网架构实践心得S1E9:架构评审一百问和设计文档五要素

    朱晔的互联网架构实践心得S1E9:架构评审一百问和设计文档五要素 [下载文本PDF进行阅读] 本文我会来说说我认为架构评审中应该看的一些点,以及我写设计文档的一些心得.助你在架构评审中过五关斩六将,助 ...

  3. DCloud-MUI:文档 UI组件

    ylbtech-DCloud-MUI:文档 UI组件 1.返回顶部 1.accordion(折叠面板) 折叠面板从二级列表中演化而来,dom结构和二级列表类似,如下: <ul class=&qu ...

  4. 一款开源免费的&period;NET文档操作组件DocX(&period;NET组件介绍之一)

    在目前的软件项目中,都会较多的使用到对文档的操作,用于记录和统计相关业务信息.由于系统自身提供了对文档的相关操作,所以在一定程度上极大的简化了软件使用者的工作量. 在.NET项目中如果用户提出了相关文 ...

  5. flexpaper 开源轻量级的在浏览器上显示各种文档的组件

    FlexPaper是一个开源轻量级的在浏览器上显示各种文档的组件,被设计用来与PDF2SWF一起使用, 使在Flex中显示PDF成为可能,而这个过程并无需PDF软件环境的支持.它可以被当做Flex的库 ...

  6. 推荐一套&period;NET文档处理组件Spire&period;Office

    原文:推荐一套.NET文档处理组件Spire.Office 以前的项目中用到一点Word简单处理的功能(文字替换和转PDF格式),当时使用的是一套COM组件,必须在服务器上安装office环境.最近考 ...

  7. GrapeCity Documents (服务端文档API组件) V3&period;0 正式发布

    近日,葡萄城GrapeCity Documents(服务端文档API组件)V3.0 正式发布! 该版本针对 Excel 文档.PDF 文档和 Word 文档的 API 全面更新,加入了用于生成 Exc ...

  8. GrapeCity Documents for Excel 文档API组件 V2&period;2 新特性介绍

    GrapeCity Documents for Excel 文档API组件 V2.2 正式发布,本次新版本包含诸多重量级产品功能,如:将带有形状的电子表格导出为 PDF.控制分页和电子表格内容.将Ex ...

  9. React文档(二十四)高阶组件

    高阶组件(HOC)是React里的高级技术为了应对重用组件的逻辑.HOCs本质上不是React API的一部分.它是从React的组合性质中显露出来的模式. 具体来说,一个高阶组件就是一个获取一个组件 ...

  10. react文档demo实现输入展示搜索结果列表

    文档页面地址:https://doc.react-china.org/docs/thinking-in-react.html 该文档只给了具体实现思路,下面是我实现的代码. 初学react,如果有写的 ...

随机推荐

  1. PS网页设计教程XXVII——设计一个大胆和充满活力的作品集

    作为编码者,美工基础是偏弱的.我们可以参考一些成熟的网页PS教程,提高自身的设计能力.套用一句话,“熟读唐诗三百首,不会作诗也会吟”. 本系列的教程来源于网上的PS教程,都是国外的,全英文的.本人尝试 ...

  2. Ubuntu 下误修改用户组导致sudo命令无效

    1.手贱地修改了当前用户的权限组,导致sudo命令无法使用,且root用户的密码尚未修改,登陆不了root用户. 2.切换到recoverymode ,使用root用户登陆 3.执行mount -o ...

  3. elasticsearch 八、重要的配置更改

    http://jingyan.baidu.com/article/7908e85c9fc626af491ad263.html

  4. Linux配置自建 YUM 软件存储库

    yum软件仓库的搭建方式有三种,分别是本地yum源,网络yum源,第三方软件仓库. 以下示例演示了搭建本地yum仓库的方法: 1. 删除 /etc/yum.repos.d/dvd.repo 这个仓库文 ...

  5. SQLite入门与分析&lpar;八&rpar;---存储模型&lpar;3&rpar;

    写在前面:接上一节,本节主要讨论索引页面格式,以及索引与查询优化的关系. (1)索引页面格式sqlite> select * from sqlite_master;table|episodes| ...

  6. 给当前的URL添加&sol;更新新的参数

    /** * 给当前的URL添加/更新新的参数 * @param a 参数 * @param b 值 * @returns {string} 新的参数 * @constructor */ functio ...

  7. JAVA语言中冒号的用法

    近来由于本人要介入android平台的开发,所以就买了本JAVA语言的书学习.学习一段时间来,我的感觉是谭浩强就是厉害,编写的<C编程语言>系列丛书不愧是经典.书中对C语言的介绍既系统又全 ...

  8. android项目架构 -----Android 知识体系与常用第三方框架

    好东西值得分享 ,这是网络上总结的一些开源的东西直接就拿过来了  .... Android通用流行框架大全 先把这张图放在这 ,先来谈一谈项目结构 .我喜欢将东西按模块来划分: 都知道module . ...

  9. perl 函数

    文档 函数参数 sub hello{ $len = @args = @_; print "hello @args\n"; } hello('ajanuw', 'alone'); # ...

  10. Oracle用户权限及死锁

    Oracle用户权限表 oracle数据库中涉及到用户权限的三个表,dba_users,all_users,user_users有什么区别 dba_开头的是查全库所有的,all_开头的是查当前用户可以 ...