提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档
文章目录
目录
1.react表单
React表单组件分为受控组件与非受控组件。
(1)受控组件:受控组件的值由props或state传入,用户在元素上交互或输入内容会引起应用state的改变。在state改变之后重新渲染组件,我们才能在页面中看到元素中值的变化,假如组件没有绑定事件处理函数改变state,用户的输入是不会起到任何效果的,这也就是“受控”的含义所在。
(2)非受控组件:类似于传统的DOM表单控件,用户输入不会直接引起应用state的变化,我们也不会直接为非受控组件传入值。想要获取非受控组件,我们需要使用一个特殊的ref属性,同样也可以使用defaultValue属性来为其指定一次性的默认值。
表单受控组件应用示例如下:
import React,{Component} from "react"; export default class App extends Component{ constructor(arg){ super(arg) this.state={msg:""} this.state={password:"123456"} this.input1=(e)=>{ console.log(e); this.state.msg=e.target.value this.setState(this.state) } this.input2=(e)=>{ console.log(e); this.state.password=e.target.value this.setState(this.state) } } render(){ return ( <div> <p>{this.state.msg}</p> text:<input type="text" value={this.state.msg} onInput={this.input1}></input> <br></br> password: <input type="password" value={this.state.password} onInput={this.input2}></input> <br></br> </div> ) } }
2.react事件
(2.1)react事件类型与事件对象
(2.1.1)事件类型
React事件使用小驼峰命名法,而不是全部小写命名。
React事件使用JSX传递一个函数作为事件处理程序,而不是一个字符串。
- 鼠标事件:onClick onDoubleClick onMouseDown
- 触摸事件:onTouchStart onTouchMove onTouchEnd
- 键盘事件:onKeyDown
- 剪切事件:onCopy onCut onPaste
- 表单事件:onChange onInput onSubmit
- 焦点事件:onFocus
- UI事件:onScroll
- 滚动事件:onWheel(2.1.2)事件对象
在react 中只能通过事件对象调用“event.preventDefault() ”进行阻止默认事件
(2.2)事件绑定
解决方法:
(1)constructor 内部对事件处理函数bind 绑定this(官方推荐)
(2)每次事件绑定都对事件处理函数做bind 绑定
(3)定义事件处理函数时使用箭头函数:
import React,{Component} from "react"; export default class App extends Component{ constructor(arg){ super(arg) this.fn=function(){ console.log(111); } //箭头函数 this.fn2=()=>{ console.log(222); } } render(){ return ( <div> <button onClick={this.fn}>btn1</button> <br></br> <button onClick={this.fn2}>btn2</button> //箭头函数 </div> ) } }
(4)当事件处理函数需要传参时:
<button onClick={this.changeData.bind(this,id)}>点击改变</button> <h2>{e=>this.changeData.call(id,event)}</h2>
3.react生命周期函数
react中的生命周期函数主要分为三个阶段创建、更新、销毁
创建阶段
(1)componentWillMount():
在渲染前调用,在客户端也在服务端。
(2)render():
此时可以创建虚拟dom,进行diff算法,更新dom树都是在此阶段,但是不能操作state
(3)componentDidMount():
在第一次渲染后调用,只在客户端。之后组件已经生成了对应的DOM结构,可以通过this.getDOMNode()来进行访问。 如果你想和其他JavaScript框架一起使用,可以在这个方法中调用setTimeout, setInterval或者发送AJAX请求等操作(防止异部操作阻塞UI)。
更新阶段
(1)componentWillReceiveProps(nextProps)在组件接收到一个新的 prop (更新后)时被调用,在初始化render时不会被调用。
(2)shouldComponentUpdate(nextProps, nextState)
返回一个布尔值。在组件接收到新的props或者state时被调用。在初始化时或者使用forceUpdate时不被调用。 可以在你确认不需要更新组件时使用。
(3)componentWillUpdata(nextProps, nextState)
在组件接收到新的props或者state但还没有render时被调用。在初始化时不会被调用。 数据发生变化后将要跟新,此时数据已经更新,但是页面还没有渲染。
(4)render()
组件进行虚拟dom的重新渲染
(5)componentDidUpdate()
在组件完成更新后立即调用。在初始化时不会被调用。
销毁阶段
(1)componentWillUnmount()组件将要卸载时调用,事件和定时器等会被清除
4.路由
(4.1)配置路由环境并实现跳转
(1)npm i react-router-dom 下载路由环境
(2)规则定义:router.js文件配置路由
import React from 'react'; import {HashRouter as Router, Route} from "react-router-dom"; import IndexPage from "./pages/IndexPage"; import NewsPage from "./pages/NewsPage"; class MyRouter extends React.Component { render() { return ( <div> {/*路由容器,所有的Route 与Link 组件都要放置其内部*/} <Router> {/*这里需要一个容器,内部存放多个路由*/} <div> {/*方法1:复杂路由放前边,辅助精确匹配*/} <Route path="/news" component={NewsPage}></Route> {/*方法2:为根路由添加精确匹配*/} <Route path="/" exact component={IndexPage}></Route> </div> </Router> </div> ); } } export default MyRouter;
(3)页面导入:App.js文件导入使用路由:
import React from 'react'; import MyRouter from "../router/router"; class App extends React.Component{ render(){ return ( <div> {/*使用路由规则*/} <MyRouter></MyRouter> </div> ) } } export default App;
(4)创建链接标签:
import {Link} from "react-router-dom"; import MyRouter from "../router/router"; class IndexPage extends React.Component { render() { return ( <div> 首页 <Link to="/">首面</Link> <Link to="/news">新闻页面</Link> </div> ); } } export default IndexPage;