目录

1.react基础:类组件、函数式组件、ES5/ES6继承

在创建一个vue项目的时候,

1.在index.js文件中引入react模块,引入在需要的节点所需要的组件
import React from 'react'; // 必须要引入的模块
import ReactDOM from 'react-dom'; // 给某一个DOM节点渲染时用到,它是从react中分离出来的 import App from '@/components/App'; // React的一个组件 // 将虚拟的组件渲染到视图中
// 组件名字必须是大写,如果是小写的话它会认为是html标签,组件的文件名也建议大写
ReactDom.render ( // render是一个钩子函数
<APP />,
document.getElementById('root') //表示的是组件放到哪个节点中
) 2.在components文件夹下,编写组件App.jsx
import React from 'react'
/**
在react中开发组件模式:
> ES6 class类写法 类组件
> ES6 箭头函数写法 函数式组件 ----无状态组件
*/
// return() ()内部的代码写的是虚拟Dom,符合jsx语法
//class 类:
class App extends React.Component {
render () {
return (
<div>hello react</div>
)
}
}
export default App; // 函数式组件
const App = () => {
return (
<div> hello function</div>
)
} 如何选择类组件还是函数式组件?
如果一个组件需要有状态,那么一定不要写函数式组件,函数式组件又会被成为 无状态组件,函数式组件一般会使用为UI组件(只负责渲染视图,数据都来源于父组件)---- 在react16.8的时候要注意一下(有另一种说法)
  • ES5 的继承,实质是先创造子类的实例对象this,然后再将父类的方法添加到this上面(Parent.apply(this))。
  • ES6 的继承机制完全不同,实质是先将父类实例对象的属性和方法,加到this上面(所以必须先调用super方法),然后再用子类的构造函数修改this。

子类必须在constructor方法中调用super方法,否则新建实例时会报错。这是因为子类自己的this对象,必须先通过父类的构造函数完成塑造,得到与父类同样的实例属性和方法,然后再对其进行加工,加上子类自己的实例属性和方法。如果不调用super方法,子类就得不到this对象。

2.生命周期钩子函数

React的生命周期的钩子函数

挂载时 ---------- 初始化阶段
  • constructor() -------声明属性
  • componentWillMount() --------即将挂载组件
  • render() --------初次渲染数据
  • componentDidMount() ----------组件挂载完毕,可以在此处进行请求数据
更新时 ---------运行时阶段
  • componenttWillReceiveProps(nextProps) --------将接收到组件的数据
  • shouldComponentUpdate() ------------- 当state或者props发生改变时,组件是否更新,默认更新,返回值为布尔类型
  • componentWillUpdate() ------------组件即将更新
  • render() -------------组件更新
  • componentDidUpdate() ----------------组件更新完毕,dom操作
卸载时 ---------销毁阶段
  • componentWillUnmount() -------------组件销毁---定时器、计数器等
错误处理
  • componentDidCatch() --------当react组件数出现错误时执行

常用的react的生命周期钩子函数

constructor() 通过给 this.state 赋值对象来初始化内部 state。为事件处理函数绑定实例

render() 只要是组件就必须有的

componentDidMount() 如果需要请求数据,如果需要DOM操作,实例化操作

componentDidUpdate() 如果需要DOM操作,实例化操作

componentWillUnmount() 如果需要清除定时器,计时器,实例对象

3.什么是JSX

jsx它既不是一个字符串也不是一个HTML,是javascript的语法拓展。jsx可以生成react中的元素,组件就是由元素组成的。
jsx的特性属性,在属性中嵌入javascript代码时,在大括号外面不用加引号
jsx可以防止javascript脚本攻击,因为在渲染的时候,它会先将代码转化成字符串。

4.props和state有什么区别

props是只读的,它用在组件与组件之间
可以把props理解为从外部传入组件内部的数据。由于React是单向数据流,所以props基本上也就是从服父级组件向子组件传递的数据。
state可读可写,它用在组件内
它就是数据的状态
  1. state是组件自己管理数据,控制自己的状态,可变;
  2. props是外部传入的数据参数,不可变;
  3. 没有state的叫做无状态组件,有state的叫做有状态组件;
  4. 多用props,少用state。也就是多写无状态组件。

5.路由配置

项目目录树:入口找布局,布局找页面,页面找的是组件,组价中可以找子组件

  1. 在入口文件中配置路由

    import { BrowserRouter as Router, Switch, Route } from react-router-dom
    import App from '@/layout/App'
    import Detail from '@/layout/Detail' <Router>
    <Switch>
    <Route path="/detail" component={ Detail } />
    <Route path="/" component={ App } />
    </Switch>
    </Router>
  2. 在布局文件中配置路由:带参数

    <Switch>
    <Route path="/detail/order" component={ Order }/>
    <Route path="/detail/:id" component={ Detail }/>
    </Switch>
  3. 在布局文件中配置路由:不带参数

    import Home from '@/view/Home'
    import Kind from '@/view/Kind'
    import Cart from '@/view/Cart'
    import User from '@/view/User'
    import { Route, Switch, NavLink, Redirect } from 'react-router-dom' <Switch>
    <Route path= '/home' component={ Home } />
    <Route path= '/kind' component={ Kind } />
    <Route path= '/cart' component={ Cart } />
    <Route path= '/user' component={ User } />
    <Redirect to ='/home' /> //重定向
    </Switch> <NavLink to="/home"><NavLink> //点击跳转,如果有样式变化用NavLink
    //<Link to={ "/detail/id=" + item.id }><Link> //没有样式变化的跳转,用Link

注:路由的查找是从上到下的,所以path = "/"一定要放在最下面,否则就直接进入path = "/"页面,找不到path="/detail" 页面

布局文件不写具体页面,子组件数据由页面传递,所以子组件中可以用函数式组件

注:详情页跳转时path="/detail/:id"

  1. 重定向和404页面

    import NoMatch from '@/view/NoMatch';
    <Redirect exact from = '/' to ='/home' /> //exact表示只有“/”才能重定向到“/home”
    <Route component = { NoMatch } />

6.自定义封住组件

1.利用{...this.props}将父组件中的值传递到子组件中,在子组件中{ }使用

2.结合类似vue的插槽完成自定中介部分的内容

封装Header组件

//<Header>组件
import React from 'react' export default (props) => {
console.log(props)
const { left, right, content, onLeft, onRight } = props //从父组件中传过来的值
return (
<ul>
<li onClick = { () => {
if(props.match.path === '/home') {
return
}
props.history.goBack()
// onLeft()
}
}>
{left}
</li>
<li>{props.children? props.children : content? content : ''}</li>
<li onClick = { () => {
onRight()
}}>{right}</li>
</ul>
)
}
//父组件中引用子组件的地方
<Header
left = "返回"
content = "搜索"
right = "扫一扫"
onLeft = {() => {
// this.props.history.goBack()
console.log('返回')
}}
onRight = { () => {
console.log('扫一扫')
}}
{...this.props}
>
<div className="seach">请输入搜索的内容</div>
</Header>
7.引入移动端react ant-design-mobile UI库‘’
  1. 安装 ant UI库文件

    cnpm i antd-mobile -S
  2. 在index页面中引入文件(引入 Promise 的 fallback 支持 (部分安卓手机不支持 Promise))

    将此段代码直接替换
    <meta name="viewport" content="width=device-width, initial-scale=1" />
    替换为:
    <meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1, minimum-scale=1, user-scalable=no" />
    <script src="https://as.alipayobjects.com/g/component/fastclick/1.0.6/fastclick.js"></script>
    <script>
    if ('addEventListener' in document) {
    document.addEventListener('DOMContentLoaded', function() {
    FastClick.attach(document.body);
    }, false);
    }
    if(!window.Promise) {
    document.writeln('<script src="https://as.alipayobjects.com/g/component/es6-promise/3.2.2/es6-promise.min.js"'+'>'+'<'+'/'+'script>');
    }
    </script>
  3. 在config/webpack.config.js中添加UI库的配置。(由于我们用到是react脚手架将config独立出来了,没有babel-plugin-文件)

    npm i babel-plugin-import -D
    在第357行,粘贴
    ["import", { libraryName: "antd-mobile", style: "css" }] // `style: true` 会加载 less 文件
  4. 基本配置完成,接下来需要哪个组件引入即可

7.React 状态管理器

1.Redux:(最基本的写法)

ReduX并不独属于React,他是js的状态管理容器,在vue中也能用,只是在react中用起来更好,react-redux是属于react的

在store.js页面中 -》 index.js页面引入store监听事件 -》在App页面disptch触发事件改变store中的值

//在store->index.js文件中配置状态管理器
import { creatStore } from 'redux'; const reducer = (state = {
bannerlist: [],
prolist:[]
},action) => {
const { type, data } = action;
switch (type) {
case 'CHANGE_BANNER_LIST': return Object.assign({}, state, {bannerlist:data})
case 'CHANGE_PRO_LIST': return Object.assign({}, state, { prolist: data })
default:
return state;
}
} const store = creatStore(reducer); export default store;
//在index.js入口文件中监听状态管理器的变化
import React from 'react'
import ReactDOM from 'react-dom' import App from './App'
import store from './store' function renderFn(){
ReactDOM.render(
<App />,
document.getElementById('root')
)
} renderFn(); // 如果检测到状态管理器中有变化触发
store.subscribe(renderFn)
//在需要使用状态管理器数据的页面中(App.jsx)请求数据,改变状态状态管理器中的数据
import React, { Component } from 'react';
import axios from 'axios';
import store from './store' export default class extends Component {
componentDidMount () {
axios.get('https://www.daxunxun.com/banner').then(res => {
console.log(res.data,'data');
console.log(store,'store');
store.dispatch({
type: 'CHANGE_BANNER_LIST',
data: res.data
})
})
axios.get('https://www.daxunxun.com/douban').then(res => {
store.dispatch({
type: 'CHANGE_PRO_LIST',
data: res.data
})
})
}
render () {
console.log(store.getState(),'getState')
const { bannerlist, prolist } = store.getState();
return (
<div>
<h1>状态管理器</h1>
<ul>
{
prolist.map(item => (
<li key = { item.id }>
{ item.title }
</li>
))
}
</ul>
</div>
)
}
}
2.redux + react-redux:(把一个组件拆分成了 容器组件 和 UI组件)

容器组件只负责业务逻辑的处理,

UI组件只负责数据的渲染

将App.jsx文件拆分成App.jsx和UI.jsx,前者负责写业务逻辑,后者负责渲染数据

//在index.js入口文件中改为
ReactDOM.render(
<Provider store = { store }>
<App />
</Provider>,
document.getElementById('root')
)
//在App.jsx中写业务 逻辑
import { connect } from 'react-redux'
import axios from 'axios';
import UI from './UI' // ui组件需要的状态
const mapStateToProps = (state) => {
return {
bannerlist: state.bannerlist,
prolist: state.prolist
}
} // ui组件的业务逻辑
const mapDispatchToProps = (dispatch) => {
return {
getBannerlist () {
axios.get('https://www.daxunxun.com/banner').then(res =>{
dispatch({
type: 'CHANGE_BANNER_LIST',
data: res.data
})
})
},
getProlist () {
axios.get('https://www.daxunxun.com/douban').then(res => {
dispatch({
type: 'CHANGE_BANNER_LIST',
data: res.data
})
})
}
}
} const App = connect(mapStateToProps, mapDispatchToProps)(UI) export default App;
//在UI组件中渲染数据
import React, { Component } from 'react'; export default class extends Component {
componentDidMount () {
this.props.getBannerlist();
this.props.getProlist();
}
render () {
// console.log(store.getState(),'getState')
const { bannerlist, prolist } = this.props;
return (
<div>
<h1>状态管理器</h1>
<ul>
{
prolist.map(item => (
<li key = { item.id }>
{ item.title }
</li>
))
}
</ul>
</div>
)
}
}
3.redux+ react-redux + react-thunk

将状态管理器拆分到每个页面,然后在store->index文件中配置,单独创建一个action文件,将异步请求数据单拎出来。

// action页面写异步请求
import axios from 'axios'; export default {
getBannerlist (dispatch) {
axios.get('https://www.daxunxun.com/banner').then(res => {
dispatch({
type: 'CHANGE_BANNER_LIST',
data: res.data
})
})
}

//状态管理器的入口文件
import { createStore, combineReducers, applyMiddleware } from 'redux';
import thunk from 'redux-thunk';
import home from './home'
import kind from './kind' const reducer = combineReducers({
home,
kind
})
// applyMiddleware 函数的作用就是对 store.dispatch 方法进行增强和改造,使得在发出 Action 和执行 Reducer 之间添加其他功能。
//引入thunk插件后,我们可以在actionCreators内部编写逻辑,处理请求结果。而不只是单纯的返回一个action对象。
const store = createStore(reducer, applyMiddleware(thunk)); export default store;
//状态管理器单个页面
const reducer = (state = {
bannerlist: [],
prolist: []
}, action) => {
const { type, data } = action;
switch (type) {
case 'CHANGE_BANNER_LIST':
return Object.assign({}, state, {bannerlist: data});
case 'CHANGE_PRO_LIST':
return Object.assign({}, state, {prolist: data});
default:
return state;
}
} export default reducer;

8.利用脚手架创建一个React项目

1.安装脚手架并且创建项目

cnpm / npm i create-react-app -g

create-react-app myapp

使用npx直接创建项目

npx是一种在npm中安装工具,也可以被单独的下载使用

在npm 5.2.0 的时候发现会买一送一,自动安装了npx。

npx create-react-app myapp

(npm 的版本必须在5.2.0以上)

2.修改配置文件、安装依赖

运行 npm run eject 抽离配置文件

修改package.json ,配置dev指令

配置src文件夹的别名 @

cnpm i node-sass -D

cnpm i react-router-dom@4 redux react-redux redux-thunk axios antd-mobile -S

在src下面创建main.scss在首页中引入

3.配置入口文件index.js

引入路由文件 import { BrowserRouter as Router, Switch, Route } from 'react-router-dom';

引入状态管理器文件 import store from './store';

配置文件 import { Provider } from 'react-redux';

全局引入组件库css文件 import 'antd-mobile/dist/antd-mobile.css';

坑点:

1.console.log()打印了2次内容

如果在render中使用console.log,由于react的生命周期中,在其初始化阶段会执行一次render初次渲染,在运行时阶段执行一次render渲染数据,所以会执行2次,也就打印了2次。

2.props提供的语法糖,可以将父组件中的所有属性复制给子组件。

{ ...this.props } 将父组件的路由信息传给组件。 this.props主要包含:history属性、location属性、match属性

3.为啥写重定向和404页面在布局文件中?

因为当我们输入网址的时候,它默认匹配“/”进入布局页面,如果你网址不对不算进入此项目,输入正确的地址后即进入项目,默认“/”进入布局页面,进入布局页面我们把它重定向到“/home”作为首页,如果输入其他匹配不到的就404页面。其他布局页面不用写,因为我们进入首页后,其他页面都是通过页面间跳转的,不需要手动在网址上输入。

React笔记1的更多相关文章

  1. React笔记_(3)_react语法2

    React笔记_(3)_react语法2 state和refs props就是在render渲染时,向组件内传递的变量,这个传递是单向的,只能继承下来读取. 如何进行双向传递呢? state (状态机 ...

  2. React笔记整理

    大概大半年时间都在用react写项目,一直在笔记上零零星星地记录着,在新的一年即将到来之际,打算整理整理发出来. 一.React是什么? React是Facebook开源的用于构建用户界面的javas ...

  3. react笔记汇总

    1.什么是React? a.React 是一个用于构建用户界面的 JAVASCRIPT 库. b.React主要用于构建UI,很多人认为 React 是 MVC 中的 V. c.React 起源于 F ...

  4. React笔记_(7)_react路由

    路由 路由(routing)是指分组从源到目的地时,决定端到端路径的网络范围的进程. 路由器当然是作为一个转发设备出现的,主要是转发数据包来实现网络互联. 那么react的路由到底指的是什么呢? 举个 ...

  5. React笔记_(6)_react语法5

    react的版本 目前主要的react有 ES5,ES6.也有ES5和ES6混合编写的.比较混乱. react官方提倡用ES6. 说到这里,就需要提到一个概念--mixin mixin在es6中被摒弃 ...

  6. React笔记_(5)_react语法4

    ajax 数据应用场景 在真实的开发环境中,拿到了产品需求,第一件事不是逼着后台开发人员先完成,然后前端再介入开发,这样太浪费时间. 正确的做法是跟后端人员先商量好接口名称,请求参数,返回的数据格式等 ...

  7. React笔记_(4)_react语法3

    生命周期 很多语言中都讲了关于生命周期.这可是决定生命的周始,有没有存在感的关键啊. 生命周期,有生有死,有始有终,因果轮回,循环往复.(说多了) react中,主要说明的是 一个组件的生命周期.简单 ...

  8. React笔记_(2)_react语法1

    这一节内容主要以了解为主. 渐渐的体会react的语法和其特性. ① htmlAndJs 混合编写 react和以往的前后台书写方式不一样. 在之前的多个语言中,讲求的是将页面代码和js代码逻辑分开, ...

  9. React笔记_(1)_react概述

    React概述   React是一种很好的前端技术. 它将应用打散成独立的小模块,然后进行组装,完成开发. react远比angularjs难学的多. react依赖的如webpack等各种工具得先学 ...

  10. React 笔记

    跟我一起学 React

随机推荐

  1. jQuery中的bind(), live(), on(), delegate()

    当我们试图绑定一些事件到DOM元素上的时候,我相信上面这4个方法是最常用的.而它们之间到底有什么不同呢?在什么场合下用什么方法是最有效的呢? 准备知识: 当我们在开始的时候,有些知识是必须具备的: D ...

  2. MyBatis学习笔记一:MyBatis最简单的环境搭建

    MyBatis的最简单环境的搭建,使用xml配置,用来理解后面的复杂配置做基础 1.环境目录树(导入mybatis-3.4.1.jar包即可,这里是为后面的环境最准备使用了web项目,如果只是做 my ...

  3. Nginx笔记总结十三:nginx 正向代理

    server { listen ; location / { resolver 202.106.0.20 202.106.119.116; resolver_timeout 30s; proxy_pa ...

  4. js类型比较

    比较数据类型做比较的三种方法typeofinstanceofObject.prototype.toString.call() javascript七大类型 javascript的数据类型分为两类:原始 ...

  5. windowserver 2012安装openssh

    下载https://github.com/PowerShell/Win32-OpenSSH/releases解压放到C:\Program Files\OpenSSH-Win64 进入到C:\Progr ...

  6. 测试LFI WITH PHPINO过程中的一些记录

    原理:以往LFI漏洞都是需要满足两个条件:1.攻击者上传一个含PHP代码的的文件,后缀名任意,没有后缀名也可以:2.需要知道上传后的文件路径及文件名,然后包含之. 后来有国外研究者发现了新的攻击方式, ...

  7. MAC使用nginx分发80至8080端口

    由于项目必须要启动80端口,但是mac系统中非root用户无法直接使用1024以下的端口 2.释放apache的80端口 由于Mac OS是自带Apache服务的,它本身占用了80端口,首先你需要将A ...

  8. Eclipse如何打开Android工程

    一.Eclipse如何打开Android工程 1.你可以在file->new->other->android object选择选项:create object from exists ...

  9. cpupower frequency 无法设置userspace的问题

    Disable intel_pstate in grub configure file: $ sudo vi /etc/default/grub Append "intel_pstate=d ...

  10. Ubuntu 14.10 进入单用户模式

    1. 开机,进入grub界面 2. 此时会有一个选项:Advanced Options for Ubuntu(ubuntu高级), 选中直接回车 3. 看到里面有很多选项,选中后面带recovery ...