我在qml中使用canvas创建了一个自定义弧进度。我根据经过的时间绘制了画布的进度。现在我需要通过进度条寻找,就像音乐搜索栏一样,我们如何在画布中获得正确的x,y位置。
这是绘制弧的代码
import QtQml 2.2
import QtQuick 2.0
// draws two arcs (portion of a circle)
// fills the circle with a lighter secondary color
// when pressed
Canvas {
id: canvas
width: canvasWidth
height: canvasHeight
antialiasing: true
property color primaryColor: "grey"
property color secondaryColor: "white"
property int canvasWidth: 0
property int canvasHeight: 0
property real centerWidth: width / 2
property real centerHeight: height / 2
property real radius: Math.min(canvas.width, canvas.height) / 2 - 2
property real minimumValue: 0
property real maximumValue: 100
property real currentValue: 33
// this is the angle that splits the circle in two arcs
// first arc is drawn from 0 radians to angle radians
// second arc is angle radians to 2*PI radians
property real angle: ((currentValue - minimumValue) / (maximumValue - minimumValue) * 2 * Math.PI)
// we want both circle to start / end at 12 o'clock
// without this offset we would start / end at 9 o'clock
property real angleOffset: (-Math.PI / 2)
property string text: "Text"
signal clicked()
onPrimaryColorChanged: requestPaint()
onSecondaryColorChanged: requestPaint()
onMinimumValueChanged: requestPaint()
onMaximumValueChanged: requestPaint()
onCurrentValueChanged: requestPaint()
onPaint: {
var ctx = getContext("2d");
ctx.save();
ctx.clearRect(0, 0, canvas.width, canvas.height);
// First, thinner arc
// From angle to 2*PI
ctx.beginPath();
ctx.lineWidth = 3;
ctx.strokeStyle = primaryColor;
ctx.arc(canvas.centerWidth,
canvas.centerHeight,
canvas.radius,
angleOffset + canvas.angle ,
(angleOffset-0.1) + 2*Math.PI );
ctx.stroke();
// Second, thicker arc
// From 0 to angle
ctx.beginPath();
ctx.lineWidth = 3;
ctx.strokeStyle = canvas.secondaryColor;
ctx.arc(canvas.centerWidth,
canvas.centerHeight,
canvas.radius,
canvas.angleOffset,
canvas.angleOffset + canvas.angle);
ctx.stroke();
ctx.restore();
}
function xOnArc(radius, radianAngle) {
var x = canvas.centerWidth + radius * Math.cos(radianAngle);
return x-(rect.width/2)
}
function yOnArc(radius, radianAngle) {
var y = canvas.centerHeight + radius * Math.sin(radianAngle);
return y-rect.height/2
}
Rectangle
{
id: rect
color: "white"
height: 10
width: 10
radius: 10/2
x: xOnArc(canvas.radius,canvas.angleOffset + canvas.angle)
y: yOnArc(canvas.radius,canvas.angleOffset + canvas.angle)
// Behavior on x
// {
// NumberAnimation {properties: "x"; duration:10}
// }
// Behavior on y
// {
// NumberAnimation {properties: "y"; duration:10}
// }
}
}
这是我将根据已用时间显示进度的代码
import QtQuick 2.0
Item {
anchors.fill: parent
property real value: 0
height: canvasHeights
width: canvasWidths
property real total_time: 180
property real progress_time: 0
property bool isPlaying: song_timer.running
signal songCompleted()
property int canvasWidths: 240
property int canvasHeights: 240
property int text_margin_progress: 0
/**
A custom control which draws the the progress Arc in canvas
*/
ProgressArc
{
id: circle
currentValue: value
anchors.centerIn: parent
canvasWidth: canvasWidths
canvasHeight: canvasHeights
/**
A timer will be started when the song starts playing this controls the progress of the song
*/
Timer
{
id: song_timer
running: false
repeat: true
interval: 1000
onTriggered:
{
//progress_time will be incremented after each second which will be used to calculate the progress percentage and
//and time
progress_time = progress_time + 1;
value = calculateStepValue(progress_time)
circle.currentValue = value;
time.text = fmtMSS(progress_time)
/**
When value reaches 100 then the song is completed and a signal will be send to the corresponsing class
*/
if(value >=100)
{
song_timer.stop()
songCompleted()
}
}
}
/**
Elapsed time will be shown in the text
*/
Text
{
id: time
anchors.horizontalCenter: parent.horizontalCenter
anchors.bottom: parent.bottom
anchors.bottomMargin: text_margin_progress
color: "white"
font.pointSize: (canvasHeights == (350*scaleFactor-(20*scaleFactor)))?20:10
}
}
/**
Convert seconds to human readable format
eg:- 68 sec eq 1:08 min
*/
function fmtMSS(time){
// Hours, minutes and seconds
var hrs = ~~(time / 3600);
var mins = ~~((time % 3600) / 60);
var secs = time % 60;
// Output like "1:01" or "4:03:59" or "123:03:59"
var ret = "";
if (hrs > 0) {
ret += "" + hrs + ":" + (mins < 10 ? "0" : "");
}
ret += "" + mins + ":" + (secs < 10 ? "0" : "");
ret += "" + secs;
return ret;
}
/**
Calculate the step value from the progress time
*/
function calculateStepValue(current_time)
{
return (100 - (((total_time - current_time)/total_time)*100))
}
/**
pause playing music
*/
function pausePlaying()
{
song_timer.stop();
}
/**
Resume playing music
*/
function resumePlaying()
{
if(value>100)
songCompleted()
else
song_timer.start()
}
/**
Start playing song. Before playing set the progress time to 0{song from start}
*/
function startPlaying()
{
progress_time = 0
song_timer.start()
}
}
答案 0 :(得分:0)
要获得您想要的内容,您需要将MouseArea
添加到Item
或直接添加到ProgressArc
(来自第二个列表):
MouseArea {
anchors.fill: parent
onClicked: {
console.log("Clicked on " + mouse.x + " " + mouse.y)
var percent = calcPercentBasedOnMousePos(mouse.x, mouse.y)
jumpToPosition(percent)
}
}
不要忘记设置锚点以填充父项目(否则此MouseArea
将为0x0
大小且无法处理任何点击次数。