用vue的抽象组件来做一个防止img标签url为空或url地址出错的验证
看了网上文章学习了下vue的抽象组件,感觉就跟react的高阶组件一样的使用场景,只是更加面向vue的底层编程
,网上介绍的抽象组件一般有2种用法,1 用来加防抖和节流 2 用来控制按钮是否允许点击做权限效验,这2个对于
目前我所做的一些项目用处不大,这里先介绍下我用抽象组件的使用场景,总不能说学习了抽象组件不管是否适用就
强行加到项目里吧。。。
1. 基本上公司项目所有用到动态地址的地方都要做2个效验,1 判断这个从后台返回的url是否为空,相信大家
经常写这种代码 :src="imgUrl|| defUrl", 2 如果这个地址存在,那么还要做验证,防止地址报错,这个
代码大家也经常写吧 @error="fixUrl"。 如果每个用动态img的地方都这么写,一个项目下来我都要吐了。
2. 就算你愿意这么写,还是有一个问题,在 @error="fixUrl"里,一般的处理方式是在方法里把imgUrl替换成
defUrl,这样就会有另一个问题,显示的图片是出来了,但是如果你的imgUrl不仅用来展示要在其他地方用,你总不能
拿替换过的imgUrl用在其他地方吧,针对这种情况,大部分人(之前的我)的处理情况就是要2套数据放到data里,一套用来
展示,一套用来内部传值使用,很不优雅对吧。
3. 我也想过,做一个组件,然后所有需要验证的地方都不用img都用这个img组件,但是img的样式,和绑定的方法,这些你都要
从外边取,然后绑定到真实img上,我只想处理个图片验证啊,怎么还有这么多需要兼容的地方要关注,好麻烦啊。
所以遇到了抽象组件,稍微思考了一下,觉得可以完美解决以上3个问题。真香,直接看抽象组件的代码吧。
<script>
export default {
name: "imgFix",
abstract: true, //标记为抽象组件
props: {
// 要替换的图片,如果是服务器下的写url地址,public目录下的写地址记得加process.env.BASE_URL,原因请看
// https://www.cnblogs.com/wzcsqaws/p/11283228.html
// assets 目录下,记得用require包裹一下
replaceImg: {
type: String
}
},
created() {
// 为了解决如果replaceImg 也报错就会重复死循环调用error方法
this.replaceObj = {
originalSrc: "",
isReplace: false
};
},
render() {
let replaceObj = this.replaceObj; // 闭包在错误函数里锁住这个对象
let replaceImg = this.replaceImg; // 要替换的图片
let vnode = this.$slots.default[0]; // 子组件的vnode
let that = vnode.context; // 子组件的vm也就是this
let on = vnode.data.on || (vnode.data.on = {}); // 获取img标签的vnode上的绑定事件,没有绑定会为空
let error = on.error; // 获取报错事件
let originalSrc = vnode.data.attrs.src;
if (!originalSrc) {
// 如果动态获取的url为空,这里之间替换为replaceImg
console.log("url is null");
vnode.data.attrs.src = replaceImg;
}
// 写一个error事件防止报错,图片没有替换
function errorFix(e) {
// 已经替换过了,还报错,说明替换的url也有问题,就renturn,避免再次赋值死循环
if (
replaceObj.isReplace &&
replaceObj.originalSrc === originalSrc
) {
console.log("replaceImg is also error");
return;
}
console.log(e, "url is error");
// 注意这里是之间改变dom上的src没有修改vue里的
// 值。就可以解决我上面说的第二个问题
vnode.elm.src = replaceImg;
replaceObj.isReplace = true;
replaceObj.originalSrc = originalSrc;
if (error) {
// 做个兼容,如果原文件也绑定了error事件,在替换图片后也会触发,并且手动绑定上下文和event
// 如果原error事件也改变了url,那么会以原文件的url来显示
error.call(that, e);
}
}
on.error = errorFix;
return vnode;
}
};
</script>
功能上还有一个细节没有处理到位,就是我在抽象组件里改了url,原文件的error事件也改了url,那么如果抽象
组件的url加载快会先显示出来,等error事件的url加载好了再替换,这样子就会闪一下,体验不好,目前的解决
办法是使用抽象组件的开发者通过规范不这么做,但是从代码角度解决最好.
用vue的抽象组件来做一个防止img标签url为空或url地址出错的验证的更多相关文章
- Vue.js 入门:从零开始做一个极简 To-Do 应用
Vue.js 入门:从零开始做一个极简 To-Do 应用 写作时间:2019-12-10版本信息:Vue.js 2.6.10官网文档:https://cn.vuejs.org/ 前言 学习 Vue ...
- 使用ant design vue的日历组件,实现一个简单交易日与非交易日的切换
使用ant design vue的日历组件,实现一个简单交易日与非交易日的切换 需求: 日历区分交易日.非交易日 可以切换面板查看整年交易日信息 可以在手动调整交易日.非交易日 演示实例 序--使用软 ...
- Vue+ElementUI: 手把手教你做一个audio组件
目的 本项目的目的是教你如何实现一个简单的音乐播放器(这并不难) 本项目并不是一个可以用于生产环境的element播放器,所以并没有考虑太多的兼容性问题 本项目不是ElementUI的一个音频插件,只 ...
- 用vue的自定义组件写了一个拖拽 组件,局部的 只能在自定义元素内的
简单实现 没有做兼容<!DOCTYPE html> <html lang="en"> <head> <meta charset=" ...
- vue怎么将一个组件引入另一个组件?
项目是由的vue-cli搭建 1.这里有两个组件,需求是把newComponents.vue里面的东西引入到helloWorld里面 2.index.js里面的配置 3.newComponents里面 ...
- 手把手从零开始---封装一个vue视频播放器组件
现在,在网页上播放视频已经越来越流行,但是网上的资料鱼龙混杂,很难找到自己想要的,今天小编就自己的亲身开发体验,手把手从零开始---封装一个vue视频播放器组件. 作为一个老道的前端搬砖师,怎么可能会 ...
- Vue 入门之组件化开发
Vue 入门之组件化开发 组件其实就是一个拥有样式.动画.js 逻辑.HTML 结构的综合块.前端组件化确实让大的前端团队更高效的开发前端项目.而作为前端比较流行的框架之一,Vue 的组件和也做的非常 ...
- [js高手之路] vue系列教程 - 组件定义与使用上部(7)
组件是vue框架比较核心的内容,那么什么是组件呢? 通俗点讲:组件是由一堆html, css, javascript组成的代码片段, 作用是为了实现模块的重用 组件的基本用法: <div id= ...
- Vue.js使用-组件(下篇)
上一节,我们定义了组件的基本使用,下面我们看看组件其他的一些特性. 1.组件作用域 同时在Vue对象和组件中定义一个属性,显示结果是怎样的呢? <!DOCTYPE html> <ht ...
随机推荐
- 给你的Mac 整个好用的命令行iTerm2 + zsh + oh-my-zsh + powerlevel10k
给你的Mac 整个好用的命令行iTerm2 + zsh + oh-my-zsh + powerlevel10k 介绍 iTerm2 是一个MacOS 下的终端模拟器,和其他的终端本质上没啥大不同.但相 ...
- Lesson 12 Life on a desert island
Lesson 12 Life on a desert island desert island ['dezət 'ailənd] n. 荒岛 uninhabited island coral isla ...
- PHP的图片转base64,base64图片转换为图片并保存代码
打卡记录 1. 图片转base64代码 /*图片转换为 base64格式编码*/ $img = 'images/avatar.jpg'; $base64_img = base64EncodeImage ...
- 【Lucas组合数定理】组合-FZU 2020
组合 FZU-2020 题目描述 给出组合数C(n,m), 表示从n个元素中选出m个元素的方案数.例如C(5,2) = 10, C(4,2) = 6.可是当n,m比较大的时候,C(n,m)很大!于是x ...
- java学习笔记之OOP(二)
java学习笔记二.面向对象[OOP]Object Oriented Programming 一.三大特性: 1.封装:隐藏对象的属性和实现细节,仅对外提供公共访问方式,将变化隔离,便于使用,提高复用 ...
- 第一篇 -- 安装和配置PyQt5
我的电脑环境是:Win10 + Python3.6.4 + JetBrains PyCharm 2017.3.2 x64 之前用tkinter写界面,现在学习如何用PyQt5写界面. 安装PyQt5: ...
- springmvc学习指南 之---第25篇 Spring Bean有三种配置方式
writed by不要张艳涛, 从tomcat转到了springmvc 现在开始有点不知道该看什么书了,看完了springmvc 学习指南之后 又查了一些书,好多都是内容相近,在找书的过程之中,发现s ...
- mysql查看当前连接数
show status like 'Threads%'; 需要root权限才能看到所有的连接
- Winform中生成自动控件
场景: 前几天项目需要模拟数据,但是实际设备还没有接上,就自己用Winform搭建了一个数据模拟器,生成数据给平台.这里又一个需求,就是从数据库中找出设备,然后自动生成控件,勾选就表示开启该设备,能上 ...
- 自学linux——2.认识目录及常用指(命)令
认识目录及常用指(命)令 1.备份: 快照(还原精灵):短期备份 频繁备份 可关可开.可能会影响系统的操作. 备份时:虚拟机--快照 还原时:虚拟机--快照--快照管理器--相应位置--转到 克隆 ...