/**
 * 监听滚动条 滚动进度变化
 * v-scroll-progress.self="(p) => console.log(p)"
 * @modifiers self 监听当前元素的滚动进度变化
 * @param params 滚动进度回调函数
 * @param p 滚动进度
 */
const rootMap = new Map()
export default {
	name: 'scroll-progress',
	mounted(el: HTMLElement, binding: any) {
		const params = binding.value
		const { self } = binding.modifiers
		const paramsType = typeof params
		const obj = {
			onscroll: () => { },
			el,
			root: self ? el : document,
			activeNum: 0,
		};
		if (paramsType === 'function') {
			obj.onscroll = params
		} else if (paramsType === 'object') {
			if (params.onscroll) obj.onscroll = params.onscroll
			if (params.GetRoot) obj.root = params.GetRoot()
			if (params.hasOwnProperty('activeNum')) obj.activeNum = params.activeNum
		}
		requestAnimationFrame(() => handleScroll({ target: obj.root }))
		if (rootMap.has(obj.root)) {
			rootMap.get(obj.root).push(obj)
			return
		}
		rootMap.set(obj.root, [obj])
		obj.root.addEventListener('scroll', handleScroll)
	},
	beforeUnmount(el: HTMLElement) {
		rootMap.forEach((objs, root) => {
			if (objs.some((v: any) => v.el === el)) {
				objs = objs.filter((v_: any) => v_.el !== el)
				rootMap.set(root, objs)
			}
			if (objs.length === 0) {
				root.removeEventListener('scroll', handleScroll)
				rootMap.delete(root)
			}
		})
	},
};
function handleScroll(e: any) {
	const target = e.target
	const objs = rootMap.get(target)
	if (!objs || objs.length === 0) return
	const el = target === document ? document.documentElement : target as HTMLElement
	const num = el.scrollTop / (el.scrollHeight - el.clientHeight);
	const progress = Math.round(num * 100)
	objs.forEach((obj: any) => {
		obj?.onscroll(progress)
		if (obj.el) {
			let isActive = progress > obj.activeNum
			obj.el.classList.toggle('active', isActive)
		}
	})
};
