vue.js自定义弹出组件插入到body中的实现划词分享功能

本文主要是介绍vue.js自定义弹出组件插入到body中的实现划词分享功能,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

实现效果
在这里插入图片描述

实现原理:

  • 方式一:通过 vue.extend 实现
  • 方式二:通过 new Vue() 实现,本例采用该方法实现,比较简单,即新实例化一个vue对象,单独操作它。其实就是动态创建一个Vue实例对象。

代码实现

<!-- components/pop-share/pop-share.vue -->
<template><!-- 最外层需要一个透明遮罩,监听点击事件 --><div class="mo-mask" :style="{ 'z-index': zIndex }" @click="handleClose"><transition name="el-fade-in-linear"><div class="pop-share" :style="style" @click.stop="handleClick"><div data-value="select" class="pop-share__item"><i class="el-icon-share"></i>选中分享</div><div data-value="all" class="pop-share__item"><i class="el-icon-share"></i>全部分享</div><div data-value="work-weixin" class="pop-share__item"><i class="el-icon-position"></i>发送到企业微信</div><div data-value="search" class="pop-share__item"><i class="el-icon-search"></i>搜索</div></div></transition></div>
</template><script>
// created at 2022-06-21
export default {name: 'pop-share',// 接收参数中可以定义需要接收的参数props: {top: {type: Number | String,default: 0},left: {type: Number | String,default: 0},// 点击事件回调onItemClick: {type: Function,default: null}},components: {},data() {return {zIndex: 0};},computed: {style() {return {top: this.top + 'px',left: this.left + 'px'};}},methods: {async getData() {},handleClick(e) {if (e.target.dataset.value) {if (this.onItemClick) {this.onItemClick({ value: e.target.dataset.value });}this.handleClose();}},handleClose(e) {this.$parent.handleClose();},// js获取当前窗口最大z-indexgetMaxZIndex() {var elements = document.querySelectorAll('*');let maxZindex = 0;for (var i = 0; i < elements.length; i++) {maxZindex = Math.max(maxZindex, elements[i].style.zIndex || 0);}return maxZindex;}},mounted() {// console.log(this.getMaxZIndex() + 1);this.zIndex = this.getMaxZIndex() + 1;},created() {this.getData();}
};
</script><style lang="less">
// 遮罩层
.mo-mask {position: fixed;top: 0;bottom: 0;left: 0;right: 0;width: 100%;height: 100%;background: rgba(0, 0, 0, 0);
}.pop-share {position: fixed;background-color: #373737;color: #fff;display: flex;align-items: center;line-height: 1.5;border-radius: 6px;transform: translate(-50%, -50px);
}.pop-share::after {content: '';position: absolute;top: 100%;left: 50%;transform: translateX(-50%);width: 0;height: 0;border-left: 8px solid transparent;border-right: 8px solid transparent;border-top: 8px solid #373737;
}.pop-share__item {font-size: 12px;line-height: 32px;height: 32px;padding: 0 12px;box-sizing: border-box;color: #dfdfdf;position: relative;cursor: pointer;white-space: nowrap;
}.pop-share__item:not(:last-child)::after {position: absolute;content: '';width: 1px;height: 14px;line-height: 14px;padding: 0;box-sizing: border-box;background-color: #666;top: 50%;right: 0;transform: translateY(-50%);
}
</style><style lang="less" scoped></style>
// components/pop-share/index.js
import Vue from 'vue';
import PopShare from './pop-share.vue';// 所有实例列表
let instances = [];// 显示
function show(props) {console.log('show');// let PopShareVue = Vue.extend(PopShare);// 此处需要使用 propsData传递参数// let instance = new PopShareVue({//   propsData: props// });let instance = new Vue({render(h) {return h(PopShare, { props });},methods: {handleClose() {close(instance);}}});instance.$mount();document.body.appendChild(instance.$el);instances.push(instance);
}// 关闭
function close(instance) {console.log('close');if (instance) {document.body.removeChild(instance.$el);}let index = instances.findIndex(item => item === instance);if (index > -1) {instances.splice(index, 1);}
}function closeAll() {for (let instance of instances) {close(instance);}
}export default {show,close,closeAll
};

将其挂载到Vue实例

// main.js
import Vue from 'vue';
import App from './App.vue';import PopShare from './components/pop-share/index.js';Vue.prototype.$popShare = PopShare;const app = new Vue({render: h => h(App)
}).$mount('#app');

调用弹出分享组件

<!-- App.vue -->
<template><div @mouseup="handleMouseUp" class="meeting-content" v-html="content"></div>
</template><script>
// created at 2022-06-21export default {name: '',data(){return {content: ""}}, 	methods: {handleMouseUp(e) {// 将当前鼠标的坐标传入	this.$popShare.show({top: e.clientY,left: e.clientX,// 点击回调onItemClick: e => {console.log(e);}});}},created() {// this.getData();}
};
</script><style lang="less">
.meeting-content {white-space: pre-wrap;line-height: 1.8;color: #222222;font-size: 14px;&::selection {background-color: #b0d4fc;}
}
</style><style lang="less" scoped></style>

参考

  • vue 自定义组件插入到body中的实现
  • 通过vue.extend实现消息提示弹框
  • js获取当前窗口最大z-index

这篇关于vue.js自定义弹出组件插入到body中的实现划词分享功能的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/516176

相关文章

C++对象布局及多态实现探索之内存布局(整理的很多链接)

本文通过观察对象的内存布局,跟踪函数调用的汇编代码。分析了C++对象内存的布局情况,虚函数的执行方式,以及虚继承,等等 文章链接:http://dev.yesky.com/254/2191254.shtml      论C/C++函数间动态内存的传递 (2005-07-30)   当你涉及到C/C++的核心编程的时候,你会无止境地与内存管理打交道。 文章链接:http://dev.yesky

[职场] 护理专业简历怎么写 #经验分享#微信

护理专业简历怎么写   很多想成为一名护理方面的从业者,但是又不知道应该怎么制作一份简历,现在这里分享了一份护理方面的简历模板供大家参考。   蓝山山   年龄:24   号码:12345678910   地址:上海市 邮箱:jianli@jianli.com   教育背景   时间:2011-09到2015-06   学校:蓝山大学   专业:护理学   学历:本科

大学湖北中医药大学法医学试题及答案,分享几个实用搜题和学习工具 #微信#学习方法#职场发展

今天分享拥有拍照搜题、文字搜题、语音搜题、多重搜题等搜题模式,可以快速查找问题解析,加深对题目答案的理解。 1.快练题 这是一个网站 找题的网站海量题库,在线搜题,快速刷题~为您提供百万优质题库,直接搜索题库名称,支持多种刷题模式:顺序练习、语音听题、本地搜题、顺序阅读、模拟考试、组卷考试、赶快下载吧! 2.彩虹搜题 这是个老公众号了 支持手写输入,截图搜题,详细步骤,解题必备

公共筛选组件(二次封装antd)支持代码提示

如果项目是基于antd组件库为基础搭建,可使用此公共筛选组件 使用到的库 npm i antdnpm i lodash-esnpm i @types/lodash-es -D /components/CommonSearch index.tsx import React from 'react';import { Button, Card, Form } from 'antd'

vue, 左右布局宽,可拖动改变

1:建立一个draggableMixin.js  混入的方式使用 2:代码如下draggableMixin.js  export default {data() {return {leftWidth: 330,isDragging: false,startX: 0,startWidth: 0,};},methods: {startDragging(e) {this.isDragging = tr

[职场] 公务员的利弊分析 #知识分享#经验分享#其他

公务员的利弊分析     公务员作为一种稳定的职业选择,一直备受人们的关注。然而,就像任何其他职业一样,公务员职位也有其利与弊。本文将对公务员的利弊进行分析,帮助读者更好地了解这一职业的特点。 利: 1. 稳定的职业:公务员职位通常具有较高的稳定性,一旦进入公务员队伍,往往可以享受到稳定的工作环境和薪资待遇。这对于那些追求稳定的人来说,是一个很大的优势。 2. 薪资福利优厚:公务员的薪资和

通过SSH隧道实现通过远程服务器上外网

搭建隧道 autossh -M 0 -f -D 1080 -C -N user1@remotehost##验证隧道是否生效,查看1080端口是否启动netstat -tuln | grep 1080## 测试ssh 隧道是否生效curl -x socks5h://127.0.0.1:1080 -I http://www.github.com 将autossh 设置为服务,隧道开机启动

ROS话题通信流程自定义数据格式

ROS话题通信流程自定义数据格式 需求流程实现步骤定义msg文件编辑配置文件编译 在 ROS 通信协议中,数据载体是一个较为重要组成部分,ROS 中通过 std_msgs 封装了一些原生的数据类型,比如:String、Int32、Int64、Char、Bool、Empty… 但是,这些数据一般只包含一个 data 字段,结构的单一意味着功能上的局限性,当传输一些复杂的数据,比如:

时序预测 | MATLAB实现LSTM时间序列未来多步预测-递归预测

时序预测 | MATLAB实现LSTM时间序列未来多步预测-递归预测 目录 时序预测 | MATLAB实现LSTM时间序列未来多步预测-递归预测基本介绍程序设计参考资料 基本介绍 MATLAB实现LSTM时间序列未来多步预测-递归预测。LSTM是一种含有LSTM区块(blocks)或其他的一种类神经网络,文献或其他资料中LSTM区块可能被描述成智能网络单元,因为

vue项目集成CanvasEditor实现Word在线编辑器

CanvasEditor实现Word在线编辑器 官网文档:https://hufe.club/canvas-editor-docs/guide/schema.html 源码地址:https://github.com/Hufe921/canvas-editor 前提声明: 由于CanvasEditor目前不支持vue、react 等框架开箱即用版,所以需要我们去Git下载源码,拿到其中两个主