vue2企业级项目(六)
vue2企业级项目(六)
自定义指令
-
创建
src/directive/index.js
const directives = require.context("./modules", true, /\.js$/);export default {install: (Vue) => {directives.keys().forEach((key) => {let directive = directives(key).default;let name = key.replace(/^\.\/(.*)\.\w+$/, "$1");directive && Vue.directive(name, directive);});}, };
-
main.js
注入使用import directives from "./directive";...Vue.use(directives);
-
创建
src/directive/modules
目录
1、v-loading
element-ui
有,就不需要
2、v-draggable
创建src/directive/draggable.js
import { checkDataType } from "@/utils/utils";
let recoverStyle = null;export default {update(el, binding) {let config = binding.value;let visible = false;let target = ".el-dialog__header";let control = ".el-dialog";if (checkDataType(config, "object")) {visible = config.visible;target = config.target;control = config.control;} else {visible = config;}const dialogHeaderEl = el.querySelector(target);const dragDom = el.querySelector(control);dialogHeaderEl.style.cursor = "move";function readStyle(dom, attr) {if (document.body.currentStyle) return dom.currentStyle[attr];return getComputedStyle(dom, false)[attr];}if (visible) {recoverStyle = {left: readStyle(dragDom, "left"),top: readStyle(dragDom, "top"),margin: readStyle(dragDom, "margin"),};dialogHeaderEl.onmousedown = function(e) {// 获取鼠标相对当前元素内部位置const disX = e.clientX - dragDom.offsetLeft;const disY = e.clientY - dragDom.offsetTop;// 获取当前窗口视图大小const screenWidth = document.body.clientWidth;const screenHeight = document.documentElement.clientHeight;// 获取当前元素大小const dragDomWidth = dragDom.offsetWidth;const dragDomheight = dragDom.offsetHeight;// 计算获取最大偏移量const maxLeft = screenWidth - dragDomWidth;const maxTop = screenHeight - dragDomheight;document.onmousemove = function(e) {let left = e.clientX - disX;let top = e.clientY - disY;// 碰撞判断if (left <= 0) left = 0;if (left >= maxLeft) left = maxLeft;if (top <= 0) top = 0;if (top >= maxTop) top = maxTop;left = ((left * 100) / screenWidth).toFixed(2) + "%";top = ((top * 100) / screenHeight).toFixed(2) + "%";dragDom.style.left = left;dragDom.style.top = top;dragDom.style.margin = 0;};document.onmouseup = function() {document.onmousemove = null;document.onmouseup = null;};};} else {// 还原初始化的样式dragDom.style.left = recoverStyle.left;dragDom.style.top = recoverStyle.top;dragDom.style.margin = recoverStyle.margin;dialogHeaderEl.onmousedown = null;recoverStyle = null;}},
};
3、v-click-outside
创建src/directive/click-outside.js
export default {bind(el, binding) {// 点击事件回调函数const onClickOutside = (event) => {if (!(el === event.target || el.contains(event.target))) {binding.value(event);}};// 将回调函数绑定到元素上el._clickOutsideCallback = onClickOutside;// 添加点击事件监听器document.addEventListener("click", onClickOutside);},unbind(el) {// 移除点击事件监听器document.removeEventListener("click", el._clickOutsideCallback);delete el._clickOutsideCallback;},
};
4、v-ripple
(简单的)
创建src/directive/ripple.js
function createRipple(el, radius, color, disX, disY) {new Promise((resolve) => {const rippleDom = document.createElement("span");rippleDom.className = "ripple";rippleDom.setAttribute("style",`display: block;position: absolute;border-radius: 50%;transform: translate(-50%, -50%) scale(0);transition: 0.5s;background-color: ${color || "rgba(0, 0, 0, 0.6)"};top: ${disY}px;left: ${disX}px;width: ${radius * 3}px;height: ${radius * 3}px;animation: ripple-animation 0.5s linear;`,);el.appendChild(rippleDom);let timer = setTimeout(() => {el.removeChild(rippleDom);resolve(timer);}, 520);}).then((timer) => {clearTimeout(timer);});
}function rippleShow(e) {const targetDom = e.target;const radius =targetDom.offsetHeight > targetDom.offsetWidth? targetDom.offsetHeight: targetDom.offsetWidth;const disX = e.clientX - targetDom.offsetLeft;const disY = e.clientY - targetDom.offsetTop;createRipple(targetDom, radius, e?._ripple, disX, disY);
}export default {bind(el, binding) {el._ripple = binding.value;el.style.position = "relative";el.style.overflow = "hidden";el.style.userSelect = "none";el.addEventListener("mousedown", rippleShow);},unbind(el) {el._ripple = null;el.removeEventListener("mousedown", rippleShow);},
};
创建src/styles/animation.less
,并在scr/styles/index.less
内引入
// ripple动画
@keyframes ripple-animation {to {transform: translate(-50%, -50%) scale(1);opacity: 0;}
}
5、v-intersect
交叉观察者
创建src/directive/intersect.js
export default {bind(el, binding) {let info = null;let callback = null;if (typeof binding.value === "object") {info = binding.value?.info;callback = binding.value?.callback;} else {callback = binding.value;}const observer = new IntersectionObserver((entries) => {entries.forEach((entry) => {if (entry.isIntersecting) {callback && callback(info);}});},{ root: el.parentElement },);observer.observe(el);},
};
6、v-scroll
滚动监听
创建src/directive/scroll.js
export default {bind(el, binding) {el.onscroll = function() {binding.value({x: el.scrollLeft,y: el.scrollTop,});};},unbind(el) {el.onscroll = null;},
};
7、v-scroll-to
滚动设置
创建src/directive/scroll-to.js
export default {update(el, binding) {let x = binding.modifiers?.x || false;if (binding.value && binding.value === binding.oldValue) return;if (typeof binding.value === "number") {x ? (el.scrollLeft = binding.value) : (el.scrollTop = binding.value);} else if (typeof binding.value === "string") {let targetDom = document.querySelector(binding.value);if (x) {let border = getComputedStyle(el, false)["borderLeftWidth"];let padding = getComputedStyle(el, false)["paddingLeft"];border = border.replace("px", "");padding = padding.replace("px", "");el.scrollLeft = targetDom.offsetLeft - el.offsetLeft - border - padding;} else {let border = getComputedStyle(el, false)["borderTopWidth"];let padding = getComputedStyle(el, false)["paddingTop"];border = border.replace("px", "");padding = padding.replace("px", "");el.scrollTop = targetDom.offsetTop - el.offsetTop - border - padding;}}},
};
8、v-auto-scroll
自动滚动
创建src/directive/scroll-auto.js
function active(el, scroll, step, max, x) {window.requestAnimationFrame(() => {x ? (el.scrollLeft = scroll) : (el.scrollTop = scroll);scroll += step;if (scroll >= max) scroll = 0 + step;active(el, scroll, step, max, x);});
}export default {inserted(el, binding) {const x = binding.modifiers?.x || false;let step = 0;let scroll = 0;if (typeof binding.value === "object") {step = binding.value?.step || 5;scroll = binding.value?.begin || 0;} else {step = binding.value || 5;}const scrollMax = x ? el.scrollWidth : el.scrollHeight;el._children = [].slice.call(el.children);el._children.forEach((child) => {el.appendChild(child.cloneNode(true));});active(el, scroll, step, scrollMax, x);},unbind(el) {el.innerHtml = "";let children = [].slice.call(el.children);children.forEach((child) => {el.removeChild(child);});el._children.forEach((child) => {el.appendChild(child.cloneNode(true));});},
};
相关文章:

vue2企业级项目(六)
vue2企业级项目(六) 自定义指令 创建src/directive/index.js const directives require.context("./modules", true, /\.js$/);export default {install: (Vue) > {directives.keys().forEach((key) > {let directive directives(key…...

OSPF的选路原则
域内 --- 1类,2类LSA 域间 --- 3类LSA 域外 --- 5类,7类LSA --- 根据开销值的计算规则不同,还分为类型1和类型2 1.如果学到的路由都是通过1类,2类LSA获取的域内路由 --- 这种情况直接比较开销值,优先选择开销值小的路…...

4.操作元素属性
4.1操作元素常用属性 ●通过 JS 设置/修改 标签元素属性,比如通过src更换图片 ●最常见的属性比如:href、 title、 src 等 ●语法: 对象.属性 值【示例】 // 1.获取元素 const pic document.querySelector( img ) // 2.操作元素 pic.src ./images/b…...

uniapp 微信小程序:v-model双向绑定问题(自定义 props 名无效)
uniapp 微信小程序:v-model双向绑定问题(自定义 props 名无效) 前言问题双向绑定示例使用 v-model使用 v-bind v-on使用 sync 修饰符 参考资料 前言 VUE中父子组件传递数据的基本套路: 父传子 props子传父 this.$emit(事件名, …...

【Lua学习笔记】Lua进阶——Table(3) 元表
接上文 文章目录 元表__tostring__call__index__newindex运算符元方法其它元表操作 元表 Q:为什么要使用元表? A:在Lua中,常常会需要表与表之间的操作。元表中提供了一些元方法,通过自定义元方法可以实现想要的功能&…...

AI编程常用工具 Jupyter Notebook
点击上方蓝色字体,选择“设为星标” 回复”云原生“获取基础架构实践 深度学习编程常用工具 我们先来看 4 个常用的编程工具:Sublime Text、Vim、Jupyter。虽然我介绍的是 Jupyter,但并不是要求你必须使用它,你也可以根据自己的喜…...

RocketMQ重复消费的解决方案::分布式锁直击面试!
文章目录 场景分析方法的幂等分布式锁Redis实现分布式锁抢锁的设计思路 分布式锁案例 直击面试rocketmq什么时候重复消费消息丢失的问题消息在哪里丢失发送端确保发送成功并且配合失败的业务处理消费端确保消息不丢失rocketmq 主从同步刷盘 场景分析 分布式系统架构中,队列是分…...

如何降低TCP在局域网环境下的数据传输延迟
以Ping为例。本案例是一个测试题目,只有现象展示,不含解决方案。 ROS_Kinetic_26 使用rosserial_windows实现windows与ROS master发送与接收消息_windows 接收ros1 消息 什么是ping? AI: ping是互联网控制消息协议(…...

【LeetCode】78.子集
题目 给你一个整数数组 nums ,数组中的元素 互不相同 。返回该数组所有可能的子集(幂集)。 解集 不能 包含重复的子集。你可以按 任意顺序 返回解集。 示例 1: 输入:nums [1,2,3] 输出:[[],[1],[2],[1…...

认可功能介绍 - 技术声誉靠认可
需求 大家在学习和工作中, 经常碰到一些热心帮助自己的人, 我们怎么向他们表示感谢呢? 各位博主在 CSDN 也做了很多贡献,也有不少用户在做各种各样的社区活动,这些活动给我们的领军人物什么回馈呢? 这些…...

EtherNet/IP转CAN网关can协议标准
生产管理设备中,会有设备与其他设备的协议不同,数据无法互通,让你的工作陷入困境。这时,一款神奇的产品出现了——远创智控YC-EIP-CAN通讯网关! 1, 这款通讯网关采用ETHERNET/IP从站功能,可以将各种CAN总线…...

解决代理IP负载均衡与性能优化的双重挑战
在当今数字化时代,代理IP的应用范围日益广泛,它不仅在数据爬取、网络抓取等领域发挥着重要作用,也成为网络安全和隐私保护的有力工具。然而,面对庞大的数据流量和复杂的网络环境,如何实现代理IP的负载均衡和性能优化成…...

深度探索 Elasticsearch 8.X:function_score 参数解读与实战案例分析
在 Elasticsearch 中,function_score 可以让我们在查询的同时对搜索结果进行自定义评分。 function_score 提供了一系列的参数和函数让我们可以根据需求灵活地进行设置。 近期有同学反馈,function_score 的相关参数不好理解,本文将深入探讨 f…...

测牛学堂:软件测试之andorid app性能测试面试知识点总结(二)
APP性能测试指标之FPS 如果经常玩游戏的同学应该听过FPS。 FPS本来是图像领域中的概念,是指画面每秒传输的帧数。每秒钟帧数越多,所显示的动作就会越流畅。 但是因为功耗的限制,一般60fps就是跑满的效果了。 我们测试的话,一般…...

尚医通06:数据字典+EasyExcel+mongodb
内容介绍 1、数据字典列表前端 2、EasyExcel介绍、实例 3、数据字典导出接口、前端 4、数据字典导入接口、前端 5、数据字典添加redis缓存 6、MongoDB简介 7、MongoDB安装 8、MongoDB基本概念 数据字典列表前端 1、测试问题 (1)报错日志 &am…...

【前端知识】React 基础巩固(三十二)——Redux的三大原则、使用流程及实践
React 基础巩固(三十二)——Redux的三大原则 一、Redux的三大原则 单一数据源 整个应用程序的state被存储在一颗object tree 中,并且这个object tree 只存储在一个store中;Redux并没有强制让我们不能创建多个Store,但是那样做不利于数据维护…...

[NLP]使用Alpaca-Lora基于llama模型进行微调教程
Stanford Alpaca 是在 LLaMA 整个模型上微调,即对预训练模型中的所有参数都进行微调(full fine-tuning)。但该方法对于硬件成本要求仍然偏高且训练低效。 [NLP]理解大型语言模型高效微调(PEFT) 因此, Alpaca-Lora 则是利用 Lora…...

Linux Shell 脚本编程学习之【第5章 文件的排序、合并与分割 (第四部分之cut命令) 】
第5章 文件的排序、合并与分割 (第四部分之cut命令) 4 cut 命令4.1 选项及其意义4.2 输出字符 (-c)4.3 改变分隔符(-d)和提取特定域(-f) 5 paste 命令5.1 paste 命令选项及其意义5.2…...

php-golang-rpc jsonrpc和php客户端tivoka/tivoka包实践
golang 代码: package main import ( "fmt" "net" "net/rpc" "net/rpc/jsonrpc" ) type App struct{} type Res struct { Code int json:"code" Msg string json:"msg" Data any json:"…...

flutter 打包iOS安装包
flutter iOS Xcode打包并导出ipa文件安装包 1、 Xcode配置 1、 启动打包 1、 等待打包 1、 打包完成、准备导出ipa 1、 选择模式 1、 选择配置文件 1、 导出 1、 选择导出位置 1、 得到ipa...

二进制重排
二进制重排作用 二进制重排的主要目的是将连续调用的函数连接到相邻的虚拟内存地址,这样在启动时可以减少缺页中断的发生,提升启动速度。目前网络上关于ios应用启动优化,通过XCode实现的版本比较多。MacOS上的应用也是通过clang进行编译的&am…...

【Linux后端服务器开发】MAC地址与其他重要协议
目录 一、以太网 二、MAC地址 三、MTU 四、ARP协议 五、DNS系统 六、ICMP协议 七、NAT技术 八、代理服务器 一、以太网 “以太网”不是一种具体的网路,而是一种技术标准:既包含了数据链路层的内容,也包含了一些物理层的内容…...

WebGPU入门
1. 引言 前序博客: CUDA入门WebGPUZKP:客户端证明 WebGPU——Draft 2023.7.17 由苹果、谷歌、Mozilla团队发起,当前处于草稿阶段,旨在成为W3C推荐标准。 WebGPU为 在图形处理单元(GPU)上执行诸如渲染和…...

React Dva项目中.roadhogrc.mock.js直接自动导入mock目录下所有文件方式
上文 React Dva项目中模仿网络请求数据方法 中,我们书写了Dva项目模拟后端数据的方式 但是 我们.roadhogrc.mock.js中的这个处理其实并不好用 我们还需要一个一个的引入 我们可以直接靠一段代码 import fs from fs; import path from path; const mock {} fs.re…...

跨境独立站如何应对恶意网络爬虫?
目录 跨境出海独立站纷纷成立 爬虫威胁跨境电商生存 如何有效识别爬虫? 技术反爬方案 防爬虫才能保发展 中国出海跨境电商业务,主要选择大平台开设店铺,例如,亚马逊、eBay、Walmart、AliExpress、Zalando等。随着业务的扩大&…...

C# SourceGenerator 源生成器初探
简介 注意: 坑极多。而且截至2023年,这个东西仅仅是半成品 利用SourceGenerator可以在编译结束前生成一些代码参与编译,比如编译时反射之类的,还有模板代码生成都很好用。 演示仓库传送门-Github-yueh0607 使用 1. 创建项目 …...

网络安全/信息安全—学习笔记
一、网络安全是什么 网络安全可以基于攻击和防御视角来分类,我们经常听到的 “红队”、“渗透测试” 等就是研究攻击技术,而“蓝队”、“安全运营”、“安全运维”则研究防御技术。 无论网络、Web、移动、桌面、云等哪个领域,都有攻与防两面…...

【Visual Studio】无法打开包括文件: “dirent.h”: No such file or directory
VS2017/2019 无法打开包括文件: “dirent.h”: No such file or directory 1 “dirent.h”: No such file or directory 在windows下的VS2017/2019编译器中,发现无法打开“dirent.h”,主要是MSVC并没有实现这个头文件,但是在Linux这个头文件…...

asp.net MVC markdown编辑器
在 ASP.NET MVC 中,你可以使用一些第三方 Markdown 编辑器来让用户在网页上方便地编辑和预览 Markdown 内容。这些编辑器通常提供实时预览功能,将 Markdown 文本转换为实时渲染的 HTML,并支持编辑器工具栏来辅助用户编辑。 以下是一些流行的…...

论文浅尝 | 预训练Transformer用于跨领域知识图谱补全
笔记整理:汪俊杰,浙江大学硕士,研究方向为知识图谱 链接:https://arxiv.org/pdf/2303.15682.pdf 动机 传统的直推式(tranductive)或者归纳式(inductive)的知识图谱补全(KGC)模型都关注于域内(in-domain)数据,而比较少关…...