js-review/js/节流.js

87 lines
2.9 KiB
JavaScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

// 节流是值函数在连续触发的情况下在规定的时间内无论如何都会执行一次比如设置的延迟时间为250
// 那么如果连续点击1秒钟那么会执行4四次而且四次的时间间隔250
/**
* @description 节流函数(首节流,第一次触发会立即执行)
* @param { Function } - 要添加节流功能的函数
* @param { number } - 要延迟的毫秒数
*/
export function firstThrottle(fun, delay) {
var flag = true // 是否可以执行
return function(){
if(!flag) return // 不能执行就直接返回
// 获取参数和上下文
var args = arguments
var context = this
fun.apply(context, args)
// 执行完成之后把flag设置成false表示不能执行并设置定时器delay毫秒之后设置true
flag = false
setTimeout(function(){
flag = true
}, delay);
}
}
/**
* @description 节流函数(尾节流,无论延迟设置多久,总会执行最后一次)
* @param { Function } - 要添加节流功能的函数
* @param { number } - 要延迟的毫秒数
*/
export function lastThrottle(fun, delay) {
var timer = 0
return function () {
if(timer) return
var args = arguments
var context = this
timer = setTimeout(function () {
fun.apply(context, args)
timer = 0
},delay)
}
}
/**
* @description 节流函数(首节流,通过时间戳实现)
* @param { Function } - 要添加节流功能的函数
* @param { number } - 要延迟的毫秒数
*/
export function lastThrottleByTime(fun, delay) {
var pre = 0
return function () {
var cur = Date.now() // 获取当前的时间戳
if(cur - pre > delay) {
var args = arguments
var context = this
fun.apply(context, args)
pre = cur
}
}
}
// 思考首节流适用delay大且对最终状态无要求的功能缺点是不会执行最终状态。
// 尾节流适用delay不大且对最终状态有要求的功能缺点是当delay大时用户会认为自己的第一次点击好像无效
// 又没有什么办法可以是首节流,又保留最终状态?之前我们讲过防抖,防抖在高频率出发下,只会触发最后一次,这不就是我们要的尾状态吗!
/**
* @description 节流函数(首尾节流,通过时间戳实现)
* @param { Function } - 要添加节流功L的函数
* @param { number } - 要延迟的毫秒数
*/
export function firstAndLastThrottle(fun, delay) {
var pre = 0
var timer = 0
var _delay = delay + 100 // 防抖用的时间间隔比节流大0.1秒因为人对0.1秒的延迟无感知
return function () {
var args = arguments
var context = this
var cur = Date.now() // 获取当前的时间戳
if(cur - pre > delay) {
fun.apply(context, args)
pre = cur
}
clearTimeout(timer)
timer = setTimeout(() => {
fun.apply(context, args)
}, _delay);
}
}