java下拉刷新上拉加载_手写上拉加载,下拉刷新(小demo)

背景

使用过很多下拉刷新,上拉加载的插件,虽然也知道一点原理,但似乎一直不太完全能理解它,闲来无事,手写一个,感受下,借鉴了better-scroll的源码,功能当然相差甚远,也只是个简易版的实现,大概就这意思。

Document

html,body,ul,li,div,input{

padding: 0;

margin: 0;

}

#header {

background: red;

}

#input{

display: inline-block;

width: 80%;

height: 30px;

}

#submit {

display: inline-block;

width: 16%;

height: 30px;

}

#article {

position: relative;

height: calc(100vh - 34px);

overflow:scroll;

}

#list {

position: relative;

list-style: none;

width: 100%;

top: 0px;

}

/* 刷新 */

#refresh {

position: absolute;

top: -50px;

left: 0;

width: 100%;

height: 50px;

overflow: hidden;

color: #969799;

font-size: 14px;

line-height: 50px;

text-align: center;

}

#text {

border: none;

line-height: 30px;

height: 30px;

text-align: center;

}

.li{

display: flex;

justify-content: center;

line-height: 80px;

height:80px;

border-bottom: 1px solid #999;

}

.load-icon{

height: 50px;

line-height: 50px;

text-align: center;

background: #f0f3f6;

}

#loading {

display: none;

}

下拉即可刷新...

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10

加载更多

let article = document.getElementById('article'), // 获取包裹ul列表的div

list = document.getElementById("list"), // 列表

loadingDom = document.getElementById("loading"), // 加载dom

loadingText = loadingDom.querySelector('.text'), // 写着“加载更多”的元素

// 下拉刷新变量

refreshDom = document.getElementById("refresh"), // 刷新dom

refreshText = refreshDom.querySelector('.text'), // 写着“下拉刷新”的元素

start = null, // 辅助变量:触摸开始时,相对于文档顶部的Y坐标

refresh = false; // 辅助变量:是否刷新

let num = 11; // 要添加的li文本,可自定义

let finish = false; // 是否继续加载

let loading = false; // 是否正在加载

// 追加li的方法,可自定义

function addLi() {

let fragment = document.createDocumentFragment();

loading = true;

for(let i=0;i<10;i++) {

let li = document.createElement('li');

li.className = 'li';

li.innerHTML = num++;

fragment.appendChild(li); // 用DocumentFragment提高渲染速度

}

setTimeout(function(){

ul.appendChild(fragment);

finish = true; // 设置加载到最低了

loadingText.innerHTML = "已经到底了~";

loading = false

},2000)

}

// 拷贝数组

var toConsumableArray = function (arr) {

if (Array.isArray(arr)) {

for (var i = 0, arr2 = Array(arr.length); i < arr.length; i++) arr2[i] = arr[i];

return arr2;

} else {

return Array.from(arr);

}

};

// 事件注册

function eventMixin(BScroll) {

// 注册事件

BScroll.prototype.on = function (type, fn) {

var context = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : this;

if (!this._events[type]) {

this._events[type] = [];

}

this._events[type].push([fn, context]);

};

// 销毁事件

BScroll.prototype.off = function (type, fn) {

var _events = this._events[type];

if (!_events) {

return;

}

var count = _events.length;

while (count--) {

if (_events[count][0] === fn) {

_events[count][0] = undefined;

}

}

};

}

/**

* new Bscroll(this.$refs.wrapper, {})

* 参数1:滚动外层dom

* 参数2:配置条件

*/

function BScroll(dom,{}){

let that = this;

this._events = {}; // init private custom events

this.x = 0; // 水平轴移动距离(水平功能暂不考虑,目前只玩y轴)

this.y = 0; // 纵轴移动距离

//获取元素滚动条卷曲的高度

this.getScrollTop = function(ele) {

return ele.scrollTop || 0;

}

//获取当前可视范围的高度

this.getClientHeight = function(ele) {

return ele.clientHeight || 0;

}

//获取文档完整的高度

this.getScrollHeight = function(ele){

return ele.clientHeight || 0;

}

// 触发touchmove事件

this.touchmoveHandle = function(){

this.trigger('touchmove',{

x: this.x,

y: this.y

})

}

// 触发touchend事件

this.touchendHandle = function(){

this.trigger('touchend',{

x: this.x,

y: this.y

})

}

// 滑动开始

article.addEventListener('touchstart',function(event){

let touch = event.touches[0];

start = touch.pageY; // 辅助变量:触摸开始时,相对于文档顶部的Y坐标

},false);

// 监听滑动事件

article.addEventListener('touchmove',function(event){

// 下拉刷新

let touch = event.touches[0];

// console.log(article.scrollTop)

// 下拉

if(article.scrollTop<=0){

console.log("下拉")

// 如果ul列表到顶部,修改ul列表的偏移,显示“下拉刷新”,并准备触发下拉刷新功能,可自定义

let diff = list.offsetTop + touch.pageY - start;

diff = diff >= 0 ? diff : 0;

list.style.top = diff +'px'; // ul.style.top = ul.offsetTop + 'px'

start = touch.pageY;

// console.log("list.style.top:",list.style.top)

// 若ul偏移量过大,则修改文字,refresh置为true,配合'touchend'刷新

if(list.offsetTop>=50) {

refreshText.innerHTML = "释放刷新";

refresh = true;

}

}else{

// 上拉

console.log("上拉")

// console.log("getScrollHeight:",that.getScrollHeight(list))

// console.log("getScrollTop:",that.getScrollTop(this))

// console.log("getClientHeight:",that.getClientHeight(this))

that.y = that.getScrollHeight(list) - that.getScrollTop(this) - that.getClientHeight(this);

// 滚动触发touchmove事件

that.touchmoveHandle();

// 触底touchend事件

if(that.y <= 10) {

//这里向后台进行数据请求(第一页数据就是1,第二页就是2,然后将请求回来的数组(处理成数组)拼接起来)

console.log("到底了!!")

// addLi();

// 触发滚动结束事件

that.touchendHandle();

}

}

},false);

// 滑动结束

article.addEventListener('touchend',function(event){

// 若'touchend'时,ul偏移,用setInterval循环恢复ul的偏移量

// 距离刷新有个20的距离

if(list.offsetTop>=20) {

refreshText.innerHTML = "加载中...";

// 若恢复时'refresh===true',刷新页面

if(refresh){

// 设置刷新

refreshDom.style.position = "static"; // 站位

list.style.top = 0;

setTimeout(() => {

location.reload();

}, 2000);

}

}

},false);

}

// 事件触发

BScroll.prototype.trigger = function (type) {

var events = this._events[type];

if (!events) {

return;

}

var len = events.length;

var eventsCopy = [].concat(toConsumableArray(events));

for (var i = 0; i < len; i++) {

var event = eventsCopy[i];

// console.log("event:",event)

var fn = event[0],

context = event[1];

if (fn) {

fn.apply(context, [].slice.call(arguments, 1));

}

}

};

// 初始化工作

eventMixin(BScroll);

let scroll = new BScroll(article,{}) // 创建实例

// 监听滚动到底

scroll.on("touchend",(pos)=>{

// 继续加载更多

if(!finish ){

// 正在加载

if(loading){

return false;

}

loadingDom.style.display = "block";

addLi(); // 加载第二页数据

}else{

// 已记载完成

loadingDom.style.display = "block";

loadingDom.querySelector(".text").innerHTML = "已经到底了~"

}

})

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值