<template>
	<view class="fs-scroll-list">
		<scroll-view
			scroll-x
			:show-scrollbar="false"
			:lower-threshold="0"
			:upper-threshold="0"
			@scrolltoupper="handleToUpper"
			@scrolltolower="handleToLower"
			@scroll="handleScroll"
		>
			<view class="fs-scroll-list-content"><slot></slot></view>
		</scroll-view>

		<view class="fs-scroll-indicator" v-if="indicator">
			<view class="fs-scroll-indicator-line"><view class="fs-scroll-indicator-bar" :style="barStyle"></view></view>
		</view>
	</view>
</template>

<script>
/**
 * 滚动列表组件
 * @description 滚动列表组件
 * @property {Boolean} indicator 是否显示面板指示器
 * @property {String} indicatorColor 指示器背景颜色
 * @property {String} indicatorActiveColor 指示器滑块颜色
 * @property {String} indicatorWidth 指示器的整体宽度(传值的时候需要带单位px)
 * @property {String} indicatorBarWidth 滑块的宽度(传值的时候需要带单位px)
 * @event {Function} left 滑到左边事件
 * @event {Function} right 滑动右边事件
 */
export default {
	name: 'fs-scroll-list'
}
</script>

<script setup>
import { onMounted, reactive, ref, computed, getCurrentInstance } from 'vue'

const props = defineProps({
	indicator: {
		type: Boolean,
		default: true
	},
	indicatorWidth: {
		type: String,
		default: '30px'
	},
	indicatorBarWidth: {
		type: String,
		default: '15px'
	},
	indicatorColor: {
		type: String,
		default: '#f2f2f2'
	},
	indicatorActiveColor: {
		type: String,
		default: '#3c9cff'
	}
})
const emits = defineEmits(['left', 'right'])

const state = reactive({
	listWidth: 0,
	contentWidth: 0,
	scrollWidth: 0
})
onMounted(() => {
	uni
		.createSelectorQuery()
		.in(getCurrentInstance().ctx)
		.select('.fs-scroll-list')
		.boundingClientRect(data => {
			state.listWidth = data.width
		})
		.exec()
})

const indicatorLeftWidth = computed(() => {
	return parseInt(props.indicatorWidth) - parseInt(props.indicatorBarWidth)
})
const listLeftWidth = computed(() => {
	return state.contentWidth - state.listWidth
})
const barStyle = computed(() => {
	const x = (state.scrollWidth * indicatorLeftWidth.value) / listLeftWidth.value + 'px'
	return `transform: translateX(${x})`
})

const handleScroll = event => {
	state.scrollWidth = event.detail.scrollLeft
	state.contentWidth = event.detail.scrollWidth
}

const handleToUpper = () => emits('left')
const handleToLower = () => emits('right')
</script>

<style lang="scss" scoped>
.fs-scroll-list {
	&-box {
		display: flex;
	}
	&-content {
		display: flex;
		flex-wrap: nowrap;
	}
}
.fs-scroll-indicator {
	display: flex;
	justify-content: center;

	&-line {
		background-color: v-bind(indicatorColor);
		width: v-bind(indicatorWidth);
		height: 8rpx;
		border-radius: 50px;
		overflow: hidden;
	}
	&-bar {
		background-color: v-bind(indicatorActiveColor);
		height: 8rpx;
		width: v-bind(indicatorBarWidth);
		border-radius: 50px;
	}
}
</style>
