Vue组件之Tooltip的示例代码


Posted in Javascript onOctober 18, 2017

前言

本文主要Alert 组件的大致框架, 提供少量可配置选项。 旨在大致提供思路

tooltip

常用于展示鼠标 hover 时的提示信息。

模板结构

<template>
 <div style="position:relative;">
  <span ref="trigger">
   <slot>
   </slot>
  </span>
  <div class="tooltip"
   v-bind:class="{
    'top':   placement === 'top',
    'left':  placement === 'left',
    'right':  placement === 'right',
    'bottom': placement === 'bottom',
    'disable': type === 'disable',
    'delete': type === 'delete',
    'visible': show === true 
   }"
   ref="popover"
   role="tooltip">
   <div class="tooltip-arrow"></div>
   <div class="tooltip-inner">
    <slot name="content" v-html="content"></slot>
   </div>
  </div>
 </div>
</template>

大致结构DOM结构 一个div 包含 箭头 及 气泡内容。

v-bind中可选tooltip位置,是否禁用,及显示隐藏

slot 差值供自定义 默认接收content内容

script

import EventListener from '../utils/EventListener.js';

export default {
 props: {
  // 需要监听的事件
  trigger: {
   type: String,
   default: 'click'
  },
  effect: {
   type: String,
   default: 'fadein'
  },
  title: {
   type: String
  },
  // toolTip消息提示
  content: {
   type: String
  },
  header: {
   type: Boolean,
   default: true
  },
  placement: {
   type: String
  }
 },
 data() {
  return {
   // 通过计算所得 气泡位置 
   position: {
    top: 0,
    left: 0
   },
   show: true
  };
 },
 watch: {
  show: function(val) {
   if (val) {
    const popover = this.$refs.popover;
    const triger = this.$refs.trigger.children[0];
    // 通过placement计算出位子
    switch (this.placement) {
     case 'top' :
      this.position.left = triger.offsetLeft - popover.offsetWidth / 2 + triger.offsetWidth / 2;
      this.position.top = triger.offsetTop - popover.offsetHeight;
      break;
     case 'left':
      this.position.left = triger.offsetLeft - popover.offsetWidth;
      this.position.top = triger.offsetTop + triger.offsetHeight / 2 - popover.offsetHeight / 2;
      break;
     case 'right':
      this.position.left = triger.offsetLeft + triger.offsetWidth;
      this.position.top = triger.offsetTop + triger.offsetHeight / 2 - popover.offsetHeight / 2;
      break;
     case 'bottom':
      this.position.left = triger.offsetLeft - popover.offsetWidth / 2 + triger.offsetWidth / 2;
      this.position.top = triger.offsetTop + triger.offsetHeight;
      break;
     default:
      console.log('Wrong placement prop');
    }
    popover.style.top = this.position.top + 'px';
    popover.style.left = this.position.left + 'px';
   }
  }
 },
 methods: {
  toggle() {
   this.show = !this.show;
  }
 },
 mounted() {
  if (!this.$refs.popover) return console.error("Couldn't find popover ref in your component that uses popoverMixin.");
  // 获取监听对象
  const triger = this.$refs.trigger.children[0];
  // 根据trigger监听特定事件
  if (this.trigger === 'hover') {
   this._mouseenterEvent = EventListener.listen(triger, 'mouseenter', () => {
    this.show = true;
   });
   this._mouseleaveEvent = EventListener.listen(triger, 'mouseleave', () => {
    this.show = false;
   });
  } else if (this.trigger === 'focus') {
   this._focusEvent = EventListener.listen(triger, 'focus', () => {
    this.show = true;
   });
   this._blurEvent = EventListener.listen(triger, 'blur', () => {
    this.show = false;
   });
  } else {
   this._clickEvent = EventListener.listen(triger, 'click', this.toggle);
  }
  this.show = !this.show;
 },
 // 在组件销毁前移除监听,释放内存
 beforeDestroy() {
  if (this._blurEvent) {
   this._blurEvent.remove();
   this._focusEvent.remove();
  }
  if (this._mouseenterEvent) {
   this._mouseenterEvent.remove();
   this._mouseleaveEvent.remove();
  }
  if (this._clickEvent) this._clickEvent.remove();
 }
};
// EventListener.js
const EventListener = {
 /**
  * Listen to DOM events during the bubble phase.
  *
  * @param {DOMEventTarget} target DOM element to register listener on.
  * @param {string} eventType Event type, e.g. 'click' or 'mouseover'.
  * @param {function} callback Callback function.
  * @return {object} Object with a `remove` method.
  */
 listen(target, eventType, callback) {
  if (target.addEventListener) {
   target.addEventListener(eventType, callback, false);
   return {
    remove() {
     target.removeEventListener(eventType, callback, false);
    }
   };
  } else if (target.attachEvent) {
   target.attachEvent('on' + eventType, callback);
   return {
    remove() {
     target.detachEvent('on' + eventType, callback);
    }
   };
  }
 }
};

export default EventListener;

封装的事件监听

使用

使用content属性来决定hover时的提示信息。由placement属性决定展示效果:placement属性值为:方向-对齐位置;四个方向:top、left、right、bottom。trigger属性用于设置触发tooltip的方式,默认为hover。

<d-tooltip content="我是tooltip">
 <d-button type="text">鼠标移动到我上面试试</d-button>
</d-tooltip>
<d-tooltip content="我是tooltip" trigger="click">
 <d-button type="text">点我试试</d-button>
</d-tooltip>

content内容分发

设置一个名为content的slot。

<d-tooltip>
 <d-button type="text">鼠标移动到我上面试试</d-button>
 <p slot="content" class="tooltip-content">我是内容分发的conent。</p>
</d-tooltip>

Attributes

参数 说明 类型 可选值 默认值
content 显示的内容,也可以通过 slot#content 传入 DOM String
placement Tooltip 的出现位置 String top/right/bottom/left top
trigger tooltip触发方式 String hover

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
javascript各种复制代码收集
Sep 20 Javascript
图片上传即时显示缩略图的js代码
May 27 Javascript
jQuery 动画弹出窗体支持多种展现方式
Apr 29 Javascript
jQuery获取浏览器中的分辨率实现代码
Apr 23 Javascript
Sort()函数的多种用法
Mar 20 Javascript
js实现登录与注册界面
Nov 01 Javascript
layui树形菜单动态遍历的例子
Sep 23 Javascript
vue-preview动态获取图片宽高并增加旋转功能的实现
Jul 29 Javascript
js实现鼠标点击飘爱心效果
Aug 19 Javascript
详解微信小程序动画Animation执行过程
Sep 23 Javascript
手动实现vue2.0的双向数据绑定原理详解
Feb 06 Vue.js
js面向对象编程OOP及函数式编程FP区别
Jul 07 Javascript
JS正则表达式完美实现身份证校验功能
Oct 18 #Javascript
详解vue项目首页加载速度优化
Oct 18 #Javascript
JS简单实现滑动加载数据的方法示例
Oct 18 #Javascript
详解cordova打包成webapp的方法
Oct 18 #Javascript
prototype.js简单实现ajax功能示例
Oct 18 #Javascript
浅谈JS函数节流防抖
Oct 18 #Javascript
用vue封装插件并发布到npm的方法步骤
Oct 18 #Javascript
You might like
双料怀旧--SHARP GF515的维护、修理和简单调试
2021/03/02 无线电
如何在WIN2K下安装PHP4.04
2006/10/09 PHP
PHP 获取远程文件内容的函数代码
2010/03/24 PHP
PHP数据库调用类调用实例(详细注释)
2012/07/12 PHP
php发送get、post请求的6种方法简明总结
2014/07/08 PHP
php登录超时检测功能实例详解
2017/03/21 PHP
使用TextRange获取输入框中光标的位
2006/10/14 Javascript
Div自动滚动到末尾的代码
2008/10/26 Javascript
推荐30个新鲜出炉的精美 jQuery 效果
2012/03/26 Javascript
jquery实现更改表格行顺序示例
2014/04/30 Javascript
jQuery表格插件datatables用法汇总
2016/03/29 Javascript
js css+html实现简单的日历
2016/07/14 Javascript
JQuery之proxy实现绑定代理方法
2016/08/01 Javascript
js 判断登录界面的账号密码是否为空
2017/02/08 Javascript
详解Vuex中mapState的具体用法
2017/09/28 Javascript
获取本机IP地址的实例(JavaScript / Node.js)
2017/11/24 Javascript
详解React Native 屏幕适配(炒鸡简单的方法)
2018/06/11 Javascript
js操作table中tr的顺序实现上移下移一行的效果
2018/11/22 Javascript
nodejs基础之buffer缓冲区用法分析
2018/12/26 NodeJs
为nuxt项目写一个面包屑cli工具实现自动生成页面与面包屑配置
2019/09/29 Javascript
Vue 组件注册全解析
2020/12/17 Vue.js
[01:09]模型精美,特效酷炫!TI9不朽宝藏Ⅰ鉴赏
2019/05/10 DOTA
初步剖析C语言编程中的结构体
2016/01/16 Python
Python PyQt5标准对话框用法示例
2017/08/23 Python
简单了解Python中的几种函数
2017/11/03 Python
django 实现电子支付功能的示例代码
2018/07/25 Python
Pycharm简单使用教程(入门小结)
2019/07/04 Python
Django实现将views.py中的数据传递到前端html页面,并展示
2020/03/16 Python
Python使用struct处理二进制(pack和unpack用法)
2020/11/12 Python
HTML5 canvas基本绘图之绘制曲线
2016/06/27 HTML / CSS
常用的HTML5列表标签
2017/06/20 HTML / CSS
HTML5表单验证特性(知识点小结)
2020/03/10 HTML / CSS
HelloFresh澳大利亚:订购你的美味食品盒、健康餐食
2018/03/28 全球购物
新党章心得体会
2014/09/04 职场文书
人事任命通知
2015/04/20 职场文书
原来实习报告是这样写的呀!
2019/07/03 职场文书