欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  IT编程

要掌握的react的一些操作

程序员文章站 2022-04-13 17:42:14
这里只是对自己的学习进行一次总结,也是为了让自己以后如果长时间不使用快速记忆起来的笔记,如果想要学习,还是去官网看文档比较好一些。、 注意 下面的代码的 script标签的type类型都为 “text/babel” 目录 一、无状态组件 二、函数式声明 三、this以及事件对象 四、操作dom元素 ......

  这里只是对自己的学习进行一次总结,也是为了让自己以后如果长时间不使用快速记忆起来的笔记,如果想要学习,还是去官网看文档比较好一些。、

  注意 下面的代码的 script标签的type类型都为 “text/babel”

目录

一、 无状态的组件

  只是普通的变量是没有状态的, 只有组件才有状态或无状态

  react是单向数据流

  状态其实就是让数据驱动视图的响应式数据

 1 let a = '这里是div元素111';
 2 
 3 settimeout(() => {
 4   console.log('函数执行了');
 5   a = '改变之后的值'
 6 },2000);
 7 
 8 const element = (
 9   <div>{a}</div>
10 );
11 
12 reactdom.render(
13   element,
14   document.getelementbyid('app')
15 )

如果你学习过vue的话,那种双向数据绑定用的 object.defineproperty() 叫数据劫持,然后用了订阅发布(观察者)那种模式,数据改变之后,会驱动着视图去改变

react必须要通过 setstate() 这个组件的实例化对象去调用去改变自身的state才会去驱动视图是改变的,所以上面的那种就算数据改变了,但是视图是没有进行改变的。

看下面的es6的这种写法

 1 class element extends react.component{
 2   constructor() {
 3     super();
 4     this.state = { // 只有在state里面的内容才是有无状态的
 5       a: '这里是div元素'
 6     };
 7 
 8     settimeout(() => {
 9       this.setstate({  // 这里必要要用 setstate这个方法来改变值才会驱动视图去改变  如果  this.state.a = 'sdfsd' 这样是不会驱动视图去改变的
10         a: '改变之后的值'
11       })
12     }, 1000)
13   }
14   render() {
15     return (
16       <div>
17         {this.state.a}
18       </div>
19     );
20   }
21 }
22 
23 reactdom.render(
24   <element/>,
25   document.getelementbyid('app')
26 )

 

二、 函数式声明

  其实之前一直都是使用的变量去指代html元素,没有使用过 class 那种,现在先使用es5的写法去写一写什么是函数式声明。

  先看一下之前的写法吧

 1 const head = (
 2   <h2>head头部</h2>
 3 );
 4 const foot = (
 5   <h2>底部</h2>
 6 );
 7 const element = (
 8   <div>
 9     {
10       head
11     }
12     <h2>element内容</h2>
13     {
14       foot
15     }
16   </div>
17 );
18 
19 reactdom.render(
20   element,
21   document.getelementbyid('app')
22 )

函数式声明是什么样子的呢

 1 const head = function () {
 2   return (
 3     <h2>head头部</h2>
 4   )
 5 };
 6 const foot = function () {
 7   return (
 8     <h2>底部</h2>
 9   )
10 };
11 const element = function() {
12   return (
13     <div>
14       <head/>
15       <h2>element内容</h2>
16       <foot/>
17     </div>
18   );
19 };
20 
21 reactdom.render(
22   <element></element>,
23   document.getelementbyid('app')
24 )

可以很清晰的看到他们两个的区别,一个是使用变量来代表的,另外的一个是使用的组件形式代表的,开发中的写法都是使用es6的class继承声明来写组件的

看一下函数声明的传值

 1 const head = function (props) {
 2   return (
 3     <h2>{props.title}</h2>
 4   )
 5 };
 6 const foot = function (props) {
 7   return (
 8     <h2>{props.con}</h2>
 9   )
10 };
11 const element = function() {
12   return (
13     <div>
14       <head
15         title={'头部信息啊'}
16       />
17       <h2>element内容</h2>
18       <foot
19         con={'底部的内容啊'}
20       />
21     </div>
22   );
23 };
24 
25 reactdom.render(
26   <element></element>,
27   document.getelementbyid('app')
28 )

这个样子和vue其实是挺像的,在标签上面写自定义的属性,子组件就可以接收到,等先这样看看,后面会使用class写的,class写起来感觉还容易理解一些。

注意: 函数式声明组件

  1. 组件的首字母必须是大写

  2. 不要使用h5新标签

下面看一个状态改变驱动视图的例子

 1 const head = function (props) {
 2   return (
 3     <h2>{props.title}</h2>
 4   )
 5 };
 6 const foot = function (props) {
 7   return (
 8     <h2>{props.con}</h2>
 9   )
10 };
11 
12 class element extends react.component{
13   constructor() {
14     super();
15     this.state = {
16       title: '头部信息',
17       con: '底部信息'
18     };
19 
20     settimeout(() => {
21       this.setstate({
22         title: '头部信息改变'
23       })
24     },2000)
25   }
26   render() {
27     return (
28       <div>
29         <head
30           title={this.state.title}
31         />
32         <h2>element内容</h2>
33         <foot
34           con={this.state.con}
35         />
36       </div>
37     );
38   }
39 }
40 
41 reactdom.render(
42   <element></element>,
43   document.getelementbyid('app')
44 )

这样就可以和上面那种结合起来了,以后所有的组件都用class来写了,就不用function那种形式了。

 

三、 this以及事件对象

  react组件中的this和事件对象的不同写法有的写法是需要绑定this的

 1 class element extends react.component{
 2   constructor() {
 3     super();
 4   }
 5 
 6   btn() {
 7     console.log(this);  // 可以看到这里打印的是 undefined
 8   }
 9 
10   render() {
11     return (
12       <div>
13        <h1>title</h1>
14         <button onclick={this.btn}>按钮</button>
15       </div>
16     );
17   }
18 }
19 
20 reactdom.render(
21   <element></element>,
22   document.getelementbyid('app')
23 )

看到上面打印的this是undefined,下面有几种写法可以更正this指向实例化对象的

第一种 更正this和事件对象

 1 class element extends react.component{
 2   constructor() {
 3     super();
 4     this.btn = this.btn.bind(this);  // 在这里更正,官方推荐的也是这种写法
 5   }
 6 
 7   btn(e) {
 8     console.log(this);
 9     console.log(e.target)
10   }
11 
12   render() {
13     return (
14       <div>
15        <h1>title</h1>
16         <button onclick={this.btn}>按钮</button>
17       </div>
18     );
19   }
20 }
21 
22 reactdom.render(
23   <element></element>,
24   document.getelementbyid('app')
25 )

需要注意的是上面的那种写法如果传递参数的话,那么事件对象就是最后一个没有对象参数的和js中的bind一样

 1 class element extends react.component{
 2   constructor() {
 3     super();
 4     this.btn = this.btn.bind(this);  // 在这里更正,官方推荐的也是这种写法
 5   }
 6 
 7   btn() {
 8     console.log(this);
 9     console.log(arguments)  // 因为下面的函数传递了参数,这里第二个参数才是事件对象
10   }
11 
12   render() {
13     return (
14       <div>
15        <h1>title</h1>
16         <button onclick={this.btn(1)}>按钮</button>
17       </div>
18     );
19   }
20 }
21 
22 reactdom.render(
23   <element></element>,
24   document.getelementbyid('app')
25 )

第二种 在行内bind

 1 class element extends react.component{
 2   constructor() {
 3     super();
 4   }
 5 
 6   btn() {
 7     console.log(this);
 8     console.log(arguments)
 9   }
10 
11   render() {
12     return (
13       <div>
14        <h1>title</h1>
15         <button onclick={this.btn.bind(this, 1)}>按钮</button>  // 直接写到行内,在这里改变this的指向,同样的问题,那个参数的事件对象是最后一个
16       </div>
17     );
18   }
19 }
20 
21 reactdom.render(
22   <element></element>,
23   document.getelementbyid('app')
24 )

第三种 在一个函数里面执行它

 1 class element extends react.component{
 2   constructor() {
 3     super();
 4   }
 5 
 6   btn(e) {
 7     console.log(this);
 8     console.log(arguments)
 9   }
10 
11   render() {
12     return (
13       <div>
14        <h1>title</h1>
15         <button onclick={(e) => {
16           this.btn(e,11);
17         }}>按钮</button>
18       </div>
19     );
20   }
21 }
22 
23 reactdom.render(
24   <element></element>,
25   document.getelementbyid('app')
26 )

第四种 改变函数的写法

 1 class element extends react.component{
 2   constructor() {
 3     super();
 4   }
 5 
 6   btn = (e) => {
 7     console.log(this);
 8     console.log(e.target)
 9   }
10 
11   render() {
12     return (
13       <div>
14        <h1>title</h1>
15         <button onclick={this.btn}>按钮</button>
16       </div>
17     );
18   }
19 }
20 
21 reactdom.render(
22   <element></element>,
23   document.getelementbyid('app')
24 )

当然了这种方式如果要传递参数的话还是需要bind的。

 

四、 操作dom元素

  如果想要在react中操作dom元素的话,有几种方法

第一种 直接使用js的方法

 1 class element extends react.component{
 2   constructor() {
 3     super();
 4 
 5   }
 6 
 7   btn = () => {
 8     const ele = document.queryselector('.h1');
 9     console.log(ele);
10 
11   };
12 
13   render() {
14     return (
15       <div>
16        <h1 classname='h1'>title</h1>
17         <button onclick={this.btn}>按钮</button>
18       </div>
19     );
20   }
21 }
22 
23 reactdom.render(
24   <element></element>,
25   document.getelementbyid('app')
26 )

第二种 通过事件对象

 1 class element extends react.component{
 2   constructor() {
 3     super();
 4 
 5   }
 6 
 7   btn = (e) => {
 8     console.log(e.target);
 9   };
10 
11   render() {
12     return (
13       <div>
14        <h1 classname='h1'>title</h1>
15         <button onclick={this.btn}>按钮</button>
16       </div>
17     );
18   }
19 }
20 
21 reactdom.render(
22   <element></element>,
23   document.getelementbyid('app')
24 )

第三种 ref

  和vue一样

 1 class element extends react.component{
 2   constructor() {
 3     super();
 4 
 5   }
 6 
 7   btn = (e) => {
 8     console.log(this.refs.abc)  // 在这里获取它
 9   };
10 
11   render() {
12     return (
13       <div>
14        <h1 ref="abc">title</h1>  // 这里定义一个字符串的名字
15         <button onclick={this.btn}>按钮</button>
16       </div>
17     );
18   }
19 }
20 
21 reactdom.render(
22   <element></element>,
23   document.getelementbyid('app')
24 )

不过最新版本的不建议上面的那种写法了,也是ref建议下面的写法

以后我们就可以用下面这种最常用的方式

 1 class element extends react.component{
 2   constructor() {
 3     super();
 4 
 5   }
 6 
 7   btn = (e) => {
 8     console.log(this.abc)
 9   };
10 
11   render() {
12     return (
13       <div>
14        <h1 ref={abc => {this.abc = abc}}>title</h1>
15         <button onclick={this.btn}>按钮</button>
16       </div>
17     );
18   }
19 }
20 
21 reactdom.render(
22   <element></element>,
23   document.getelementbyid('app')
24 )

第四种 reactdom.finddomnode

 1 class element extends react.component{
 2   constructor() {
 3     super();
 4 
 5   }
 6 
 7   btn = (e) => {
 8     console.log(this.abc)
 9 
10     console.log(reactdom.finddomnode(this.abc));
11   };
12 
13   render() {
14     return (
15       <div>
16        <h1 ref={abc => {this.abc = abc}}>title</h1>
17         <button onclick={this.btn}>按钮</button>
18       </div>
19     );
20   }
21 }
22 
23 reactdom.render(
24   <element></element>,
25   document.getelementbyid('app')
26 )

ref如果标记的是组件,那么ref他就是组件,但是finddomnode这种方式是获取dom元素的,就算里面的参数是组件,也是获得dom元素

 

五、 父子组件传值

  核心思想 

  父组件给子组件传值 直接在组件上面添加属性就可以了 子组件通过props访问,得到 其实是构造函数实例化的时候传过去了

  子组件给父组件传值 其实是父组件给子组件传一个函数,子组件调用的时候把 要传递的数据 放到 父组件传递过来的函数 的参数里面,然后父组件再去做他自己的操作

item子组件


1 class item extends react.component { 2 constructor (props) { 3 super(props); 4 this.state = { 5 sub: this.props.data 6 } 7 } 8 9 componentwillreceiveprops(nextprops) { 10 console.log('执行了吗'); 11 console.log(nextprops); 12 } 13 14 render() { 15 console.log('子组件打印this'); 16 console.log(this); 17 console.log(this.props); 18 19 return ( 20 <div> 21 <p>item组件</p> 22 <h1>{this.state.sub.res}</h1> 23 <input type="button" defaultvalue="这里" onclick={this.props.supfn.bind(this,'子组件参数')} /> 24 <input type="button" 25 defaultvalue="22" 26 onclick={() => { 27 this.props.supfn('参数2') 28 }} 29 30 /> 31 </div> 32 ); 33 } 34 }

父组件

 1 class main extends react.component {
 2   constructor() {
 3     super();
 4     this.superfn = this.superfn.bind(this);
 5 
 6   }
 7   state = {
 8     data: {
 9       res: '里面的数据'
10     }
11   };
12 
13   superfn(a) {
14     console.log('父组件的函数');
15     console.log(`${a}`);
16     let data = {
17         res: '修改过后'
18     };
19     console.log(data);
20 
21     this.setstate({
22       data: data
23     })
24   }
25   render() {
26     return (
27       <div>
28         <p>主页面</p>
29           <p>{this.state.data.res}</p>
30         <item supfn={this.superfn} data={this.state.data} aaa="传值啊"></item>
31       </div>
32     );
33   }
34 }
35 
36 reactdom.render(
37   <main />,
38   document.getelementbyid('app')
39 )

六、在浏览器中支持import export

  要在服务器环境下打开文件

  在谷歌浏览器输入框中输入

要掌握的react的一些操作

然后就可以使用模块导出导出功能了

1 // 2.js
2 const a = 1;
3 const b = 2;
4 
5 export default {a, b};

 

1 <script type="module">
2     // 要服务器环境下打开  http服务
3     // chrome//flags 开启那个权限
4     import a from './2.js';
5     console.log(a)
6 </script>

如果你看了我的文章有了一些收获我会非常高兴的,由于能力有限,文章有的部分解释的不到位,希望在以后的日子里能慢慢提高自己能力,如果不足之处,还望指正。