FluentUI/src/controls/FluMediaPlayer.qml

142 lines
3.4 KiB
QML
Raw Normal View History

2023-03-25 13:35:21 +08:00
import QtQuick 2.15
import QtQuick.Controls 2.15
import QtMultimedia 5.15
import QtGraphicalEffects 1.15
import FluentUI 1.0
2023-03-24 15:21:47 +08:00
Item {
2023-03-24 18:25:13 +08:00
id:control
width: 480
height: 270
property url source
Rectangle{
anchors.fill: parent
color: FluColors.Black
}
2023-03-24 15:21:47 +08:00
MediaPlayer {
id: mediaplayer
2023-03-24 18:25:13 +08:00
property bool autoSeek:true
2023-03-25 13:35:21 +08:00
autoPlay: true
2023-03-24 18:25:13 +08:00
source: control.source
2023-03-25 13:35:21 +08:00
onError: {
console.debug(error)
2023-03-24 18:25:13 +08:00
}
onPositionChanged: {
if(autoSeek){
slider.seek(mediaplayer.position*slider.maxValue/mediaplayer.duration)
}
}
2023-03-25 13:35:21 +08:00
onStatusChanged: {
if(status===6){
2023-03-24 18:25:13 +08:00
slider.maxValue = mediaplayer.duration
}
}
2023-03-24 15:21:47 +08:00
}
2023-03-24 18:25:13 +08:00
onSourceChanged: {
2023-03-25 13:35:21 +08:00
slider.seek(0)
2023-03-24 18:25:13 +08:00
}
2023-03-24 15:21:47 +08:00
VideoOutput {
anchors.fill: parent
2023-03-25 13:35:21 +08:00
source: mediaplayer
2023-03-24 15:21:47 +08:00
}
2023-03-24 18:25:13 +08:00
Item{
height: 100
anchors{
bottom: parent.bottom
left: parent.left
right: parent.right
leftMargin: 10
rightMargin: 10
bottomMargin: 10
}
Rectangle{
anchors.fill: parent
color:FluTheme.isDark ? Qt.rgba(45/255,45/255,45/255,0.97) : Qt.rgba(237/255,237/255,237/255,0.97)
radius: 5
layer.enabled: true
layer.effect: GaussianBlur {
radius: 5
samples: 16
}
}
FluSlider{
id:slider
size:parent.width-20
y:20
anchors.horizontalCenter: parent.horizontalCenter
enableTip:false
onPressed: {
mediaplayer.autoSeek = false
}
onReleased: {
2023-03-25 13:35:21 +08:00
mediaplayer.seek(value*mediaplayer.duration/slider.maxValue)
2023-03-24 18:25:13 +08:00
mediaplayer.autoSeek = true
}
2023-03-24 15:21:47 +08:00
}
2023-03-24 18:25:13 +08:00
FluText{
id:start_time
anchors{
top: slider.bottom
topMargin: 10
left: slider.left
}
text: formatDuration(slider.value*mediaplayer.duration/slider.maxValue)
}
FluText{
id:end_time
anchors{
top: slider.bottom
right: slider.right
topMargin: 10
}
text: formatDuration(mediaplayer.duration)
}
FluIconButton{
iconSize: 15
2023-03-25 13:35:21 +08:00
iconSource: mediaplayer.playbackState === Audio.PlayingState ? FluentIcons.Pause : FluentIcons.Play
2023-03-24 18:25:13 +08:00
anchors{
horizontalCenter: parent.horizontalCenter
bottom: parent.bottom
bottomMargin: 10
}
onClicked: {
2023-03-25 13:35:21 +08:00
if(mediaplayer.playbackState === Audio.PlayingState){
2023-03-24 18:25:13 +08:00
mediaplayer.pause()
}else{
mediaplayer.play()
}
}
}
}
function formatDuration(duration) {
const seconds = Math.floor(duration / 1000);
const hours = Math.floor(seconds / 3600);
const minutes = Math.floor((seconds % 3600) / 60);
const remainingSeconds = seconds % 60;
return `${pad(hours)}:${pad(minutes)}:${pad(remainingSeconds)}`;
2023-03-24 15:21:47 +08:00
}
2023-03-24 18:25:13 +08:00
function pad(value) {
return value.toString().padStart(2, '0');
}
2023-03-24 15:21:47 +08:00
}