Vue + ts实现轮播插件的示例


Posted in Javascript onNovember 10, 2020

背景

最近在学习 ts,打算用 ts 写一个练手项目,参照的网站内容是 wanandroid,这个接触过android开发的同学可能更i了解一些,其实一开始是打算后台全部都自己写的,不过奈何一个懒字,所以现在的打算就是自己实现登录注册简单的逻辑。这些都不重要,一开始实现轮播是打算在 vue 中引入轮播图 swiper.js,后来想想还是自己写算了。也当作熟悉 ts。先上效果图(这里没有动态图片,各位同学可以自己实现)

代码已经上传 git,进度比较慢,如果可以各位大佬点个 star。 github.com/jiwenjie/vu…

Vue + ts实现轮播插件的示例

<!-- vue 实现轮播图 -->
<template>
 <div id="swiperDIV" :style="{height: height + 'px'}" @mouseover="suspend" @mouseout="autoPlay" @blur="suspend"
  @focus="autoPlay">
  <!-- 淡入淡出效果 -->
  <transition-group tag="ul" class="img-list" :name="animation">
   <li v-for="(item, index) in bannerList" :key="item.id" v-show="curIndex === index">
    <img :src="item[nameField]">
   </li>
  </transition-group>
  <!-- 操作按钮部分(底部导航器) -->
  <ul class="option-list" v-if="showPagination">
   <li class="option-list-item" :class="curIndex === index ? 'cur-option-style':''"
    v-for="(item, index) in bannerList" :key="item.id" @click="jump(item, index)"></li>
  </ul>

  <!-- 左侧右侧切换按钮 -->
  <template v-if="showBtn">
   <div class="common-btn-space pre-btn-space">
    <span class="common-btn-span pre-btn-span"></span>
   </div>
   <div class="common-btn-space next-btn-space">
    <span class="common-btn-span next-btn-span"></span>
   </div>
  </template>
 </div>
</template>

<!-- ts 文件拆分 -->
<script lang="ts">
 // 两种动画背景
 import {
  Component,
  Prop,
  Vue
 } from 'vue-property-decorator'
 import swiper from './ts/swiper'

 @Component({
  name: 'Swiper',
  mixins: [swiper],
 })
 export default class extends Vue {}

</script>

<!-- 样式文件拆分 -->
<style lang="scss" scoped>
 @import url("./css/swiper.scss");

</style>

ts文件

import {
 Component,
 Prop,
 Vue
} from 'vue-property-decorator'
import { Banner } from '@/beans/index' // 首页banner图
@Component({
 name: 'Swiper',
 components: {},
})
export default class IndexPage extends Vue {
 @Prop({ default: 6000 }) private timeout: number; // 默认的切换banner图的时长
 @Prop({ default: 400 }) private height: number | string; // banner区域高度
 @Prop({ default: () => [] }) private bannerList: Banner[]; // 传入的图片数组
 @Prop({ default: 'imagePath' }) private nameField: string; // 图片地址对应的字段名
 @Prop({ default: true }) private showPagination: boolean; // 是否显示底部原点分页器
 @Prop({ default: false }) private showBtn: boolean; // 是否显示左右的切换按钮
 @Prop({
  default: 'fade', validator: function (value) {
   let arr = ['fade', 'translate']
   return arr.includes(value);
 } }) private animation: string; // 是否显示左右的切换按钮

 private timer: any;
 private curIndex: number = 0;

 created(): void {
  this.autoPlay()
 }

 // lifecycle hook
 mounted(): void {

 }

 // method
 private handleSelect() {

 }

 // 自动播放图片
 private autoPlay() {
  clearInterval(this.timer)//还是一样,开启定时器之前需要先清除一下,防止bug
  this.timer = setInterval(this.nextClick, this.timeout as number)
 }

 // 切换下一个 banner 图片
 private nextClick() {
  this.curIndex++;
  if (this.curIndex >= this.bannerList.length) {
   this.curIndex = 0;
  }
 }

 // 切换上一个图片
 private preClick() {
  this.curIndex++;
  if (this.curIndex >= this.bannerList.length) {
   this.curIndex = 0;
  }
 }

 // 暂停的方法
 private suspend() {
  clearInterval(this.timer)
 }

 // 点击底部原点按钮调整方法
 private jump(bannerItem: Banner, index: number) {
  this.curIndex = index;
 }

 // private animationMethodValidator(): string {

 // }
}

css文件

#swiperDIV {
 position: relative;
 display: block;
 width: 100%;
}

.img-list {
 width: 100%;
 height: 100%;
 position: relative;
 margin: 0;
 padding: 0;
 z-index: 9;
}

.img-list li {
 position: absolute;
 left: 0;
 width: 100%;
 height: 100%;
}

.img-list img {
 width: 100%;
 height: 100%;
}

.option-list {
 position: absolute;
 left: 0;
 right: 0;
 bottom: 10px;
 height: 30px;
 line-height: 30px;
 z-index: 99;
 text-align: center;
}

.option-list-item {
 display: inline-block;
 background-color: rgba(255, 255, 255, .4);
 width: 10px;
 height: 10px;
 border-radius: 50%;
 margin: 0 3px;
 cursor: pointer;
}

.cur-option-style {
 background-color: #fff;
}

.common-btn-space {
 position: absolute;
 top: 0;
 bottom: 0;
 z-index: 99;
 width: 22px;
}

.pre-btn-space {
 left: 20px;
}

.next-btn-space {
 right: 20px;
}

.common-btn-span {
 display: inline-block;
 width: 22px;
 height: 22px;
 background-color: transparent;
 cursor: pointer;
 position: absolute;
 top: 0;
 bottom: 0;
 margin: auto;
 border-top: 2px solid transparent;
 border-right: 2px solid transparent;
 border-bottom: 2px solid red;
 border-left: 2px solid red;
}

.pre-btn-span {
 transform: rotate(45deg);
}

.next-btn-span {
 transform: rotate(-135deg);
}

/* 实现动画的两组类(淡入淡出) */
.fade-enter-active,
.fade-leave-active {
 transition: opacity .6s;
}

.fade-enter,
.fade-leave-to {
 opacity: 0;
}

/* (滚动) */
.translate-enter {
 transform: translateX(100%)
}

.translate-enter-to {
 transition: all .6s ease;
 transform: translateX(0);
}

.translate-leave {
 transform: translateX(0)
}

.translate-leave-active {
 transition: all .6s ease;
 transform: translateX(-100%)
}

很多地方做了配置,包括底部的分页器,左右两侧的按钮。动画目前只实现了两种,一种是淡入淡出,一种是平滑滚动。

这里我把整个 vue 文件做了拆分。有多种原因,一个是我司做项目时整体就是这种拆分,不过我司用的就是正常的 vue 和 js。主要原因就是考虑到页面复杂和逻辑交互很多的时候,一个 vue 文件可能超过万行,所以做了拆分,这里我也延续了这种写法,基本思想其实就是使用 mixins 引入 ts。还有一个原因是 ts 在 vue 文件中会有很多莫名其妙的报错,明明代码没问题,但就是有错误警告。如果提到 ts 文件中就正常,这也是我拆分的一个原因。

其他的功能可以自己在加,如果有问题可以留言,有错误希望各位大佬指正。

以上就是Vue + ts实现轮播插件的示例的详细内容,更多关于Vue + ts 轮播插件的资料请关注三水点靠木其它相关文章!

Javascript 相关文章推荐
IE与Firefox在JavaScript上的7个不同句法分享
Oct 30 Javascript
Express作者TJ告别Node.js奔向Go
Jul 14 Javascript
提交按钮的name='submit'引起的js失效问题及原因
Feb 25 Javascript
表单验证插件Validation应用的实例讲解
Oct 10 Javascript
javascript基于prototype实现类似OOP继承的方法
Dec 16 Javascript
javascript判断图片是否加载完成的方法推荐
May 13 Javascript
jQuery原理系列-css选择器的简单实现
Jun 07 Javascript
微信小程序 animation API详解及实例代码
Oct 08 Javascript
bootstrap——bootstrapTable实现隐藏列的示例
Jan 14 Javascript
js实现无缝滚动图(可控制当前滚动的方向)
Feb 22 Javascript
JS实现全屏预览F11功能的示例代码
Jul 23 Javascript
layer.open 子页面弹出层向父页面传输数据的例子
Sep 26 Javascript
vue router返回到指定的路由的场景分析
Nov 10 #Javascript
如何将Node.js中的回调转换为Promise
Nov 10 #Javascript
vue实现动态给id赋值,点击事件获取当前点击的元素的id操作
Nov 09 #Javascript
jquery实现加载更多&quot;转圈圈&quot;效果(示例代码)
Nov 09 #jQuery
夯基础之手撕javascript继承详解
Nov 09 #Javascript
vue实现动态表格提交参数动态生成控件的操作
Nov 09 #Javascript
es5 类与es6中class的区别小结
Nov 09 #Javascript
You might like
PHP内核介绍及扩展开发指南―基础知识
2011/09/11 PHP
php和js如何通过json互相传递数据相关问题探讨
2013/02/26 PHP
PHP中调用C/C++制作的动态链接库的教程
2016/03/10 PHP
JavaScript 学习笔记 Black.Caffeine 09.11.28
2009/11/30 Javascript
javascript 折半查找字符在数组中的位置(有序列表)
2010/12/09 Javascript
javascript自动给文本url地址增加链接的方法分享
2014/01/20 Javascript
深入理解Javascript中this的作用域
2014/08/12 Javascript
jQuery统计指定子元素数量的方法
2015/03/17 Javascript
jQuery实现仿Alipay支付宝首页全屏焦点图切换特效
2015/05/04 Javascript
JavaScript中数据结构与算法(四):串(BF)
2015/06/19 Javascript
浅谈angular懒加载的一些坑
2016/08/20 Javascript
Vue.js组件使用开发实例教程
2016/11/01 Javascript
js实现用户输入的小写字母自动转大写字母的方法
2017/01/21 Javascript
深入探究angular2 UI组件之primeNG用法
2017/07/26 Javascript
原生JavaScript实现Ajax异步请求
2017/11/19 Javascript
AngularJS基于http请求实现下载php生成的excel文件功能示例
2018/01/23 Javascript
vue通信方式EventBus的实现代码详解
2019/06/10 Javascript
Python中的迭代器漫谈
2015/02/03 Python
用Python实现一个简单的多线程TCP服务器的教程
2015/05/05 Python
用Python操作字符串之rindex()方法的使用
2015/05/19 Python
浅谈Python实现贪心算法与活动安排问题
2017/12/19 Python
scrapy爬虫完整实例
2018/01/25 Python
numpy使用fromstring创建矩阵的实例
2018/06/15 Python
python读取Excel表格文件的方法
2019/09/02 Python
python urllib爬虫模块使用解析
2019/09/05 Python
python保留格式汇总各部门excel内容的实现思路
2020/06/01 Python
Emporio Armani腕表天猫官方旗舰店:乔治·阿玛尼为年轻人设计的副线品牌
2017/07/02 全球购物
综合实践活动总结
2014/05/05 职场文书
环保志愿者活动方案
2014/08/14 职场文书
股东出资证明书(正规版)
2014/09/24 职场文书
2014年监理工作总结范文
2014/11/17 职场文书
获奖感言一句话
2015/07/31 职场文书
初三化学教学反思
2016/02/22 职场文书
2019年家电促销广告语集锦
2019/10/21 职场文书
python基于tkinter制作下班倒计时工具
2021/04/28 Python
windows server2008 开启端口的实现方法
2022/06/25 Servers