vue实现页面加载动画效果


Posted in Javascript onSeptember 19, 2017

我们经常看到数据未出现时,页面中会有一条提示消息, 页面正在加载中,如何实现该效果呢 ,请看下面代码

<template>
 <section class="page" v-if="option" 
  :style="{background: option.background,color: option.color||'#fff'}"  
  :class="{'page-before': option.index < currentPage,
    'page-after': option.index > currentPage,
    'page-current': option.index === currentPage}">
  <div :class="{'all-center': option.isCenter}">
   <slot></slot>
  </div>
 </section>
 <section class="page" v-else>页面正在渲染中。。。</section>
</template>

有木有感觉很简单
下面上点干货,实现页面的动画效果

<template>
 <nav class="controller">
  <button v-if="option.arrowsType" class="prev-btn" :class="{moving:option.arrowsType === 'animate'}" @click="changePage(prevIndex)"></button>
  <ul v-if="option.navbar">
   <li v-for="index in pageNum" @click="changePage(index)" :class="{current:option.highlight && index === currentPage}" :key="'controller-'+index" :data-index="index" class="controller-item"></li>
  </ul>
  <button v-if="option.arrowsType" class="next-btn" :class="{moving:option.arrowsType === 'animate'}" @click="changePage(nextIndex)"></button>
 </nav>
</template>

<script>
export default {
 name: 'page-controller',
 props: {
 pageNum: Number,
 currentPage: Number,
 option: {
  type: Object,
  default: {
  arrowsType: 'animate',
  navbar: true,
  highlight: true,
  loop: true  //是否开启滚动循环
  }
 }
 },
 methods: {
 changePage (index) {
  this.$emit('changePage', index);
 }
 },
 computed: {
 nextIndex () {
  if (this.currentPage === this.pageNum) {
  if(this.option.loop){
   return 1
   }else{
   return this.pageNum
   }
  } else {
  return this.currentPage + 1;
  }
 },
 prevIndex () {
  if (this.currentPage === 1) {
  if(this.option.loop){
   return this.pageNum
   }else{
   return 1
   }
  } else {
  return this.currentPage - 1;
  }
 }
 },
 created () {
 if (this.option.navbar === undefined) {
  this.option.navbar = true;
 }
 },
 mounted () {
 let _this = this;
 let timer = null;
 let start = 0;
 // 滚轮处理
 function scrollHandler (direction) {
  // 防止重复触发滚动事件
  if (timer != null) {
  return;
  }
  if (direction === 'down') {
  _this.changePage(_this.nextIndex);
  } else {
  _this.changePage(_this.prevIndex);
  }
  timer = setTimeout(function() {
  clearTimeout(timer);
  timer = null;
  }, 300);
 }
 // if (Object.hasOwnProperty.call(window,'onmousewheel')) {
 if (Object.hasOwnProperty.call(window,'onmousewheel')) {
  // 监听滚轮事件
  window.addEventListener('mousewheel',function (event) { // IE/Opera/Chrome
  let direction = event.wheelDelta > 0 ? 'up':'down';
  scrollHandler(direction);
  },false);
 } else {
  window.addEventListener('DOMMouseScroll',function (event) { // Firefox
  let direction = event.detail > 0 ? 'up':'down';
  scrollHandler(direction);
  },false);
 }
 // 移动端触摸事件处理
 window.addEventListener('touchstart', function (event) {
  start = event.touches[0].clientY;
 })
 window.addEventListener('touchmove', function (event) {
  event.preventDefault();
 })
 window.addEventListener('touchend', function (event) {
  let spacing = event.changedTouches[0].clientY - start;
  let direction;  
  if (spacing > 50) {
  direction = 'up';
  scrollHandler(direction);
  } else if (spacing < -50) {
  direction = 'down';
  scrollHandler(direction);
  }
 })
 }
}
</script>

<style scoped>
.controller {
 position: fixed;
 right: 20px;
 top: 50%;
 z-index: 99;
}
.controller ul {
 transform: translate3d(0,-50%,0);
 list-style: none;
 margin: 0;
 padding: 0;
}
.controller-item {
 cursor: pointer;
 width: 20px;
 height: 20px;
 border-radius: 50%;
 margin-top: 10px;
 background-color: rgba(255, 255, 255, 0.3);
 transition: background-color 0.3s ease 0s;
}
.controller-item:hover {
 background-color: rgba(255, 255, 255, 0.7);
}
.controller-item.current {
 background-color: rgba(255, 255, 255, 1);
}
.prev-btn,.next-btn {
 cursor: pointer;
 display: block;
 text-align: center;
 width: 20px;
 height: 20px;
 position: fixed;
 left: 50%;
 margin-left: -10px;
 border: 4px solid #fff;
 background-color: transparent;
 outline: none;
}
.prev-btn {
 top: 80px;
 transform: rotate(-45deg);
 border-bottom-color: transparent;
 border-left-color: transparent;
}
.next-btn {
 bottom: 80px;
 transform: rotate(45deg);
 border-top-color: transparent;
 border-left-color: transparent;
}
.prev-btn.moving {
 animation: prev-up-down 0.7s linear 0s infinite;
}
.next-btn.moving {
 animation: next-up-down 0.7s linear 0s infinite;
}
@keyframes next-up-down {
 0% {
 transform: translate3d(0,0,0) rotate(45deg);
 }
 25% {
 transform: translate3d(0,6px,0) rotate(45deg);
 }
 50% {
 transform: translate3d(0,0,0) rotate(45deg);
 }
 75% {
 transform: translate3d(0,-6px,0) rotate(45deg);
 }
 100% {
 transform: translate3d(0,0,0) rotate(45deg);
 }
}
@keyframes prev-up-down {
 0% {
 transform: translate3d(0,0,0) rotate(-45deg);
 }
 25% {
 transform: translate3d(0,-6px,0) rotate(-45deg);
 }
 50% {
 transform: translate3d(0,0,0) rotate(-45deg);
 }
 75% {
 transform: translate3d(0,6px,0) rotate(-45deg);
 }
 100% {
 transform: translate3d(0,0,0) rotate(-45deg);
 }
}
</style>

本文已被整理到了《Vue.js前端组件学习教程》,欢迎大家学习阅读。

关于vue.js组件的教程,请大家点击专题vue.js组件学习教程进行学习。

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

Javascript 相关文章推荐
javascript动画效果类封装代码
Aug 28 Javascript
图像替换新技术 状态域方法
Jan 28 Javascript
node.js中的fs.createWriteStream方法使用说明
Dec 17 Javascript
JS简单实现多级Select联动菜单效果代码
Sep 06 Javascript
JS组件Bootstrap dropdown组件扩展hover事件
Apr 17 Javascript
BootStrap的Datepicker控件使用心得分享
May 25 Javascript
微信小程序 教程之wxapp视图容器 swiper
Oct 19 Javascript
利用Mongoose让JSON数据直接插入或更新到MongoDB
May 03 Javascript
react项目实践之webpack-dev-serve
Sep 14 Javascript
35个最好用的Vue开源库(史上最全)
Jan 03 Javascript
小程序二次贝塞尔曲线实现购物车商品曲线飞入效果
Jan 07 Javascript
基于Vue实现平滑过渡的拖拽排序功能
Jun 12 Javascript
深入理解Node.js中通用基础设计模式
Sep 19 #Javascript
微信小程序媒体组件详解(视频,音乐,图片)
Sep 19 #Javascript
Javascript中将变量转换为字符串的三种方法
Sep 19 #Javascript
详解JS中的this、apply、call、bind(经典面试题)
Sep 19 #Javascript
JavaScript 中的 this 简单规则
Sep 19 #Javascript
在 Node.js 中使用原生 ES 模块方法解析
Sep 19 #Javascript
Webpack 服务器端代码打包的示例代码
Sep 19 #Javascript
You might like
ThinkPHP php 框架学习笔记
2009/10/30 PHP
php 分库分表hash算法
2009/11/12 PHP
PHP仿博客园 个人博客(1) 数据库与界面设计
2013/07/05 PHP
php实现memcache缓存示例讲解
2013/12/04 PHP
PHP实现采集中国天气网未来7天天气
2014/10/15 PHP
分享下php5类中三种数据类型的区别
2015/01/26 PHP
解决Extjs 4 Panel作为Window组件的子组件时出现双重边框问题
2013/01/11 Javascript
超链接怎么正确调用javascript函数
2016/05/23 Javascript
Jquery on方法绑定事件后执行多次的解决方法
2016/06/02 Javascript
jquery插件autocomplete用法示例
2016/07/01 Javascript
angularjs 表单密码验证自定义指令实现代码
2016/10/27 Javascript
探讨跨域请求资源的几种方式(总结)
2016/12/02 Javascript
微信小程序实现瀑布流布局与无限加载的方法详解
2017/05/12 Javascript
Vue.set()实现数据动态响应的方法
2018/02/07 Javascript
Vuejs 实现简易 todoList 功能 与 组件实例代码
2018/09/10 Javascript
微信小程序使用二次贝塞尔曲线画波浪
2018/12/25 Javascript
Vue实例的对象参数options的几个常用选项详解
2019/11/08 Javascript
ant-design-vue 快速避坑指南(推荐)
2020/01/21 Javascript
微信小程序canvas开发水果老虎机的思路详解
2020/02/07 Javascript
Vue父组件监听子组件生命周期
2020/09/03 Javascript
python简单分割文件的方法
2015/07/30 Python
学习python类方法与对象方法
2016/03/15 Python
详解Python如何获取列表(List)的中位数
2016/08/12 Python
python编写简易聊天室实现局域网内聊天功能
2018/07/28 Python
python 判断三个数字中的最大值实例代码
2019/07/24 Python
Python中qutip用法示例详解
2020/10/02 Python
python使用scapy模块实现ARP扫描的过程
2021/01/21 Python
英国工具中心:UK Tool Centre
2017/07/10 全球购物
美国市场上最实惠的送餐服务:Dinnerly
2018/03/18 全球购物
乌克兰品牌化妆品和香水在线商店:Bomond
2020/01/14 全球购物
无刑事犯罪记录证明范本
2014/09/29 职场文书
2014年基层党支部工作总结
2014/12/04 职场文书
2015年学校党支部工作总结
2015/04/01 职场文书
解决jupyter notebook启动后没有token的坑
2021/04/24 Python
教你用Python爬取英雄联盟皮肤原画
2021/06/13 Python
Java获取字符串编码格式实现思路
2022/09/23 Java/Android