在本教程系列的第1部分中,我们使用create-react-app
工具创建了一个工作示例应用程序,作为“ Movie Mojo”画廊应用程序的起点。
在第二部分中,我们将添加第一个自定义组件以显示单个电影卡。 我们还将看到使用道具如何允许我们通过传入数据而不是对其进行硬编码来自定义组件的外观。
这展示了组件的灵活性和可重用性,以及它们如何在React应用程序中用作强大的构建块。
我们的第一个组成部分
好,让我们创建一个组件! 首先,我们将使事情变得非常简单,并将标头HTML重构为它自己的组件。
现代React最佳实践建议将应用程序中的每个组件分离到一个单独的文件中。 我们将遵循此原则,因此,在您的项目/src/components/
文件夹中,创建一个名为Header.js
的新文件,并在文本编辑器中将其打开。
在组件文件的顶部,我们总是从导入所需的库,其他组件(因为我们可以嵌套组件)以及我们需要的其他资产(例如样式)开始。 import
声明是ES6的一部分,使我们能够保持项目高度模块化。
对于我们的<Header />
组件,我们只需要导入React库,我们可以使用以下语句执行此操作:
import React, { Component } from 'react';
这将导入整个React库,并通过React
变量使其可用。 它也直接导入Component
对象,因此我们可以使用它,而不必通过前面的React.
专门限定它React.
对象参考。
换句话说,如果我们没有显式导入Component
对象,则必须按以下方式访问它:
React.Component
但是因为我们直接导入了Component
,所以我们可以单独使用它而无需引用React
变量。 不管使用哪个,都取决于偏好。
接下来,要实际创建组件,我们扩展Component
对象以创建一个定义<Header />
组件的新类。 在import
语句之后,键入:
class Header extends Component {
}
export default App;
在这里,我们使用ES6 类作为组件容器。 类是封装描述组件所需的所有代码的好方法。
您可能还已经注意到,组件文件以export语句结尾。 如您所料,这将导出我们的组件并将其提供给我们项目中的其他文件。
至少,所有React组件都必须具有render方法,该方法返回一些标记。 这可能是HTML,其他React组件或两者的混合。
将此添加到您的组件类中:
render() {
return React.createElement( 'div', null, 'Hello there, this is a React component!' );
}
React.createElement()
方法创建一个HTML元素(在本例中为<div>
)并向其中添加一些内容。 将更改保存到Header.js
并打开App.js
要在另一个组件中使用React组件,我们首先需要将其导入,因此将其添加到App.js
顶部的import语句列表中:
import Header from './Header';
请注意,假设您不需要添加.js
文件扩展名。 另外,由于<Header />
组件与<App />
组件位于同一文件夹中,因此我们无需指定完整路径。
实际上,如果您尝试使用import Header from './components/Header';
从App.js
内部,您将收到编译错误。
现在,我们可以像任何HTML元素一样在return语句中添加<Header />
组件。 但是,有一个警告。 您只能在组件的return方法内返回一个顶级元素。
因此,这是不允许的:
render() {
return (
<div className="apples"></div>
<div className="oranges"></div>
);
}
如果要返回多个元素,则必须将它们全部包装在一个包装器元素中:
render() {
return (
<div className="fruit">
<div className="apples"></div>
<div className="oranges"></div>
</div>
);
}
因此,请确保在<div className="App">
元素内添加<Header />
组件,以避免出现错误。
class App extends Component {
render() {
return (
<div className="App">
<Header />
<div className="App-header">
<h2>Discover Your Movie Mojo!</h2>
</div>
<p className="App-intro">
Welcome to the 'Movie Mojo' React app!
</p>
</div>
);
}
}
这将导致我们的<Header />
组件被渲染。
为了完成<Header />
组件,我们将从App.js
删除以下HTML块并将其添加到Header.js
。
<div className="App-header">
<h2>Discover Your Movie Mojo!</h2>
</div>
但是,您可能已经注意到有问题。 在App.js
, <App />
组件的render方法返回的外观类似于HTML。 但是在Header.js
,只有一个对React.createElement()
调用。 这是怎么回事?
答案是JSX。 在App.js
我们使用JSX编写类似HTML的语法来定义组件输出。 将此与我们的Header.js
组件定义进行比较。
React.createElement( 'div', null, 'Hello there, this is a React component!' );
这就是我们必须在没有JSX的情况下编写React组件的方式。 实际上,实际上是在将JSX呈现给浏览器之前将其编译到其中。
您完全不需要为React组件使用JSX; 这完全取决于您。 但是您将遇到的几乎所有组件都将用JSX编写,因为它编写起来非常容易。
对于您的代码新手来说,它也具有很高的可读性。 想象一下,必须学习一个React工程,其中包含用普通JavaScript编写的数十种不同组件!
因此,在本系列教程的其余部分中,我们将JSX用于组件定义也就不足为奇了。
继续,并用我们从App.js
复制的JSX等效项替换React.createElement()
调用。 您的Header.js
文件现在应如下所示:
import React, { Component } from 'react';
class Header extends Component {
render() {
return (
<div className="App-header">
<h2>Discover Your Movie Mojo!</h2>
</div>
);
}
}
export default Header;
尽管JSX使我们在编写组件时具有更大的灵活性,但是请记住,它不是我们正在编写的实际HTML,而是它的抽象。
您可以在上面的代码片段中看到这一点。 注意,在<div>
标记中,我们使用className
而不是class
来指示要在哪里声明CSS类? 这是因为所有JSX均已编译为纯JavaScript,而class
是ES6 JavaScript中的保留字。
让我们还调整标题样式。 打开App.css
并将.App-header
CSS类编辑为:
.App-header {
background-color: steelblue;
height: 70px;
padding: 20px;
color: white;
}
这将更新标题的背景色并减小高度。
组件道具
到目前为止,我们的<Header />
组件是静态的。 即,它显示了永远不变的固定内容。 但是可以使组件成为动态的,并通过组件道具显示传递给它们的内容。 这使得组件在变得通用且可重用时突然变得更加有用。
将组件属性视为类似于HTML标签。 例如, <div>
标记可能具有id
, class
, style
等属性,这些属性使我们能够为该特定的<div>
元素分配唯一值。
我们可以对React组件做同样的事情。 假设我们不希望标题输出固定文本“ Discover Your Movie Mojo!”。 每时每刻。 如果标题可以显示任何文本会更好吗?
与HTML属性不同,我们可以随意命名组件prop。 在App.js
,将<Header />
标记更新为:
<Header text="David's Movie Mojo App!" />
然后,更新<Header />
组件以使用text
道具。
<div className="App-header">
<h2>{this.props.text}</h2>
</div>
这导致我们的标题显示在App.js
添加到text
prop的任何文本。
让我们仔细看看我们如何在Header.js
引用text
道具:
{this.props.text}
花括号只是告诉JSX我们有一些我们要评估JavaScript。 这将其与文本区分开。 如果我们不使用任何花括号,则将输出字符串文字this.props.text
,这不是我们想要的。
this
关键字引用Header
组件类,而props
是一个对象,其中包含从<Header text="David's Movie Mojo App!" />
传入的所有值<Header text="David's Movie Mojo App!" />
<Header text="David's Movie Mojo App!" />
。 在我们的例子中, props
对象仅包含一个条目,但是您可以在实践中添加任意数量的对象。
现在,我们的<Header />
组件更加通用,并且不包含硬编码的字符串。 编写React组件时,这是一个好习惯。 您使它们变得越通用,它们就越可重用。
这对于开发未来的React应用程序是个好消息,因为您可以重用以前项目中的组件,因此您不必从头开始编写所有内容。
我们在上面使用了props将固定的字符串传递到<Header />
组件中,但是props也可以将变量,函数引用和状态传递给组件。
要通过props发送变量,我们可以这样做,其中headerText
是变量:
<Header text={headerText} />
检查React组件
Chrome浏览器有一个非常有用的工具,可让您检查有关React应用程序的信息。
默认的开发人员工具仅允许您查看常规HTML元素,但是在安装了React Developer Tools扩展后,您可以浏览应用程序中的所有React组件。
安装后,打开浏览器检查器工具,然后单击新可用的React选项卡。 请注意,您可以在应用程序中看到React组件的层次结构,而不是HTML元素。 单击<App />
组件以将其选中。
选择后,有关组件的信息将显示在右侧窗口中。 <App />
组件没有任何道具,因此该窗口为空。 但是,如果选择<App />
的<Header />
组件,那么您将看到我们传入的“文本”属性。
React开发人员工具对于调试非常有用,尤其是在您开发更复杂的React应用程序时,因此习惯在更简单的应用程序上使用它们非常值得。
您还可以使用React开发人员工具检查您的应用程序状态,我们将在下一个教程中介绍它。
结论
在本教程中,您学习了如何将应用程序拆分为单独的组件以使其更具模块化。 组件属性使您可以将值传递给各个组件,类似于为HTML元素添加属性的方式。
我们还看到了如何利用新的浏览器检查器工具检查组件和道具数据。
在第3部分中,我们将状态添加到我们的应用中,以帮助我们更有效地管理数据。
翻译自: https://code.tutsplus.com/tutorials/react-crash-course-for-beginners-part-2--cms-29292