从头开始创建 QML 控件:滑块Slider

继续我们从头开始的 QML 控件系列,这次我们将实现一个 Slider。Slider 具有valueminimummaximum公共属性。Slider 是用一个覆盖整个控件的MouseArea实现的,并利用拖动来处理用户左右滑动“药丸”(用户移动的部分)。

背景“托盘”(一条水平线,可以点击)被分成左右两部分,以便在启用时不会通过药丸显示设置为假(因为药丸在禁用状态下是部分透明的) . Slider 唯一棘手的部分是计算像素值和像素值的方程。

Slider.qml

import QtQuick 2.0

Item {
    id: root
   
// public
    property double maximum: 10
    property double value:    0
    property double minimum:  0
   
    signal clicked(double value);  //onClicked:{root.value = value;  print('onClicked', value)}
       
// private
    width: 500;  height: 100 // default size
    opacity: enabled  &&  !mouseArea.pressed? 1: 0.3 // disabled/pressed state
   
    Repeater { // left and right trays (so tray doesn't shine through pill in disabled state)
        model: 2
       
        delegate: Rectangle {
            x:     !index?               0: pill.x + pill.width - radius
            width: !index? pill.x + radius: root.width - x;  height: 0.1 * root.height
            radius: 0.5 * height
            color: 'black'
            anchors.verticalCenter: parent.verticalCenter
        }
    }
   
    Rectangle { // pill
        id: pill
       
        x: (value - minimum) / (maximum - minimum) * (root.width - pill.width) // pixels from value
        width: parent.height;  height: width
        border.width: 0.05 * root.height
        radius: 0.5 * height
    }
   
    MouseArea {
        id: mouseArea

        anchors.fill: parent
   
        drag {
            target:   pill
            axis:     Drag.XAxis
            maximumX: root.width - pill.width
            minimumX: 0
        }
       
        onPositionChanged:  if(drag.active) setPixels(pill.x + 0.5 * pill.width) // drag pill
        onClicked:                          setPixels(mouse.x) // tap tray
    }
   
    function setPixels(pixels) {
        var value = (maximum - minimum) / (root.width - pill.width) * (pixels - pill.width / 2) + minimum // value from pixels
        clicked(Math.min(Math.max(minimum, value), maximum)) // emit
    }
}

 Test.qml

import QtQuick 2.0

Slider {
    property double backend: 0
   
    maximum:  10
    value:    backend
    minimum: -10
   
    onClicked: backend = value
}
分类: C++标签: