reactJs 基础
react不是一个完整的mvc,mvvm框架。
react跟web components 不冲突 背景原理:基于React进行开发时所有的DOM构造都是通过虚拟DOM进行,每当数据变化时,React都会重新构建整个DOM树,然后React将当前整个DOM树和上一次的DOM树进行对比,得到DOM结构的区别,然后仅仅将需要变化的部分进行实际的浏览器DOM更新
react的特点就是‘轻’
组件化的开发思路
应用场景:复杂场景下的高性能 重用组件库,组件组合
ReactDOM.render()是React最基本方法 ,用于将模版转为HTML语言,并插入指定的DOM节点。
React.createClass()方法 就用于生成一个组件类 每个组件类都必须有自己的 render: 方法,用于输出组件。
注意:1 组件类第一个字母大写 2 组件类只能包含一个顶层标签 如用<div> 包裹
<HelloMessage name="John"> 组建的属性可以在 组件类的 this.props 对象上获取,this.props.name可以获取到
this.props.children 表示此组件的所有子节点 三种结果:1 没有子节点 undefined 2 有一个子节点 object 3 有多个子节点 array
React.Children.map() 遍历子节点
组件类的PropTypes 属性,用来验证组件实例的属性是否符合要求
propTypes:{title:React.PropTypes.string.isRequired,}
getDefaultProps 方法用来设置组件属性的默认值 getDefaultProps:function(){return{title:'Hello World'};}
ref属性 可以从组件中获取真实DOM节点 父组件引用子组件
this.refs.[name] 返回真实的DOM节点 需要等到click事件后调用
var MyComponent = React.createClass({
handleClick:function(){
this.refs.myTextInput.focus();
},
render:function(){
return(
<div>
<input type="text" ref=”myTextInput“ />
<input type = "button" value="Focus the text input" onClick = {this.handleClick} />
)
}
})
组件中getInitialState 方法用于定义初始化状态(对象),可以通过this.state属性读取。
var Input = React.createClass({
getInitialState: function() {
return {value: 'Hello!'};
},
handleChange: function(event) {
this.setState({value: event.target.value});
},
render: function () {
var value = this.state.value;
return (
<div>
<input type="text" value={value} onChange={this.handleChange} />
<p>{value}</p>
</div>
);
}
});
this.setState方法就修改状态值,每次修改后 自动调用this.render 方法,再次渲染组件。
this.props 表示那些一旦定义 就不再改变的特性;
this.state 是会随着用户互动而产生改变的
上面代码中,文本输入框的值,不能用 this.props.value
读取,而要定义一个 onChange
事件的回调函数,通过 event.target.value
读取用户输入的值。textarea
元素、select
元素、radio
元素都属于这种情况
引入解析jsx的文件 <script src='http://cdnjs.cloudflare.com/ajax/libs/react/0.13.3/JSXTransformer.js'></script> type=''text/javascript"
reactComponent 是指创建的dom节点
react component lifecycle的生命周期:
1 Mounted --- React.renderComponent() React Components被render解析生成对应的DOM节点 并被插入浏览器的DOM结构的一个过程
componentWillMount 前被调用 --> render --> componentDidMount 后被调用
getDefaultProps()
getInitialState() 初始化
2 Update --- setState() / setProps() 至render() 一个mounted的ReactComponents被重新render的过程
componentWillUpdate / componentDidUpdate / shouldComponentUpdate /componentWillReceiveProps
3 Unmounted --- React.unmountAndReleaseReactRootNode() 一个mounted的React Components对应的DOM节点 被从DOM结构中移除的这样一个过程
componentWillUnmount
总结:每一个状态 react都封装了对应的hock函数
组件的生命周期:初始化——运行中——销毁
初始化:可使用的钩子
1 getDefaultProps 只调用一次,实例之间共享引用
2 getInitialState 初始化每个实例特有的状态,都需要调用
3 componentWillMount render之前最后一次修改状态
4 render 只能访问this.props和this.state 不允许修改状态和DOM输出
5 componentDidMount 渲染完成之后触发,可对dom进行操作。
运行中:
1 componentWillReceiveProps 父组件修改属性触发,可以修改新属性,修改状态
2 shouldComponentUpdate 返回faulse 会阻止render调用
3 componentWillUpdate 不能修改属性和状态
4 render 只能访问this.props 和 this.state,不允许修改状态和DOM输出
5 componentDidUpdate 可以修改DOM
销毁:
componentWillUnmount
属性 组件自己不能修改属性,可以从父组件获取属性,父组件也可以修改它的属性,他也可以修改子组件的属性 :本身具有的,属性的四种用方式:
1 <HelloWorld name=? /> 出入键值对 "字符创" “item”
2 {“time”}{123}数字、字符串、等 var props={one:'123',two:321} <HeeloWorld{...props}/> {...props}展开对象的方式,取到的是值;{props}此方法取到的是对象
3 {【1,2,3】}数组
4 {变量}
状态 只和自己相关 与父组件子组件都不相关,有自己维护 :事物所处的状况,不断变化的
状态用法:
1 getInitialState:初始化每个实例特有的状态
2 setState:更新组件状态
setState-----diff-----dom
区分:组件在运行中需要修改的数据就是 状态。
极客react
非dom节点:
1、 dangerouslySetInnerHTML = {rawHTML}
var rawHTML = {__html:"<h1>i'm inner HTML"}
React.render(<div style={style} dangerouslySetInnerHTML={rawHTML}></div>, )
2、ref
3、key 列表类相同的节点 li 一定要加上key值 <li key='1'></li><li key='2'></li>
事件用法:组件(1,React自有方法:render 、componentWillUpdate、componentDidMount
2. 用户定义方法:handleClick、handleChange、handleMouseover)
绑定事件处理函数:
触摸:onTouchCancel
onTouchEnd
onTouchMove
onTouchStart
键盘:onKeyDown
onKeyPress
onKeyUp
剪切:onCopy
onCut
onPaste
表单:onChange
onInput
onSubmit
焦点:onFocus
onBlur
UI元素:onScroll
滚动:onWheel
鼠标:onDrop/onDrag/onDragEnd/onDragEnter/onDragExit/onDragLeave/onDragOver/onDragStart
onClick/onContextMenu/onDoubleClick/onMouseDown/onMouseEnter/onMouseLeave/onMouseLeave/onMouseMove/onMouseOut/onMouseOver/onMouseUp
事件对象的属性:
事件和状态关联:
handleChange:function(e){this.setState({inputText:e.target.value})}
组件协同:
1 组件嵌套: 父子关系 父组件-属性-》子组件;子组件-委托(触发事件)-》父组件
2 mixin:React双向绑定Minxin
组件要可控:符合react的数据流;数据存储在state中,便于使用;
表单元素:
<label htmlFor="name">对应相应的input的id</label>
<input><textarea><select><option></option></select>
事件处理函数复用:
1、bind复用:
handleChange:function(name,event){....}
{this.handleChange.bind(this,'input')}
2、name复用:
handleChange:function(event){var name=event.target.name}
{this.handleChange}
React性能调优:
提高性能的方式:虚拟DOM,diff算法,将dom操作减少到最小,但是
问题1:父组件更新默认出发所有子组件更新;解决方法:子组件覆盖shouldComponentUpdate方法,返回true,触发更新流程,生成新的虚拟DOM节点与之前的进行比较,不同则进行操作;返回false,自行解决是否更新。
问题2:列表类型的组件默认更新方式比较复杂;解决方法:给列表中的组件添加key属性
性能调优:分析性能热点
控制台输入React.addons.Perf.start()--->进行一次操作---->React.addons.Perf.stop() ;完成后台记录消耗时间
查看记录结果:React.addons.Perf.printInclusive();
如何解决性能问题:1;PureRenderMixin判断是否需要进入更新流程,本质上就是判断状态和属性是否改变(只能处理原始值,不能处理对象)
在shouldComponentUpdate(nextProps,nextStates)内判断!shallowEqual(this.props,nextProps)||!shallowEqual(this.state,nextState);
2;不可变插件Immutability Helpers,实现js不可变对象
基本语法:update(obj,cmd)
组件嵌套:
钩子函数:
初始化:getDefaultProps 只调用一次
getInitialState
componentWillMount 渲染之前最后一次修改状态this.setState({}),触发render()函数;
render
componentDidMount 操作或修改真正的dom
运行中:componentWillReceiveProps 父组件修改属性之前触发,此函数可以修改新属性、修改状态
shouldComponentUpdate 返回false,根据需要使用
componentWillUpdate :不能修改属性和状态
render:只能访问this.props和this.state,不能修改
componentDidUpdate :可以修改dom
销毁:componentwillUnmount 在删除组件之前进行清理操作,比如计时器和事件监听器,必须手动清理。方法1.在子组件中componentwillUnmount:function(){} 方法2:在子组件的handle函数中,调用:React.unmountComponentAtNode(document.getElementsByTagName('body')[0]);//传入的必须是装载入的节点。
React.findDOMNode()
react添加css动画:
var ReactCSSTransitionGroup = React.addons.CSSTransitionGroup; 引入react-addons-t
调用:return(<ReactCSSTransitionGroup transitionName="example">{items}</ReactCSSTransitionGroup>)
react添加js动画:
componentDidUpdate:function(){if(this.props.position){setTimeout(this.resolveSetTimeout,this.props.timeoutMs);}},
render:function(){var divStyle={marginLeft:this.state.position};return <div style={divStyle}>this will animate!</div>}})
React.render(<Positioner></positioner>,document.body);
React.render(<Positioner position={100} timeout={10}></Positioner>,document.body);第二次调用,改变属性值props,触发componentDIdUpdate();从而达到动画效果
项目实战:
1.分析目标-确定开发顺序:页面上有组件->组件能正常显示内容->内容的样式正确->设置项可以正常工作->交互功能正常
在jsx中使用循环,一般会用到Array.prototype.map
class Hello extends React.Component{
render(){
const arr = ['a','b','c'];
return (
<div>
{arr.map((item,index) => {
return <p key={index}> this is {item}</p>
})}
</div>
)
}
}
参考链接:http://www.imooc.com/article/14500
代码分离:
page层 ./app/containers/Hello/index.jsx
subpage层 ./app/containers/Hello/subpage/...jsx
component层 ./app/components/... 把多个页面都可能用到的功能,封装到一个组件中,放到此目录下。
数据传递&数据变化
props:一般只用作父组件给子组件传递数据用,不能被自身修改。
每个页面引用Header时,设置独自的title属性值,<Header title='Hello页面'/>;而在子组件中这样取到 render(){return(<p>{this.props.title}</p>)}
state:自身组件状态发生变化,constructor(props,context){super(props,context);this.state = {now:Date.now()}} render(){return (<div><p>hello world {this.state.now}</p></div>)}}
智能组件&木偶组件
智能组件:./app/containers 简称“页面”,只对数据负责,只需获取数据、定义好数据操作的相关函数,然后将这些数据、函数直接传递给具体的实现组件。
木偶组件:做一些展示的工作,展示给用户。 ./app/components/...
性能检测优化:参考https://github.com/wangfupeng1988/react-simple-o2o-demo/tree/getready-redux-width-react 本地切换到对应的分支
1安装react的性能检测工具npm install react-addons-perf --save 在./app/index.jsx中import Perf from 'react-addons-perf' if(__DEV__){window.Perf = Perf}
使用:Perf.start()开始检测,Perf.stop停止检测,Perf.printWasted()即可打印出浪费性能的组件列表。
2安装react的优化插件 PureRenderMixin,npm install react-addons-pure-render-mixin --save
使用:在constructor(props,context){super(props,context);this.shouldComponentUpdate = PureRenderMixin.shouldComponentUpdate.bind(this);}} 重写组件shouldComponentUpdate函数,在每次更新之前判断props和state,如果有变化返回true。
3 Immutable.js优化:使用此来处理数据,实现js中不可变数据的概念。适用于数据结构层次很深(obj.x.y.a.b=10)其定义了新的语法,不轻易使用。
React-router
安装 npm install react-route --save
1 创建子页面./app/containers/App.jsx 所有页面的外壳 ./app/containers/Home等主页、列表页、详情页
2 配置router 创建./app/router/routerMap.jsx 文件
class RouteMap extends React.Component{
updateHandle(){
//每次router变化之后都会触发
}
render(){
return (
<Router history={this.props.history} onUpdate={this.updateHandle.bind(this)}>
<Route path='./' component={App}>
<IndexRoute component={Home}/>
<Route path='list' component={list}/>
<Route path='detail/:id' component={Detail}/> //id表示参数
<Route path="*" component={NotFound}/>
</Route> //route可以嵌套
</Route>
)
}
}
3 使用Route
./app/index.jsx
import React from 'react'
import {render} from 'react-dom'
import {hashHistory} from 'react-router' import RouteMap from './router/routeMap' render(
<RouteMap history={hashHistory}/>, //hashHistory规定hash来表示router localhost:8080/#/list
document.getElementById('root')
)
页面跳转
1 <link to='/list'>to list </link>
2 js跳转
return(<ul>
{arr.map((item,index) => {
return <li key={index} onClick={this.clickHandle.bind(this,item)}>js jump to {item} </li>})}
</ul>)}
clickHandle(value){
hashHistory.push('/detail/' + value)
}}
性能优化--静态资源懒加载 huge-apps
他将react-router本身和webpack的require.ensure结合起来,解决此问题。
reactJs 基础的更多相关文章
- ReactJS基础(续)
前边的ReactJS基础,我们可以了解到,对于React,可以说是万物皆组件 React的组件应该具有 可组合(Composeable)可重用(Reusable)可维护(Maintainable)的特 ...
- ReactJS基础视频教程
React是什么?React.js 是 Facebook 推出的一个用来构建用户界面的 JavaScript 库.Facebook开源了React,这是该公司用于构建反应式图形界面的JavaScrip ...
- 2.ReactJS基础(虚拟DOM,JSX语法)
将脚手架(create-react-app)创建的todolist项目精简为hello world示例 即,删除自动生成的样式文件.logo.svt.App.test.js.serviceWorker ...
- 【JavaScript】ReactJS基础
初探React,将我们的View标签化 前言 我之前喜欢玩一款游戏:全民飞机大战,而且有点痴迷其中,如果你想站在游戏的第一阶梯,便需要不断的练技术练装备,但是腾讯的游戏一般而言是有点恶心的,他会不断的 ...
- 1. ReactJS基础(开发环境搭建)
本文主要介绍通过React官方提供的create-react-app脚手架进行开发环境的搭建. 1.安装node环境(安装过程这里不做介绍,可参考其他博文) 在cmd中输入node -v 如果可以看到 ...
- web前端学习路线(含20个真实web开发项目集合)
目前web前端工程师日均岗位缺口已经超过50000,随着互联网+的深入发展,html5作为前端展示技术,市场人才需求量将呈直线上涨. Web前端工程师的岗位职责是利用HTML.CSS.Java.DOM ...
- 自学web前端达到什么水平,才能满足求职的标准?
大多数野生程序员最棘手的问题就是如何依靠技术解决温饱,通俗来讲就是技术折现的问题. 如果是单纯出于兴趣,或者只是为了突击某一阶段或者某一项目技术壁垒,不跟就业挂钩的自学倒也是无关痛痒.但是当上岗成为自 ...
- ReactJS入门基础
渲染这俩字可能在很多地方都见过.但可能不太理解是啥意思. 那么首先我们来理解一下渲染. 渲染 我觉得这样理解比较通俗. 我们做一个汽车,开始是没有喷漆的(没有css) 只是些框框架架(HTML标签). ...
- React基础---->ReactJS的使用(一)
ReactJS的初次使用,比较简单的例子. React的使用 一.下载ReactJS,地址:http://reactjs.cn/react/downloads.html,直接解压就行. 二.在html ...
随机推荐
- 【算法】K-Means聚类算法(k-平均或k-均值)
1.聚类算法和分类算法的区别 a)分类 分类(Categorization or Classification)就是按照某种标准给对象贴标签(label),再根据标签来区分归类. 举例: 假如你有一堆 ...
- 如何在ThinkPHP中开启调试模式
1.为什么使用调试模式? 因为调试会在我们的模板页的最后增加一些trace信息. 2.什么是trace信息? 是ThinkPHP为我们提供好的一些包含了系统运行时间.占用内存.加载时间.请求的协议.. ...
- 数据库和AI的一次火花
欢迎大家前往腾讯云+社区,获取更多腾讯海量技术实践干货哦~ 本文由宗文 发表于云+社区专栏 | 导语 通过历史数据,基于时间序列来预测未来. 我们生活中很多数据是有时间维度的.比如说天气或者股票价格. ...
- Win10新建分区
今天忽然觉得将系统分为四个盘,有点无法将分类分开,所以增加了几个分区: 1.windows+X键在弹出的对话框中选择磁盘管理,进入如下界面: 2.如果你想从某个盘分出一些内存建立一个新的分区,就在这个 ...
- jqGrid随窗口大小变化自适应宽度
$(function(){ $(window).resize(function(){ $("#jqgridID").setGridWidth($(window).width()); ...
- 动作方法中 参数,Json
一.方法中可以出现的参数类 1.HttpServletRequest 2.HttpServletResponse 3.HttpSession 4.Model 二.返回接收json数据 1. 接收,返回 ...
- navicat 12 破解
一.安装 官方下载下载 http://www.navicat.com.cn/download/navicat-premium 二.安装完后下载破解文件 https://pan.baidu.com/s/ ...
- js简单时分秒倒计时
效果: javascript: <script type="text/javascript"> function countTime() { //获取当前时间 var ...
- 使用 iframe + postMessage 实现跨域通信
在实际项目开发中可能会碰到在 a.com 页面中嵌套 b.com 页面,这时第一反应是使用 iframe,但是产品又提出在 a.com 中操作,b.com 中进行显示,或者相反. 1.postMess ...
- Linux服务器性能评估与优化(一)
网络内容总结(感谢原创) 1.前言简介 一.影响Linux服务器性能的因素 1. 操作系统级 性能调优是找出系统瓶颈并消除这些瓶颈的过程. 很多系统管理员认为性能调优仅仅是调整一下 ...