DataV icon indicating copy to clipboard operation
DataV copied to clipboard

使用vue2.x 中的extend继承属性, 被继承的组件中使用DataV的边框组件,svg图层无法获取width与height

Open bayniidt opened this issue 5 years ago • 16 comments

...

bayniidt avatar Nov 17 '20 08:11 bayniidt

能否给出复现例子

jiaming743 avatar Nov 19 '20 05:11 jiaming743

能否给出复现例子

作者你好,我这边貌似出现了同样的问题,我的环境中,使用dv-border-box-3(其他边框一样问题)组件,会出现边框显示不全的问题。如果改变浏览器大小(最大化等操作),边框会显示出来。查看了代码,发现是组件渲染的时候,svg属性没有获取width和height值。如果改变浏览器大小后(图二),会获取到。目前掌握的前端知识无法自己处理这个问题。。。希望能帮忙看一下。感谢。

https://user-images.githubusercontent.com/11781345/99629159-773c2200-2a72-11eb-9ff2-b727bf6ddeb3.png

https://user-images.githubusercontent.com/11781345/99629059-54aa0900-2a72-11eb-8562-f9f8176009ea.png

bantu4me avatar Nov 19 '20 06:11 bantu4me

能否给出复现例子

作者你好,我这边貌似出现了同样的问题,我的环境中,使用dv-border-box-3(其他边框一样问题)组件,会出现边框显示不全的问题。如果改变浏览器大小(最大化等操作),边框会显示出来。查看了代码,发现是组件渲染的时候,svg属性没有获取width和height值。如果改变浏览器大小后(图二),会获取到。目前掌握的前端知识无法自己处理这个问题。。。希望能帮忙看一下。感谢。

https://user-images.githubusercontent.com/11781345/99629159-773c2200-2a72-11eb-9ff2-b727bf6ddeb3.png

https://user-images.githubusercontent.com/11781345/99629059-54aa0900-2a72-11eb-8562-f9f8176009ea.png

微信截图_20201119143810 在改变浏览器大小后,发现执行了这里的代码,然后出现了完整的边框

bantu4me avatar Nov 19 '20 06:11 bantu4me

目前看,改页面下所有边框节点有类似的问题。我已经按照文档建议 “边框内的节点封装成组件,以组件的形式置入边框”

bantu4me avatar Nov 19 '20 07:11 bantu4me

你好,我也有类似的问题,请问下你那边有解决这个问题吗?

bantu4me avatar Nov 20 '20 01:11 bantu4me

你好,我也有类似的问题,请问下你那边有解决这个问题吗?

出现这个问题的原因可能是,svg的宽高使用的是clinetWidth与clinetHeight这两个只读属性, 这两个属性需要的是DOM渲染到浏览器上,真实的宽高。 我的解决办法是,使用一个中间DIV ,先给这个中间DIV赋予宽高并且执行到vue的mouted生命周期后,再渲染datav中的边框组件,此时的svg就可以获取到宽高了

bayniidt avatar Nov 20 '20 01:11 bayniidt

你好,我也有类似的问题,请问下你那边有解决这个问题吗?

然而出现的另一个问题就是, dom结构会很乱,在其他组件中用到的时候会出现无法渲染继承自datav边框组件DOM的情况。目前也为解决

bayniidt avatar Nov 20 '20 01:11 bayniidt

你好,我也有类似的问题,请问下你那边有解决这个问题吗?

出现这个问题的原因可能是,svg的宽高使用的是clinetWidth与clinetHeight这两个只读属性, 这两个属性需要的是DOM渲染到浏览器上,真实的宽高。 我的解决办法是,使用一个中间DIV ,先给这个中间DIV赋予宽高并且执行到vue的mouted生命周期后,再渲染datav中的边框组件,此时的svg就可以获取到宽高了

请问下,你这里用原生js吗?有没有示例参考下?

bantu4me avatar Nov 20 '20 06:11 bantu4me

你好,我也有类似的问题,请问下你那边有解决这个问题吗?

出现这个问题的原因可能是,svg的宽高使用的是clinetWidth与clinetHeight这两个只读属性, 这两个属性需要的是DOM渲染到浏览器上,真实的宽高。 我的解决办法是,使用一个中间DIV ,先给这个中间DIV赋予宽高并且执行到vue的mouted生命周期后,再渲染datav中的边框组件,此时的svg就可以获取到宽高了

请问下,你这里用原生js吗?有没有示例参考下?

用Vue就不用原生了, 应该还有更好的解决办法 ,可以互相学习 extend1 extend2

bayniidt avatar Nov 20 '20 08:11 bayniidt

你好,我也有类似的问题,请问下你那边有解决这个问题吗?

出现这个问题的原因可能是,svg的宽高使用的是clinetWidth与clinetHeight这两个只读属性, 这两个属性需要的是DOM渲染到浏览器上,真实的宽高。 我的解决办法是,使用一个中间DIV ,先给这个中间DIV赋予宽高并且执行到vue的mouted生命周期后,再渲染datav中的边框组件,此时的svg就可以获取到宽高了

请问下,你这里用原生js吗?有没有示例参考下?

你的业务逻辑如果只需要渲染一次 DataV边框组件的话就简单了,用一个固定宽高的div包裹住就行 例如:

<div style='wdith:100px; height: 100px'>
    <dv-border-box-8>dv-border-box-8</dv-border-box-8>
</div>

bayniidt avatar Nov 20 '20 08:11 bayniidt

能否给出复现例子

业务代码比较多,尝试简单demo是可以正常使用的。

出现问题的业务:在高德地图的信息弹框infoWindow时,弹出一个信息组件alarm,该组件被 <dv-border-box> 包裹,继承信息组件alarm后拿到alarm.$el 的HTML模板字符串,最后再塞到高德API infoWindow中进行渲染。

主要原因是svg使用了clinetWidth与clintHeight作为宽高属性,DOM并没有被挂载,所以svg的宽高就为0

bayniidt avatar Nov 20 '20 08:11 bayniidt

能否给出复现例子

业务代码比较多,尝试简单demo是可以正常使用的。

出现问题的业务:在高德地图的信息弹框infoWindow时,弹出一个信息组件alarm,该组件被 <dv-border-box> 包裹,继承信息组件alarm后拿到alarm.$el 的HTML模板字符串,最后再塞到高德API infoWindow中进行渲染。

主要原因是svg使用了clinetWidth与clintHeight作为宽高属性,DOM并没有被挂载,所以svg的宽高就为0

我这边代码逻辑比你的简单,没有组件的继承,就是在我的自定义组件内引用dataV边框,我尝试外面套一个div的形式也没有解决。 最外层div是后面加的,发现还是有一样的问题。 image

bantu4me avatar Nov 23 '20 02:11 bantu4me

能否给出复现例子

业务代码比较多,尝试简单demo是可以正常使用的。

出现问题的业务:在高德地图的信息弹框infoWindow时,弹出一个信息组件alarm,该组件被 <dv-border-box> 包裹,继承信息组件alarm后拿到alarm.$el 的HTML模板字符串,最后再塞到高德API infoWindow中进行渲染。

主要原因是svg使用了clinetWidth与clintHeight作为宽高属性,DOM并没有被挂载,所以svg的宽高就为0

我的问题解决了。但是原理是什么我还是不清楚。之前我出问题的组件是直接渲染的,然后我尝试加个if标签试试看,没想到问题就好了。。。 image

bantu4me avatar Nov 23 '20 02:11 bantu4me

我尝试使用v-if也不行 ,原理应该是延迟渲染了 ,如果父盒子有宽高,那div-border应该会继承父盒子的宽高的吧,能用就好了

bayniidt avatar Nov 24 '20 02:11 bayniidt

我也遇到了相似的问题。

我的场景是:引用了Element UI的Tabs组件,在每一个tab页中,我都引用了DataV中的dv-decoration-9组件。然而,有趣的是,组件只能显示在一个tab上,其他tab不显示。

经过排查后发现,是与楼里各位同样的问题,svg获取不到width,width为0。

经过进一步的排查,原来在el-tab中,当一个tab页显示,其他tab页会用“display:none”的属性隐藏,然而在display: none的时候,会将没有渲染的元素(比如这里的dv-decoration-9)移出DOM树,因而svg也就获取不到width了。Google搜索“display:none width 0”的关键词可以搜到很多这样的问题,不仅仅局限于DataV。

我解决的突破口放在避免“display: none”的使用上。所以我通过v-if控制tab页的渲染,即只有在tab页被选中时,才将它渲染到页面上。例如:

<el-tabs v-model="activeName"> <el-tab-pane name="first" :key="0"> <span style="font-size: 18px;" slot="label"><i class="el-icon-s-grid"></i> Data Analytics</span> <HeadLayout v-if="activeName === 'first'"></HeadLayout> <el-main v-if="activeName === 'first'"> <BodyLayout></BodyLayout> </el-main> </el-tab-pane> <el-tab-pane name="second" :key="1"> <span style="font-size: 18px;" slot="label"><i class="el-icon-s-grid"></i> AI </span> <HeadLayout2 v-if="activeName === 'second'"></HeadLayout> <el-main v-if="activeName === 'second'"> <BodyLayout2></BodyLayout2> </el-main> </el-tab-pane> </el-tabs> methods: { handleTabClick(tab) { // 只有在点击的是未激活的选项卡时才会触发 if (tab.name !== this.activeName) { this.activeName = tab.name } } } 这样组件便可以正常显示了。楼上的朋友用v-if可以成功,应该也是这样的原理。

eurecalulu avatar Apr 14 '23 06:04 eurecalulu

我也遇到了相似的问题。

我的场景是:引用了Element UI的Tabs组件,在每一个tab页中,我都引用了DataV中的dv-decoration-9组件。然而,有趣的是,组件只能显示在一个tab上,其他tab不显示。

经过排查后发现,是与楼里各位同样的问题,svg获取不到width,width为0。

经过进一步的排查,原来在el-tab中,当一个tab页显示,其他tab页会用“display:none”的属性隐藏,然而在display: none的时候,会将没有渲染的元素(比如这里的dv-decoration-9)移出DOM树,因而svg也就获取不到width了。Google搜索“display:none width 0”的关键词可以搜到很多这样的问题,不仅仅局限于DataV。

我解决的突破口放在避免“display: none”的使用上。所以我通过v-if控制tab页的渲染,即只有在tab页被选中时,才将它渲染到页面上。例如:

<el-tabs v-model="activeName"> <el-tab-pane name="first" :key="0"> <span style="font-size: 18px;" slot="label"><i class="el-icon-s-grid"></i> Data Analytics</span> <HeadLayout v-if="activeName === 'first'"></HeadLayout> <el-main v-if="activeName === 'first'"> <BodyLayout></BodyLayout> </el-main> </el-tab-pane> <el-tab-pane name="second" :key="1"> <span style="font-size: 18px;" slot="label"><i class="el-icon-s-grid"></i> AI </span> <HeadLayout2 v-if="activeName === 'second'"></HeadLayout> <el-main v-if="activeName === 'second'"> <BodyLayout2></BodyLayout2> </el-main> </el-tab-pane> </el-tabs> methods: { handleTabClick(tab) { // 只有在点击的是未激活的选项卡时才会触发 if (tab.name !== this.activeName) { this.activeName = tab.name } } } 这样组件便可以正常显示了。楼上的朋友用v-if可以成功,应该也是这样的原理。

太棒了,真的

i1arn avatar Apr 07 '24 17:04 i1arn