Reputation: 91
I have to create a slider with a custom shape like the one shown below (blue is the slider handle):
The red color one is groove and the blue color one is handle.
Upvotes: 0
Views: 2846
Reputation: 9681
You can do this directly in QML using Canvas
or in Qt C++ (example with a circular slider) and then expose the element to QML. While not a direct copy-and-paste solution check this to see a custom circular progress bar that uses arc()
to draw the element. You can use line()
if you want straight lines. The behaviour of the slider is also something you will have to do on your own.
You can try to inherit from Slider
to try and get some (or even most) of the functionality that your element requires.
Upvotes: 0
Reputation: 13691
For the groove, you can use any Item
to draw this shape, e.g. a Image
For the handle, you just use a Rectangle
and place it according to the Slider.position
, e.g. like so:
Slider {
id: slider
width: 400
height: 150
y: 200
handle: Rectangle {
x: slider.leftPadding + slider.visualPosition * (slider.availableWidth - width)
y: Math.max(slider.topPadding, slider.availableHeight - height + slider.topPadding - ((slider.availableHeight - height) * (slider.position * 2)))
width: 15
height: 30
radius: 5
color: 'blue'
}
}
If you have a stranger shape, just change the function for y.
You can use any function that maps a value position
(range [0, 1]) to an y-value. You can use every property of the slider, to calculate an appropriate position.
Here another example, where the slider draws the sine function:
Slider {
width: 400
height: 150
id: slider1
y: 200
handle: Rectangle {
x: slider1.leftPadding + slider1.visualPosition * (slider1.availableWidth - width)
y: slider1.topPadding + (slider1.availableHeight - height) / 2 + (slider1.availableHeight - height) / 2 * Math.sin(slider1.position * 10)
width: 15
height: 30
radius: 5
color: 'blue'
}
}
And here for the fun of it: A random function. But I don't think you can draw a fitting groove to it
Slider {
id: slider
width: 400
height: 150
y: 200
onPositionChanged: {
var a = Math.round(Math.random() * 5) - Math.round(Math.random() * 5)
console.log(a)
handle.handleY = handle.y + (a)
console.log(handle.handleY)
}
handle: Rectangle {
property int handleY: slider.topPadding + slider.availableHeight / 2 - height / 2
x: slider.leftPadding + slider.visualPosition * (slider.availableWidth - width)
y: Math.max(slider.topPadding, Math.min(handleY, slider.availableHeight - height + slider.topPadding))
width: 15
height: 30
radius: 5
color: 'blue'
}
}
Upvotes: 1