低代码可视化-uniapp SliderRange区间组件-代码生成器

简介: SliderRange区间组件是一种用户界面元素,允许用户通过拖动滑块选择数值范围。组件支持微信小程序、H5和App,具有高度可定制性、响应式设计和多种事件处理功能。适用于价格筛选、音量调节等场景。代码实现包括滑动区域、滑块、事件处理等部分,支持可视化配置步长、颜色等属性。使用时需注意选择合适步长、提供清晰标签和考虑无障碍设计。

SliderRange区间组件是一种用户界面(UI)元素,允许用户通过拖动滑块来选择一个数值范围。这种组件在多种应用程序和平台中广泛使用,组件已经测试兼容微信小程序、H5、App。以下是对SliderRange区间组件的详细介绍:
image.png

一、组件构成
SliderRange区间组件通常由以下部分构成:

滑动区域:用于显示滑动条的背景,通常是一个长条形的区域。

滑块:用户可以通过拖动滑块来改变数值范围。滑块可以是单个的,也可以是双个的,用于选择区间的起始和结束值。

二、主要功能和特点
数值范围选择:SliderRange区间组件允许用户选择一个数值范围,而不是单个数值。这使得它非常适合用于需要用户输入范围的应用场景,如价格筛选、音量调节等。

高度可定制性:许多SliderRange区间组件提供了丰富的配置选项,如颜色、大小、步长、方向等,以满足不同应用的需求。

响应式设计:许多SliderRange区间组件支持响应式设计,能够自适应不同的屏幕尺寸和分辨率,确保在各种设备上都能提供良好的用户体验。

事件处理:SliderRange区间组件通常支持多种事件处理机制,如值变化事件、拖动事件等,使得开发者可以根据用户的操作进行相应的处理。

三、使用场景
SliderRange区间组件广泛应用于各种需要用户输入数值范围的应用场景,如:

音乐播放器:用于调节音量大小,通常是一个垂直的SliderRange区间组件。

图片编辑器:用于调节图片的亮度、对比度等参数,通常是一个水平的SliderRange区间组件。

电子商务网站:用于价格筛选,用户可以通过拖动滑块来选择价格范围。

数据可视化:用于调整图表中的数值范围,以便更好地观察数据的变化趋势。

四、组件实现
扩展一个uniapp slider组件diy-sliderrange。支持可视化定义步长、最小值、最大值、区间、激活颜色、按钮颜色等。组件库实现代码如下。

<template>
    <view class="slider-range">
        <view class="slider-container" :style="{ height: `${containerHeight}px` }">
            <view class="slider-track" :style="{
    
          backgroundColor: inactiveColor,
          height: `${
     barHeight}px`,
          top: `${
     (Math.max(buttonSize, barHeight) - barHeight) / 2 + 4}px`
        }"></view>
            <view class="slider-fill" :style="{
    
          backgroundColor: activeColor, 
          left: `${
     leftPercentage}%`, 
          width: `${
     rangePercentage}%`,
          height: `${
     barHeight}px`,
          top: `${
     (Math.max(buttonSize, barHeight) - barHeight) / 2 + 4}px`
        }"></view>
            <view class="slider-handle-container left" :style="{
    
          left: `${
     leftPercentage}%`,
          top: `${
     (Math.max(buttonSize, barHeight) - buttonSize) / 2 + 4}px`
        }" @touchstart="startDrag('left')" @touchmove.stop.prevent="drag" @touchend="endDrag">
                <view class="slider-handle" :style="{
    
            backgroundColor: buttonColor,
            width: `${
     buttonSize}px`,
            height: `${
     buttonSize}px`
          }">
                    <text v-if="valuePosition === 'inside'&&showValue" class="slider-value inside"
                        :style="{ color: valueColor }">{
   {
    formatValue(modelValue[0]) }}</text>
                </view>
                <text v-if="valuePosition === 'below'&&showValue" class="slider-value below"
                    :style="{ color: valueColor }">{
   {
    formatValue(modelValue[0]) }}</text>
            </view>
            <view class="slider-handle-container right" :style="{
    
          left: `${
     rightPercentage}%`,
          top: `${
     (Math.max(buttonSize, barHeight) - buttonSize) / 2 + 4}px`
        }" @touchstart="startDrag('right')" @touchmove.stop.prevent="drag" @touchend="endDrag">
                <view class="slider-handle" :style="{
    
            backgroundColor: buttonColor,
            width: `${
     buttonSize}px`,
            height: `${
     buttonSize}px`
          }">
                    <text v-if="valuePosition === 'inside'&&showValue" class="slider-value inside"
                        :style="{ color: valueColor }">{
   {
    formatValue(modelValue[1]) }}</text>
                </view>
                <text v-if="valuePosition === 'below'&&showValue" class="slider-value below"
                    :style="{ color: valueColor }">{
   {
    formatValue(modelValue[1]) }}</text>
            </view>
        </view>
    </view>
</template>

<script>
    export default {
   
        name: 'diy-sliderrange',
        props: {
   
            //区间值
            modelValue: {
   
                type: Array,
                required: true,
                validator: (value) => value.length === 2 && value.every(v => typeof v === 'number')
            },
            //最小值
            min: {
   
                type: Number,
                default: 0
            },
            //最大值
            max: {
   
                type: Number,
                default: 100
            },
            //布长
            step: {
   
                type: Number,
                default: 1
            },
            //最小区间
            minRange: {
   
                type: Number,
                default: 0
            },
            //进度条非激活态颜色
            inactiveColor: {
   
                type: String,
                default: '#e0e0e0'
            },
            //进度条激活态颜色
            activeColor: {
   
                type: String,
                default: '#007aff'
            },
            //拖动滑块按钮颜色
            buttonColor: {
   
                type: String,
                default: '#ffffff'
            },
            //进度条高度
            barHeight: {
   
                type: Number,
                default: 2
            },
            //滑块按钮大小
            buttonSize: {
   
                type: Number,
                default: 32
            },
            valueColor: {
   
                type: String,
                default: '#333333'
            },
            //是否显示值
            showValue: {
   
                type: Boolean,
                default: true
            },
            valuePosition: {
   
                type: String,
                default: 'inside',
                validator: (value) => ['inside', 'below'].includes(value)
            }
        },
        emits: ['update:modelValue', 'change'],
        computed: {
   
            leftPercentage() {
   
                return ((this.modelValue[0] - this.min) / (this.max - this.min)) * 100
            },
            rightPercentage() {
   
                return ((this.modelValue[1] - this.min) / (this.max - this.min)) * 100
            },
            rangePercentage() {
   
                return this.rightPercentage - this.leftPercentage
            },
            containerHeight() {
   
                const baseHeight = Math.max(this.buttonSize, this.barHeight) + 8
                return this.valuePosition === 'below' ? baseHeight + 8 : baseHeight
            }
        },
        data() {
   
            return {
   
                isDragging: false,
                currentHandle: null,
                sliderWidth: 0,
                sliderLeft: 0
            }
        },
        mounted() {
   
            this.initSliderDimensions()
        },
        methods: {
   
            initSliderDimensions() {
   
                const query = uni.createSelectorQuery().in(this)
                query.select('.slider-container').boundingClientRect(data => {
   
                    if (data) {
   
                        this.sliderWidth = data.width
                        this.sliderLeft = data.left
                    }
                }).exec()
            },
            startDrag(handle) {
   
                this.isDragging = true
                this.currentHandle = handle
            },
            drag(event) {
   
                if (!this.isDragging) return

                const touch = event.touches[0]
                const x = touch.clientX - this.sliderLeft
                const percentage = Math.max(0, Math.min(100, (x / this.sliderWidth) * 100))
                const value = Math.round((percentage / 100) * (this.max - this.min) / this.step) * this.step + this.min

                let newValues = [...this.modelValue]
                if (this.currentHandle === 'left') {
   
                    newValues[0] = Math.min(value, newValues[1] - this.minRange)
                    newValues[0] = Math.max(this.min, newValues[0])
                } else {
   
                    newValues[1] = Math.max(value, newValues[0] + this.minRange)
                    newValues[1] = Math.min(this.max, newValues[1])
                }

                this.$emit('update:modelValue', newValues)
                this.$emit('change', newValues)
            },
            endDrag() {
   
                this.isDragging = false
                this.currentHandle = null
            },
            formatValue(value) {
   
                return value.toFixed(this.step < 1 ? 1 : 0)
            }
        }
    }
</script>

<style>
    .slider-range {
   
        width: 100%;
    }

    .slider-container {
   
        position: relative;
    }

    .slider-track {
   
        position: absolute;
        width: 100%;
        border-radius: 50rpx;
    }

    .slider-fill {
   
        position: absolute;
    }

    .slider-handle-container {
   
        position: absolute;
        transform: translateX(-50%);
        display: flex;
        flex-direction: column;
        align-items: center;
    }

    .slider-handle {
   
        border-radius: 50%;
        box-shadow:0 0 4px rgba(0, 0, 0, 0.2);
        display: flex;
        justify-content: center;
        align-items: center;
    }

    .slider-value {
   
        font-size: 12px;
    }

    .slider-value.below {
   
        margin-top: 4px;
    }
</style>

五、组件调用

<template>
    <view class="container container329152">
        <u-form-item class="diygw-col-24" label="滑块" prop="sliderrange">
            <view class="flex1 flex align-center diygw-col-24">
                <diy-sliderrange class="flex1" active-color="#07c160" name="sliderrange" v-model="sliderrange" :button-size="32" :min="0" :max="100" :step="1"></diy-sliderrange>
            </view>
        </u-form-item>
        <u-form-item class="diygw-col-24" label="滑块" prop="sliderrange1">
            <view class="flex1 flex align-center diygw-col-24">
                <diy-sliderrange class="flex1" active-color="#9f05d4" name="sliderrange1" v-model="sliderrange1" :button-size="32" :min="0" :max="100" :step="1"></diy-sliderrange>
            </view>
        </u-form-item>
        <u-form-item class="diygw-col-24" label="滑块" prop="sliderrange2">
            <view class="flex1 flex align-center diygw-col-24">
                <diy-sliderrange class="flex1" active-color="#fc0c00" name="sliderrange2" v-model="sliderrange2" value-color="#ab0202" :bar-height="7" :button-size="32" :min="0" :max="100" :step="1"></diy-sliderrange>
            </view>
        </u-form-item>
        <u-form-item class="diygw-col-24" label="滑块" prop="sliderrange3">
            <view class="flex1 flex align-center diygw-col-24">
                <diy-sliderrange class="flex1" active-color="#e60643" name="sliderrange3" v-model="sliderrange3" button-color="#d04c4c" value-color="#ffffff" :bar-height="8" :button-size="33" :min="0" :max="100" :step="1"></diy-sliderrange>
            </view>
        </u-form-item>
        <view class="clearfix"></view>
    </view>
</template>

<script>
    export default {
   
        data() {
   
            return {
   
                //用户全局信息
                userInfo: {
   },
                //页面传参
                globalOption: {
   },
                //自定义全局变量
                globalData: {
    isshow: false },
                sliderrange: [16, 66],
                sliderrange1: [16, 66],
                sliderrange2: [16, 66],
                sliderrange3: [10, 80]
            };
        },
        onShow() {
   
            this.setCurrentPage(this);
        },
        onLoad(option) {
   
            this.setCurrentPage(this);
            if (option) {
   
                this.setData({
   
                    globalOption: this.getOption(option)
                });
            }

            this.init();
        },
        methods: {
   
            async init() {
   }
        }
    };
</script>

<style lang="scss" scoped>
    .container329152 {
   
    }
</style>

六、注意事项
在使用SliderRange区间组件时,需要注意以下几点:

选择合适的步长:步长决定了滑块每次移动的最小单位。选择合适的步长可以使得用户更容易选择到精确的数值范围。

提供清晰的标签和说明:为了确保用户能够正确理解和使用SliderRange区间组件,需要提供清晰的标签和说明来指示数值范围和当前选择的值。

考虑无障碍设计:对于需要支持无障碍访问的应用,需要确保SliderRange区间组件能够与其他辅助技术(如屏幕阅读器)兼容,并提供相应的无障碍支持。

综上所述,SliderRange区间组件是一种功能强大且易于使用的UI元素,适用于多种应用场景。通过合理配置和使用,可以为用户提供良好的交互体验和操作便利性。

目录
相关文章
|
1月前
|
数据可视化 API
低代码可视化工具-uniapp页面跳转传参-代码生成器
低代码可视化工具-uniapp页面跳转传参-代码生成器
69 2
|
19天前
|
数据可视化 前端开发 UED
低代码可视化-Uniapp Cascader级联选择器-代码生成器
Cascader级联选择器是一种常用的UI组件,适用于从具有层级关系的数据中进行选择,如省市区选择、公司层级选择等。它通过分组多列展示选项,支持多级分类、联动选择、搜索与过滤等功能。组件具备自定义样式、禁用选项、清空选项等特性,广泛应用于电商、企业内部系统等场景。代码示例展示了其详细的实现和调用方法。
27 7
低代码可视化-Uniapp Cascader级联选择器-代码生成器
|
1月前
|
数据挖掘
uniapp uview扩展u-picker支持日历期间 年期间 月期间 时分期间组件
uniapp uview扩展u-picker支持日历期间 年期间 月期间 时分期间组件
55 10
|
1月前
|
移动开发 JavaScript 前端开发
UniApp低代码-颜色选择器diy-color-picker-代码生成器
UniApp低代码-颜色选择器diy-color-picker-代码生成器
65 5
|
1月前
|
搜索推荐 JavaScript 数据可视化
uniapp/vue个性化单选、复选组件
uniapp/vue个性化单选、复选组件
84 5
|
1月前
|
数据可视化 API
低代码可视化-uniapp购物车页面-代码生成器
低代码可视化-uniapp购物车页面-代码生成器
23 1
|
1月前
|
数据可视化 大数据 API
低代码可视化开发-uniapp新闻跑马灯组件-代码生成器
低代码可视化开发-uniapp新闻跑马灯组件-代码生成器
80 2
|
1月前
|
存储 API 数据库
uniapp APP自动更新组件
uniapp APP自动更新组件
63 1
|
1月前
|
数据可视化 JavaScript 前端开发
低代码可视化Uniapp点击事件-代码生成器
低代码可视化Uniapp点击事件-代码生成器
50 0
低代码可视化Uniapp点击事件-代码生成器
|
1月前
|
小程序 数据可视化 API
低代码可视化-uniapp商城首页小程序-代码生成器
低代码可视化-uniapp商城首页小程序-代码生成器
26 0