关于Taro 中的事件冒泡的坑

5,017 阅读2分钟

在小程序中 天生有catchTap事件可以阻断事件冒泡

所以可以

<view catchTap="clickHandler"></view>

来阻止事件传播

在taro中 官方推荐使用e.stopPropagation()阻断事件冒泡

但是在小程序中 e.stopPropagation() 是一个空函数

实际上调用这个函数是没有任何作用的 那Taro是如何使用这个函数阻止事件冒泡的呢

答案就是Taro在编译时 发现这个handler中有调用e.stopPropagation() 将把事件绑定方法从onTap改成catchTap

那我们直接在taro中使用catchTap可以吗?

首先 我们试试使用匿名函数 直接将处理函数写在jsx内

编译后得到的是

这个时候 catchTap所绑定的方法 变成了anonymousState__temp2 这个东西不是一个注册在组件内部的方法 小程序的事件绑定会以字符串的形式触发注册在组件根部的方法,这个没有注册在组件根部,所以是不行的。

然后我们试试绑定在成员函数上面

taro的输出变成了

看起来很美好 感觉成功就在眼前了

然而

为什么找不到这个方法呢 这个方法不是被注册在了this上面吗?

我们点进这个黄色的warning 打个断点看看

代码是这样的

命中断点后是这样的

我们发现这个Object一干二净上面连一个handler方法都没有

展开_

proto_

原来这些方法被定义在了原型链上

仔细找了一下 发现原型链上注册的这些方法并不包含onClearSearch 这个方法

应该是Taro发现只有需要作为事件处理的方法才会被定义在原型链上

这个catchTap对于Taro来说并不算是事件处理的方法

那我们是不是只要想办法让onClearSearch这个方法出现在原型链上就可以了呢

换句话说只要让Taro把他认作是事件处理方法注册在对象的原型上我们就可以调用到了

那我们将onClick和catchTap都绑上这个事件 因为Taro应该是认识onClick的 必须会把onClick的事件注册到原型链上

编译后是这样的 

这次我们发现 onClearSearch 这个方法终于出现在了原型链上 而且也能调用成功了

结论

如果在jsx里面写匿名时间处理函数 可以直接写

<View 
    onClick=(e)=>{
      e.stopPropagation()
      //balabala
    }
>
</View>

Taro编译时检测到stopPropagation后会直接将onClick变成catchTap

如果要将事件处理函数绑定在成员方法上如 则可以写成

<Text 
      catchTap={this.onClearSearch}
      onClick={this.onClearSearch}
 />