全网整合营销服务商

电脑端+手机端+微信端=数据同步管理

免费咨询热线:400-708-3566

实现一个简单的vue无限加载指令方法

vue 中的自定义指令是对底层 dom 进行操作,下面以实现滚动到底部加载数据,实现无限加载来介绍如何自定义一个简单的指令。

无限加载的原理是通过对滚动事件的监听,每一次滚动都要获取到已滚动的距离,如果滚动的距离加上浏览器窗口高度,会大于等于内容高度,就触发函数加载数据。

先介绍不使用 vue 的情况如何实现无限加载。

不使用框架

首先是html:

<!DOCTYPE html><html lang="en">
<head><meta charset="UTF-8">
<title>实现滚动加载</title>
<style>
 * {
  -webkit-box-sizing: border-box;
  -moz-box-sizing: border-box;
  box-sizing: border-box;
  }
 li, ul {
  list-style: none;
 }
 .container {
  width: 980px;
  margin: 0 auto;
 }
 .news__item {
  height: 80px;
  margin-bottom: 20px;
  border: 1px solid #eee;
 }</style>
</head>
<body>
<div class="container">
 <ul class="news" id="news">
  <li class="news__item">1、hello world</li>
  <li class="news__item">2、hello world</li>
  <li class="news__item">3、hello world</li>
  <li class="news__item">4、hello world</li>
  <li class="news__item">5、hello world</li>
  <li class="news__item">6、hello world</li>
  <li class="news__item">7、hello world</li>
  <li class="news__item">8、hello world</li>
  <li class="news__item">9、hello world</li>
  <li class="news__item">10、hello world</li>
 </ul>
</div>
</body>
</html>

打开浏览器,调整下浏览器窗口高度,让页面可以滚动。

先了解三个变量

  • document.body.scrollTop 滚动条滚动的距离
  • window.innerHeight 浏览器窗口高度
  • document.body.clientHeight 内容高度

对应上面的原理就是

window.addEventListener('scroll', function() {
 var scrollTop = document.body.scrollTop;
 if(scrollTop + window.innerHeight >= document.body.clientHeight) {
  // 触发加载数据    
  loadMore();
 }
});
function loadMore() {
 console.log('加载数据')'
}

loadMore() 函数就是从接口获取到数据,组装 html,插入到原先到节点后面。

// 表示列表的序号
var index = 10;
function loadMore() {
 var content = '';
 for(var i=0; i< 10; i++) {
  content += '<li class="news__item">'+(++index)+'、hello world</li>'  
 }
 var node = document.getElementById('news');
 // 向节点内插入新生成的数据  
 var oldContent =   node.innerHTML;
 node.innerHTML = oldContent+content;
}

这样就实现了无限加载。

在 vue 中使用指令实现

为什么要用指令实现呢?好像只有指令是可以获取到底层 dom 的?而实现无限加载,是需要拿到内容高度的。

首先初始化一个项目,添加一个组件,用来显示列表。

// components/Index.vue
<template>
 <div>
  <ul class="news">
   <li class="news__item" v-for="(news, index) in newslist">
    {{index}}-{{news.title}}
   </li>
  </ul>
 </div>
</template>
<style>
 .news__item {
  height: 80px;
  border: 1px solid #ccc;
  margin-bottom: 20px;
 }
</style>
<script>
 export default{
  data(){
   return{
    newslist: [
     {title: 'hello world'},
     {title: 'hello world'},
     {title: 'hello world'},
     {title: 'hello world'},
     {title: 'hello world'},
     {title: 'hello world'},
     {title: 'hello world'},
     {title: 'hello world'},
     {title: 'hello world'},
     {title: 'hello world'}
    ]
   }
  }
 }
</script>

OK,现在开始编写指令。从传统实现中,我们了解到要注册对滚动事件对监听,同时拿到内容高度。

directives: {
 scroll: {
  bind: function (el, binding){
   window.addEventListener('scroll', ()=> {
    if(document.body.scrollTop + window.innerHeight >= el.clientHeight) {
     console.log('load data');
    }
   })
  }
 }
}

首先是在组件内注册了 scroll 指令,然后在指令第一次绑定到组件时,也就是对应着 bind钩子,注册滚动监听。

钩子函数就是一些生命周期改变时会调用的函数。bind 在第一次绑定到组件时调用、unbind 在指令与组件解绑时调用。

还可以注意到 bind 对应到函数有两个参数,el 和 binding,这是钩子函数参数,比如 el 对应绑定的节点,binding 有很多数据,比如传给指令的参数等。

下面的el.clientHeight就是表示获取绑定指令的这个节点的内容高度。

和之前一样,判断滚动的高度加上窗口高度是否大于内容高度。

绑定指令到节点上:

<template>
 <div v-scroll="loadMore">
  <ul class="news">
   <li class="news__item" v-for="(news, index) in newslist">
    {{index}}-{{news.title}}
   </li>
  </ul>
 </div>
</template>

可以看到给指令传了一个值,这个值就是加载数据的函数:

methods: {
 loadMore() {
  let newAry = [];
  for(let i = 0; i < 10; i++) {
   newAry.push({title: 'hello world'})
  }
  this.newslist = [...this.newslist, ...newAry];
 }
}

当然,现在在滚动到底部时,只会打印load data,只要把这里改成调用函数就OK了:

 window.addEventListener('scroll', ()=> { 
 if(document.body.scrollTop + window.innerHeight >= el.clientHeight) {  
  let fnc = binding.value;  
  fnc(); 
 }
})

v-scroll="loadMore"的 loadMore可以在钩子函数参数的 binding 上拿到。

至此,一个简单的指令就完成了。

优化

上面的例子并没有真正从接口获取数据,所以存在一个隐藏的 bug:当接口响应很慢的情况,滚动到底部正在加载数据时,稍微滚动一下仍会触发获取数据函数,这会造成同时请求多次接口,一次性返回大量数据。

解决办法是添加一个全局变量 scrollDisable,当第一次触发加载数据函数时,将该值设置为 true,根据该值判断是否要执行加载函数。

以普通实现为例:

var scrollDisable = false;
window.addEventListener('scroll', function() {
 var scrollTop = document.body.scrollTop;
 if(scrollTop + window.innerHeight >= document.body.clientHeight) {
  // 触发加载数据    
  if(!scrollDisable) {
   // 
   loadMore(); 
  } 
 }
});
// 表示列表的序号
var index = 10;
function loadMore() {
  // 开始加载数据,就不能再次触发这个函数了
 scrollDisable = true;
 var content = '';
 for(var i=0; i< 10; i++) {
  content += '<li class="news__item">'+(++index)+'、hello world</li>'  
 }
 var node = document.getElementById('news');
 // 向节点内插入新生成的数据  
 var oldContent =   node.innerHTML;
 node.innerHTML = oldContent+content;
 // 插入数据完成后  
 scrollDisable = false;
}

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


# vue  # 无限加载  # vuejs无限加载  # vuejs  # 实现加载更多  # Vue实现一个无限加载列表功能  # Vue实现无限加载瀑布流  # vue 使用vant插件做tabs切换和无限加载功能的实现  # Vue下滚动到页面底部无限加载数据的示例代码  # Vue中的无限加载vue-infinite-loading的方法  # Vue.js实现无限加载与分页功能开发  # vue实现商品列表的无限加载思路和步骤详解  # 加载  # 绑定  # 自定义  # 这是  # 是在  # 还可以  # 都要  # 有很多  # 是从  # 要把  # 只会  # 注意到  # 要用  # 可以看到  # 就不能  # 为例  # 设置为  # 先到  # 解决办法  # 这会 


相关文章:   建站主机数据库如何配置才能提升网站性能?  零服务器AI建站解决方案:快速部署与云端平台低成本实践  香港服务器部署网站为何提示未备案?  家庭建站与云服务器建站,如何选择更优?  最好的网站制作公司,网购哪个网站口碑最好,推荐几个?谢谢?  如何在万网ECS上快速搭建专属网站?  如何通过PHP快速构建高效问答网站功能?  简历在线制作网站免费,免费下载个人简历的网站是哪些?  如何用AWS免费套餐快速搭建高效网站?  建站主机空间推荐 高性价比配置与快速部署方案解析  网站建设设计制作营销公司南阳,如何策划设计和建设网站?  建站之星上传入口如何快速找到?  已有域名如何免费搭建网站?  建站主机是什么?如何选择适合的建站主机?  免费公司网站制作软件,如何申请免费主页空间做自己的网站?  网站建设制作、微信公众号,公明人民医院怎么在网上预约?  电商网站制作多少钱一个,电子商务公司的网站制作费用计入什么科目?  php json中文编码为null的解决办法  制作宣传网站的软件,小红书可以宣传网站吗?  如何在云服务器上快速搭建个人网站?  如何在万网自助建站平台快速创建网站?  建站之星如何配置系统实现高效建站?  独立制作一个网站多少钱,建立网站需要花多少钱?  如何制作公司的网站链接,公司想做一个网站,一般需要花多少钱?  网站制作公司广州有几家,广州尚艺美发学校网站是多少?  如何登录建站主机?访问步骤全解析  海南网站制作公司有哪些,海口网是哪家的?  如何在云主机快速搭建网站站点?  建站之星在线客服如何快速接入解答?  如何在云主机上快速搭建网站?  北京营销型网站制作公司,可以用python做一个营销推广网站吗?  如何通过万网虚拟主机快速搭建网站?  昆明高端网站制作公司,昆明公租房申请网上登录入口?  建站之星如何助力网站排名飙升?揭秘高效技巧  ,在苏州找工作,上哪个网站比较好?  如何在宝塔面板中修改默认建站目录?  桂林网站制作公司有哪些,桂林马拉松怎么报名?  GML (Geography Markup Language)是什么,它如何用XML来表示地理空间信息?  python的本地网站制作,如何创建本地站点?  制作网站外包平台,自动化接单网站有哪些?  专业的网站制作设计是什么,如何制作一个企业网站,建设网站的基本步骤有哪些?  成都品牌网站制作公司,成都营业执照年报网上怎么办理?  深圳企业网站制作设计,在深圳如何网上全流程注册公司?  如何访问已购建站主机并解决登录问题?  PHP正则匹配日期和时间(时间戳转换)的实例代码  重庆市网站制作公司,重庆招聘网站哪个好?  建站之星如何优化SEO以实现高效排名?  济南网站建设制作公司,室内设计网站一般都有哪些功能?  如何用PHP工具快速搭建高效网站? 

您的项目需求

*请认真填写需求信息,我们会在24小时内与您取得联系。