React里eltable自己变小的bug排查全过程
最后更新于
这有帮助吗?
最后更新于
这有帮助吗?
大家看 这神奇的BUG
现在里边这个表格是撑满这个弹框的
然后把弹框重新打开
大家看里边表格就变窄了
我们先来检查一下这个元素
现在这个表格的宽度大家看是
然后呢我们刷新一下
大概正常的情况下呢这个表格是
然后我们把它关闭
再重新打开
大概变成450了
怎么回事呢
我们先来看一下代码
他这个用的是react的
说实话react 我也不是很熟
没关系大家跟着我看就可以哈
我们先去看一下这个table的源码
这个react直接点不进去
所以呢我们需要自己去这个node_modules
里面去找到这个组件
在这里然后呢找到他这个table body
他看这块就有一个width等于this.bodyWidth
比如说他肯定是每一次展开的时候
这个值发生变化了
我们先来看一下这个值在哪设置的哈
哎在这里大家看
bodyWidth是从layout里面
取出来的
然后下面这点运算影响不大
那我们来看layout啊
layout他在这同级目录下有一个 table layout
然后呢这里边我们在搜bodyWidth
打开这个赋值 赋了一个
this.table的一个宽度
我们不管他再往下找
在这里
打开 body width
等于这两个值里边那个大的
body width
就是上面我们看到它取的就是这个el-table
table 的
这个整体的宽度
然后呢它还有一个变量body min width
它是怎么取的呢
大家看他在这啊
就是取他每一列的设置的这个width
或者每一列你给设置那个minWidth(之和)
啥意思呢
就是在这个表格里边大家看
他给每一列都设置
了一个minWidth
现在 minWidth minWidth
大家看!三列:150 、100 ,200 加一起
正好是那个
所以呢他在这我们可以断定
(二次打开的时候 ) 他在这取值的时候肯定是他这个
正好比他大
那为什么他会比他大呢
这个很容易我们试一下就知道了
因为他不是取的这个el-table的clientWidth吗
我们就取他的
clientWidth
大家看 现在是
我把它关闭
因为他是关闭的时候弹出的一瞬间吗
所以我们这个时候再获取一下
大家看这就是0了
也就是说他在隐藏的时候啊
取到的这个clientWidth是
所以呢他0一定是小于最小宽度450的
所以打开的时候
就被更新成450的宽度了
但问题是
他为什么要在这
调一下这个更新的组件呢
来看一下这个方法在哪调用的
大家看在这
其他的就没了
然后呢我们再看这个方法在哪调的
resizeListener 这个很正常
这个啊就是构造函数里边的一个监
加了一个监听
这个不管他
我们再找
componentDidMount
这估计是react的一些生命周期
挂载完之后的我们再来找
componentDidUpdate
估计就是走到这了
我们再来看应该就没有别的了
大家看 就回来了 所以
应该就是走在这
就是说他每次重新打开的时候
都走了这个方法
然后呢他这有个判断 大家看
看这个字面的意思
就是看这些属性是不是发生变化了
就说columns、style、className
这3个属性任意一个发生变化
他都会更新一下这个表格的一些
尺寸啊什么的
那现在的问题就
是我们这3个属性到底变没变
我们来看一下
哈
我们选中这个 el-table
然后呢我们盯着这节点的这些属性
打开这个弹框大家看
大家看 没有变化对不对
我再关闭
也就是说 他任意一个属性都没有变化
包括style也没有变化
为什么他就会走这里呢
所以呢这就很奇怪
那这种情况呢
我们最好的方法就是
在这可以加一个输出
来调试一下
但是啊直接在这加输出是不好使的
这个我试过
但后来我找到了一个方法
分享给大家哈
就这样
他不是有这段代码吗
我们搜一下这段代码在哪呢
在页面上找network
然后刷新一下
把所有资源加载上以后啊
然后啊在这里用 command + option + F
调出来这个窗口
然后我们在这搜
粘过来直接搜哈
开始直接搜的话
他搜出来一个这个大家看TabeLayout.js
跟那个是一样的
这个我也试了他不走
后来我想是不是引号的问题
我就把这个单引号换成双引号
试了一下
就找到这个了
chunk-CADB....
那我们打开这个
然后呢在这右键 open in new tab
这样的话
就可以单独浏览这个js文件了
我们把这个文件名复制到这个vscode里
看有没有直接打开这个
大家看有这个,我最近打开过哈
如果没有打开过的话
直接在这找是没有的
大家可以直接在这里边一层一层去找
那我这个打开过
先不管它哈
我们在这打开它
然后呢还是找到这段代码
大家看
那这几个咱们都在这输出一下
打卡靠拢 style
然后再来一个拉丝内容
看到底是哪个属性他发生变化了
然后呢注意在这个文件里改的东西啊
每次他需要重启一下
我们重启一下
然后呢我们刷新一下
咱再搜一下这个
大家看,这console.log就加上了
然后呢我们在这再刷新
看下效果
大家看我打开它
先不管他清空然后关闭
大家看
关闭的时候他有一次是中间那个是true
我们再打开
他看还是中间那个是true
他就一直认为中间那个值,也就是说
这个style发生变化了
好那我们再来看
他为什么会认为style发生变化了
我们看下这里边他怎么写的
在这里他获取了最新的style的样式
然后获取了(pre嘛)上一次的样式
然后他俩做了一个
不等于的比较
我们把这一段代码啊都拿过去
放到这然后呢把这key改成("style")
(因为它认为style变了嘛)
我们把style拿过来
我们用 JSON.stringify
然后呢再来一个
这个 pre 的
然后后面就不要了
好我们再来试一下,注意重启一下
好我们来试一下啊先把这刷新一下
因为他可能有缓存
然后再来这刷新
清空一下
展开关闭我们再清空
最后我们再展开注意看啊
大家看,明明是一模一样的值
他就认为
发生变化了
那这是为什么呢我们来看一下这
他在写这个table的时候啊
这个style里边是这样写的
所以呢
他每次
这个地方
他都会认为这是一个新的对象
所以呢
他在这做这个属性比较的时候 大家注意看
因为他用的是这个
3个等号的这种比较所以呢他会认为
这块虽然值一样
但是他不是同一个对象了
所以就发生变化了
我们把它去掉试一下
不要任何的样式了
报错! 我们把这个也去掉吧!不要style了
刷新
大家看
这就没问题了
但是呢实际情况可能又需要配置样式
那怎么办呢
我们可以这样把这个样式啊
放到上面这个state里面
在这里比如说我们叫tableS tyle
哎把它拿这来
然后呢在下边我们用
this.state.tableStyle
好我们再刷新一下
大家看 没问题了这样就完美解决了
那还有一种方法呢
就是我们不用style了
把我们想写的样式封装成CSS
然后呢在这写className
这个是没有问题的
这个我试过
你怎么写
他都不会认为这个属性发生变化了
所以呢就不会有任何问题