前端(八):react入门
React 特点:声明式设计、虚拟DOM、JSX、组件、数据驱动。
一、环境搭建
1.安装npm、cnpm
# 安装node.js 从而安装npm,它会在当前用户家目录下生成node_moudules文件夹,来对npm安装的全局第三方包进行管理
brew install node
# npm安装cnpm,因为npm默认的库下载速度太慢,所以建议使用cnpm指定淘宝库
npm install -g cnpm --registry=https://registry.npm.taobao.org
npm config set registry https://registry.npm.taobao.org # 测试
cnpm install express -g
2.安装react全家桶
# 安装create-react-app
cnpm install create-react-app -g
# 利用create-react-app 来创建一个项目
create-react-app 项目名称 # 假设这里的项目名称是my-app
# 进入项目文件夹
cd my-app
# 生成配置文件
# cnpm run eject # 生成scripts文件夹和config文件夹,cnpm
# 启动服务
cnpm start # 它相当于执行 scrpits/starts.js,这个已经在package.json中配置好了
3.文件目录结构
my-app
- config # 项目默认配置文件,由npm run eject生成
- .gitignore # git配置
- node_modules # 本地第三方安装包
- package.json # npm项目配置,里面记录了项目的名字、版本、依赖包、和自定义配置
- package-lock.json
- public # 公共资源
- index.html # 静态页面
- README.md
- scripts # 配置pacakage.json中的"scripts"定义的命令
- build.js # build命令,可由npm build执行,生成静态文件用于迁移到生产环境
- start.js # start命令
- test.js
- src
- App.css # 创建项目时自动生成的css样式,没用
- App.js # react组件
- App.test.js
- index.css # 入口文件的样式
- index.js # 入口文件
- log.svg
- registerServiceWorker.js
项目启动时,会加载public下的index.html文件,并进而执行index.js,从而完成整个页面的渲染。
二、react一些概念
<!--public/index.html简化如下-->
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
<meta name="theme-color" content="#000000">
<title>React App</title>
<style>
body {
margin: 0;
padding: 0;
}
</style>
</head>
<body>
<div id="root"></div>
</body>
</html>
react简单示例只保留简化后的public/index.html和src/index.js
1.React.Component
React.Component是自定义组件的父类,必须重写render方法来完成组件的声明和返回。所谓组件,就是用js类定义的一组html标签、样式、数据、事件等的整合,该类可以用<类名 />的方式进行标签化(实例化),实例化时自动调用render方法,并最终交由React.render完成渲染。
一张网页就可以分割成多个组件,每个组件自己实现标签、样式、数据交互和用户交互。也就是说,网页是由多个组件堆砌而成的,每个组件都必须继承React.Component来实现并返回自己的定制化。显然地,组件既包含一个div标签组,本身也是一个类,它具有双重角色。
一个继承了React.Component的组件,通过render返回一个组件对象。经验上谈,一个子类的某个固定方法极有可能是其父类方法(或接口)的重写(实现),而往往这个方法会在程序运行时被自动调用。因此,render方法是重写了React.Component,在程序启动时被自动执行,挂载到网页的某个节点上。
import React, {Component, Fragment} from "react"; class Boom extends Component{
render() {
return (
<Fragment>
<div>
<input /><button>提交</button>
</div>
<ul>
<li>what the hell?</li>
<li>你瞅啥子</li>
</ul>
</Fragment>
)
}
} export default Boom;
2.ReactDOM.render
index.js中的ReactDOM.render函数用于将标签或者组件渲染到public下的页面中。第一个参数可以是任意的单个标签、div包裹的多个标签,以及自定义的组件Component。
ReactDOM.render用于将组件挂载到某个标签上。比如html中某个id为root的div标签上。简单粗暴:一个包含了西瓜瓤、西瓜籽、西瓜皮的西瓜挂在了西瓜藤上。
3.React JSX
用于编译jsx语法。React.Component和ReactDOM.render中的标签都使用了jsx语法,所以必须使用React进行编译。JSX看起来像是急于XML的javascript的扩展。它编写简单并且执行更快,同时也是类型安全的,在编译过程中就能发展错误。
经验之谈:如果一个标签的首字母时大写,那么它就遵循JSX语法,如果一个标签的首字母小写,那么它就是原始html标签(但这个标签有可能是按照jsx语法编译的)。
JSX允许在一对{}中写js代码,例如:
{
/*
遍历list生成li标签,并给每个li标签添加删除功能
/
this.state.list.map(
(item, index) => {
return <li
key={index}
onClick={(index)=>{this.handleLiDelete(index)}}
> { item }</li>
}
)
}
4.组件内部参数声明和使用
组件内部可以声明参数,无论是textNode还是其它Node,都是以 { 参数 } 的形式被组件调用。组件react虚拟DOM的具体实现方式,它来完成对页面和业务逻辑的划分。
// src/index.js
import React from 'react';
import ReactDOM from 'react-dom'; class App extends React.Component{
render (){
const string = "hello, react!";
const style1 = {
color: "white"
};
const style2 = {
textAlign:"center",
fontStyle: "border",
backgroundColor: "green"
};
return (
<div style={style1}>
{/*这是一段注释*/}
<h2 style={style2}>{ string }</h2>
</div>
)
}
} ReactDOM.render(<div>
<h2>hello, react!</h2>
<App />
</div>, document.getElementById('root'));
组件间可以实现嵌套。
import React from 'react';
import ReactDOM from 'react-dom'; class App extends React.Component{
render (){
return <h2>这是子组件</h2>
}
}
class App2 extends React.Component{
render (){
const style = {
backgroundColor: "blue"
};
return (
<div style={style}>
<h2>这是父组件</h2>
<App />
</div>
)
}
} ReactDOM.render(<App2 />, document.getElementById('root'));
5.静态数据传递--props
组件间数据通过this.props属性来进行数据传递。父组件在标签化时通过属性的方式传递数据,子组件通过this.props来获取所有的数据。
import React from 'react';
import ReactDOM from 'react-dom'; class App extends React.Component{
render (){
return <h2>App: { this.props.name }, { this.props.age }</h2>
}
}
class App2 extends React.Component{
render (){
const name = "Sun", age=5000; return (
<div>
<h2>App2: { this.props.name }, { this.props.age }</h2>
<App name={name} age={age} />
</div>
)
}
}
ReactDOM.render(<App2 name="Li" age="20" />, document.getElementById('root'));
注意:1.props只能传递静态数据,无法与用户交互;2.{}不是Object对象,如果想写<App2 obj={name: "Li", age: 20} />,就必须提前声明。3.style样式作为数据传递是无效且荒谬的。
const obj = {name: "Li",age: 20};
<App2 obj={obj}/>
6.动态数据交互--state
React是一个响应式框架,它将数据和dom分开,能够根据数据的变化自动更新dom。再次强调:React.Component具有双重属性:组件(dom)属性和js类属性(类:数据封装)。
state用于负责处理动态数据。数据需要在构造函数中通过this.state事先声明,并在事件中通过this.setSate完成数据更新。
import React from 'react';
import ReactDOM from 'react-dom'; class App extends React.Component{
constructor(props){
super(props);
this.state = {
nameList:["Sun", "Li", "Zhao", "Qian"]
}
}
addPerson(){
this.setState({
nameList: [...this.state.nameList, "zhou"]
})
}
render (){
return (
<div>
<button onClick={()=>this.addPerson()}>加入周先生</button>
<ul>
{this.state.nameList.map((name, index) => <li key={index+1}>{name}</li>)}
</ul>
</div> )
}
}
ReactDOM.render(<App />, document.getElementById('root'));
7.事件绑定
在react中,事件以属性的方式直接在标签中使用,其调用函数要用一层函数包裹。调用函数可以直接写在对象内部,并且要用bind进行监听和更新。
在上面的示例中,我们通过这一行代码代替了bind的过程:
<button onClick={()=>this.addPerson()}>加入周先生</button>
鉴于js中没有局部作用域只有函数作用域,所以如果直接写onClick={this.addPerson}时,this指的就是window对象。用一层函数包裹时,this对象指的就是这个函数。
其它的做法有两种:
首先,在事件绑定时直接使用this.function:
<button onClick={this.addPerson}>加入周先生</button>
其次可以用箭头函数来声明addPerson函数,本质上和上面使用的方法一样:
addPerson = ()=>{
this.setState({
nameList: [...this.state.nameList, "zhou"]
})
};
或者可以不改addPersonn函数,而是在构造器中添加上这么一句话:
this.addPerson = this.addPerson.bind(this)
一个示例:
import React, {Component, Fragment} from "react"; class Boom extends Component{
constructor(props){
super(props);
this.state = {
inputValue: "",
list: []
}
}
handleInputChange(e){
this.setState({
inputValue: e.target.value
});
}
handleBtnClick(){
this.setState({
list:[...this.state.list, this.state.inputValue],
inputValue: "" // 在提交时自动清空输入框里的内容
})
} handleLiDelete(index){
const list = [...this.state.list]; // 只能通过setState修改数据,所以不要写成this.state.list.splice(index, 1);
list.splice(index, 1);
this.setState({
list: list
});
}
render() {
return (
<Fragment>
<div>
<input
value={ this.state.inputValue }
onChange={this.handleInputChange.bind(this)}
/>
<button onClick={()=>this.handleBtnClick()}>提交一个句子</button>
</div>
<ul>
{
this.state.list.map(
(item, index) => {
return <li
key={index}
onClick={(index)=>{this.handleLiDelete(index)}}
> { item }</li>
}
)
}
</ul>
</Fragment>
)
}
} export default Boom;
8.条件渲染
render本身是一个实例方法,支持js中的各种代码逻辑。可以用if-else来控制返回结果。条件渲染在用户登录和重定向中使用的比较频繁。
// src/index.js
import React from 'react';
import ReactDOM from 'react-dom'; class App extends React.Component{
constructor(props){
super(props);
this.state = {isLogIn: false} }
login (){
this.setState({isLogIn: true})
};
logout(){
this.setState({isLogIn: false})
}
render (){
let button=null;
if (this.state.isLogIn){
button = <button onClick={()=>this.logout()}>注销</button>
}else {
button = <button onClick={()=>this.login()}>登录</button>
}
return button
}
}
ReactDOM.render(<App />, document.getElementById('root'));
也可以用三元表达式简写:
render (){
return (
<div>
{this.state.isLogIn ? <button onClick={()=>this.logout()}>注销</button> : <button onClick={()=>this.login()}>登录</button>}
</div>
)
}
注意:由于{}传递的数据可以是任意值,所以需要用div包裹。
前端(八):react入门的更多相关文章
- 2015年最热门前端框架React 入门实例教程
现在最热门的前端框架,毫无疑问是 React . 上周,基于 React 的 React Native 发布,结果一天之内,就获得了 5000 颗星,受瞩目程度可见一斑. React 起源于 Face ...
- 不会几个框架,都不好意思说搞过前端: React 入门实例教程
现在最热门的前端框架,毫无疑问是 React . 上周,基于 React 的 React Native 发布,结果一天之内,就获得了 5000 颗星,受瞩目程度可见一斑. React 起源于 Face ...
- 前端框架React入门课程【视频】
视频教程列表: http://v1.mukewang.com/1a8228ac-5f7f-48de-b1c5-7d1b8bce9c77/L.mp4 1-1 React入门课程介绍 http://v1. ...
- 前端框架React Js入门教程【精】
现在最热门的前端框架有AngularJS.React.Bootstrap等.自从接触了ReactJS,ReactJs的虚拟DOM(Virtual DOM)和组件化的开发深深的吸引了我,下面来跟我一起领 ...
- React 入门实例教程
现在最热门的前端框架,毫无疑问是 React . 上周,基于 React 的 React Native 发布,结果一天之内,就获得了 5000 颗星,受瞩目程度可见一斑. React 起源于 Face ...
- react 入门教程 阮一峰老师真的是榜样
- 转自阮一峰老师博客 React 入门实例教程 作者: 阮一峰 日期: 2015年3月31日 现在最热门的前端框架,毫无疑问是 React . 上周,基于 React 的 React Nati ...
- React入门实例教程
文章转自:阮一峰 现在最热门的前端框架,毫无疑问是 React . 上周,基于 React 的 React Native 发布,结果一天之内,就获得了 5000 颗星,受瞩目程度可见一斑. React ...
- React 入门实例教程(转载)
现在最热门的前端框架,毫无疑问是 React . 上周,基于 React 的 React Native 发布,结果一天之内,就获得了 5000 颗星,受瞩目程度可见一斑. React 起源于 Face ...
- 【转】react入门实例教程
作者: 阮一峰 日期: 2015年3月31日 写在前面:原文链接http://www.ruanyifeng.com/blog/2015/03/react.html github地址https:/ ...
- React 入门实例教程【转】
Any day will do. 哪一天都行 Are you kidding? 你在开玩笑吧! Congratulations! 祝贺你! I don’t mean it. 我不是故意的. 原文作者: ...
随机推荐
- js简单正则表达式验证密码
包含3种及以上 var reg = new RegExp("^(?![A-Za-z]+$)(?![A-Z\\d]+$)(?![A-Z\\W]+$)(?![a-z\\d]+$)(?![a-z\ ...
- placeholder插件详解
placeholder插件是用来实现input或者textarea文本框显示默认文字的功能,当获得焦点时,默认文字消失.用户按删除键,把输入的字符删除掉,并失去焦点时,默认文字又出现等功能.使用此插件 ...
- ansible api2.0 多进程执行不同的playbook
自动化运维工具:ansible 多进程调用ansible api的应用场景: 应用系统检查 一个应用系统可能具有20—50台服务器的集群,初步的系统层面检查可以用一个统一的playbook来检查, ...
- css中代码格式以及@import的语法结构
CSS中代码格式 CSS是Cascading Style Sheets(层叠样式表)的缩写.是一种对web文档添加样式的简单机制,属于表现层的布局语言. 1.基本语法规范分析一个典型CSS的语句: p ...
- 架构师养成记--29.redis开篇
主要有从下几点讲解 NOSQL(Redis) 简介.redis安装与部署 Redis基础事件类型详解 Redis高级命令 Redis与java的使用 Redis集群搭建 Redis集群与spring的 ...
- Webpack学习错误解决笔记
错误1:在用npm install 安装模块时,时常会出现没有以下类似的错误 解决方法:右键点击node_modules文件夹,选取属性,将文件夹只读选项去除 错误2:在学习到清理/dist文件夹这块 ...
- mysql启动不起来
在刚编译安装完成mysql,启动mysql时报了下面错误: /etc/init.d/mysqld start Starting MySQL... ERROR! The server quit with ...
- winform两个窗体之间传值(C#委托事件实现)
委托 定义一个委托,声明一个委托变量,然后让变量去做方法应该做的事. 委托是一个类型 事件是委托变量实现的 经典例子:两个winform窗体传值 定义两个窗体:form1和form2 form1上有一 ...
- centos 7 网站前端中文乱码分析、解决办法
2019-03-28 1.网站前端中文文字乱码主要原因有两点: (1)mysql数据库内部存储的数据本身处于乱码状态 (2)前端与数据库传输数据的字符集与数据库内部字符集不一致导致 2.查找造成中文乱 ...
- c# Equals方法
很多C#的教材都会强调对象相等的概念.我们都知道,在C#的世界里存在两种等同性.一种是逻辑等同性:如果两个对象在逻辑上代表同样的值,则称他们具有逻辑等同性.另一种是引用等同性:如果两个引用指向同一个对 ...