| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118 | import { VantComponent } from '../common/component';import { range } from '../common/utils';import { isObj } from '../common/validator';const DEFAULT_DURATION = 200;VantComponent({    classes: ['active-class'],    props: {        valueKey: String,        className: String,        itemHeight: Number,        visibleItemCount: Number,        initialOptions: {            type: Array,            value: [],        },        defaultIndex: {            type: Number,            value: 0,            observer(value) {                this.setIndex(value);            },        },    },    data: {        startY: 0,        offset: 0,        duration: 0,        startOffset: 0,        options: [],        currentIndex: 0,    },    created() {        const { defaultIndex, initialOptions } = this.data;        this.set({            currentIndex: defaultIndex,            options: initialOptions,        }).then(() => {            this.setIndex(defaultIndex);        });    },    methods: {        getCount() {            return this.data.options.length;        },        onTouchStart(event) {            this.setData({                startY: event.touches[0].clientY,                startOffset: this.data.offset,                duration: 0,            });        },        onTouchMove(event) {            const { data } = this;            const deltaY = event.touches[0].clientY - data.startY;            this.setData({                offset: range(data.startOffset + deltaY, -(this.getCount() * data.itemHeight), data.itemHeight),            });        },        onTouchEnd() {            const { data } = this;            if (data.offset !== data.startOffset) {                this.setData({ duration: DEFAULT_DURATION });                const index = range(Math.round(-data.offset / data.itemHeight), 0, this.getCount() - 1);                this.setIndex(index, true);            }        },        onClickItem(event) {            const { index } = event.currentTarget.dataset;            this.setIndex(index, true);        },        adjustIndex(index) {            const { data } = this;            const count = this.getCount();            index = range(index, 0, count);            for (let i = index; i < count; i++) {                if (!this.isDisabled(data.options[i]))                    return i;            }            for (let i = index - 1; i >= 0; i--) {                if (!this.isDisabled(data.options[i]))                    return i;            }        },        isDisabled(option) {            return isObj(option) && option.disabled;        },        getOptionText(option) {            const { data } = this;            return isObj(option) && data.valueKey in option                ? option[data.valueKey]                : option;        },        setIndex(index, userAction) {            const { data } = this;            index = this.adjustIndex(index) || 0;            const offset = -index * data.itemHeight;            if (index !== data.currentIndex) {                return this.set({ offset, currentIndex: index }).then(() => {                    userAction && this.$emit('change', index);                });            }            return this.set({ offset });        },        setValue(value) {            const { options } = this.data;            for (let i = 0; i < options.length; i++) {                if (this.getOptionText(options[i]) === value) {                    return this.setIndex(i);                }            }            return Promise.resolve();        },        getValue() {            const { data } = this;            return data.options[data.currentIndex];        },    },});
 |