feat(thumbnail):添加播放器动态预览UI界面

This commit is contained in:
qiqi 2023-09-12 18:18:30 +08:00
parent 5f50d06b1d
commit 75027dce8b
11 changed files with 234 additions and 67 deletions

View File

@ -20,12 +20,22 @@
import QtQuick 2.15
import QtGraphicalEffects 1.15
Item {
Rectangle {
id: root
property variant source
property int samples: 9
property real radius: Math.floor(samples / 2)
property real blurRadius: Math.floor(samples / 2)
property bool hideSource: false
color: "transparent"
layer.enabled: true
layer.effect: OpacityMask {
maskSource: Rectangle {
width: root.width
height: root.height
radius: root.radius
}
}
ShaderEffectSource {
id: effectSource
@ -39,9 +49,9 @@ Item {
GaussianBlur {
anchors.fill: parent
source: effectSource
radius: root.radius
radius: root.blurRadius
samples: root.samples
}
//TODO:
//base
}
}

View File

@ -15,7 +15,7 @@ Rectangle {
y: 100
width: 500
height: 500
radius: 40
blurRadius: 40
samples: 81
source: image
Drag.active: dragArea.drag.active

View File

@ -18,7 +18,7 @@ MouseArea {
ListView {
width: childrenRect.width
height: 300
height: 200
orientation: ListView.Horizontal
spacing: 20
@ -28,8 +28,8 @@ MouseArea {
model: thumbnailView.viewModel
delegate: MouseArea {
width: 250
height: 300
width: 300
height: 200
acceptedButtons: Qt.LeftButton | Qt.RightButton
onClicked: {
@ -46,6 +46,8 @@ MouseArea {
Layout.fillWidth: true
Layout.preferredHeight: 32
Layout.maximumHeight: 32
visible: windowThumbnail.thumbnailMprisModel.count <= 0
ThemeIcon {
Layout.preferredHeight: 32
Layout.preferredWidth: 32
@ -60,6 +62,7 @@ MouseArea {
}
}
WindowThumbnail {
id: windowThumbnail
Layout.fillWidth: true
Layout.fillHeight: true

View File

@ -507,7 +507,7 @@ void UkuiTaskManager::activateWindow(const QString &winId)
QString UkuiTaskManager::windowTitle(const QString &winId)
{
return kdk::WindowManager::getWindowTitle(winId);;
return kdk::WindowManager::getWindowTitle(winId);
}
QIcon UkuiTaskManager::windowIcon(const QString &winId)

View File

@ -217,9 +217,9 @@ void PlayerItemPrivate::updateMediaPlayer2PlayerProps(QDBusPendingCallWatcher *w
void PlayerItemPrivate::updateMediaPlayer2PlayerPropsFromMap(const QVariantMap &map)
{
QVector<int> updateProperties;
if(map.find(QStringLiteral("PlayBackStatus")) != map.constEnd()) {
m_mp2PlayerProps.m_playbackStatus = map.value(QStringLiteral("PlayBackStatus")).toString();
updateProperties << MprisProperties::PlayBackStatus;
if(map.find(QStringLiteral("PlaybackStatus")) != map.constEnd()) {
m_mp2PlayerProps.m_playbackStatus = map.value(QStringLiteral("PlaybackStatus")).toString();
updateProperties << MprisProperties::PlaybackStatus;
}
if(map.find(QStringLiteral("LoopStatus")) != map.constEnd()) {
m_mp2PlayerProps.m_loopStatus = map.value(QStringLiteral("LoopStatus")).toString();
@ -490,4 +490,4 @@ bool PlayerItem::valid()
return d->m_valid;
}
#include "player-item.moc"
#include "player-item.moc"

View File

@ -86,7 +86,7 @@ QVariant PlayerItemsModel::data(const QModelIndex &index, int role) const
return item->supportedUriSchemes();
case MprisProperties::SupportedMimeTypes:
return item->supportedMimeTypes();
case MprisProperties::PlayBackStatus:
case MprisProperties::PlaybackStatus:
return item->playbackStatus();
case MprisProperties::LoopStatus:
return item->loopStatus();

View File

@ -39,7 +39,7 @@ public:
SupportedUriSchemes,
SupportedMimeTypes,
//media player2 player properties
PlayBackStatus,
PlaybackStatus,
LoopStatus,
Rate,
Shuffle,

View File

@ -1,19 +1,182 @@
import QtQuick 2.12
import QtQuick.Layouts 1.12
import QtQuick.Controls 2.12
import org.ukui.panel.publicItems 1.0
import org.ukui.sidebar.items 1.0
import org.ukui.windowThumbnail 1.0
ListView {
id: mprisView
width: 100
height: 100
clip: true
interactive: false
model: mprisModel
delegate: Rectangle {
width: 100
height: 100
Text {
width: 100
height: 100
text: model.Identity
elide: Text.ElideRight
verticalAlignment: Text.AlignVCenter
delegate: Loader {
property var artUrl: model.MetaData["mpris:artUrl"]
property var title: model.MetaData["xesam:title"]
property var artist: model.MetaData["xesam:artist"]
property var playbackStatus: model.PlaybackStatus
sourceComponent: {
if (artUrl) {
return artUrlComponent;
} else {
return thumbanilComponent;
}
}
}
}
Component {
id: artUrlComponent
Item {
width: 304
height: 96
RowLayout {
height: parent.height
width: height * 3
Image {
id: artUrlImage
Layout.fillHeight: true
Layout.preferredWidth: artUrlImage.height
source: artUrl
}
BlurItem {
Layout.fillHeight: true
Layout.fillWidth: true
ColumnLayout {
anchors.fill: parent
anchors.leftMargin: 24
anchors.rightMargin: 24
anchors.bottomMargin: 10
Text {
Layout.fillWidth: true
text: title
elide: Text.ElideRight
verticalAlignment: Text.AlignVCenter
}
Text {
Layout.fillWidth: true
text: artist
elide: Text.ElideRight
verticalAlignment: Text.AlignVCenter
}
Loader {
Layout.fillWidth: true
Layout.preferredHeight: 28
property var playStatus: playbackStatus
sourceComponent: buttonArea
}
}
}
}
}
}
Component {
id: thumbanilComponent
Item {
width: 256
height: 144
Loader {
id: thumbnailLoader
anchors.fill: parent
sourceComponent: {
if (windowThumbnailConfig.pipewireThumbnailEnable) {
return piperWireThumbnailComponent;
} else {
return x11ThumbnailComponent;
}
}
}
BlurItem {
x: buttonBase.x
y: buttonBase.y
width: buttonBase.width
height: buttonBase.height
radius: 4
blurRadius: 40
samples: 81
source: thumbnailLoader
}
Loader {
id: buttonBase
height: 28
width: 128
z: 10
anchors.bottom: parent.bottom
anchors.bottomMargin: 16
anchors.horizontalCenter: parent.horizontalCenter
property var playStatus: playbackStatus
sourceComponent: buttonArea
}
}
}
Component {
id: buttonArea
StyleBackground {
useStyleTransparency: false
paletteRole: PaletteRole.Base
alpha: 0.65
radius: 4
RowLayout {
anchors.fill: parent
MouseArea {
Layout.preferredHeight: 28
Layout.fillWidth: true
onClicked: {
mprisModel.operation(mprisView.model.index(index, 0), MprisProperties.Previous, [])
}
Image {
height: 16
width: 16
anchors.centerIn: parent
source: "file:///usr/share/icons/ukui-icon-theme-fashion/scalable/actions/media-skip-backward-symbolic.svg"
}
}
MouseArea {
Layout.preferredHeight: 28
Layout.fillWidth: true
onClicked: {
mprisModel.operation(mprisView.model.index(index, 0), MprisProperties.PlayPause, [])
}
Image {
height: 16
width: 16
anchors.centerIn: parent
property bool isPlaying: {
if (playStatus === "Playing") {
return true;
} else {
return false;
}
}
source: isPlaying ?
"file:///usr/share/icons/ukui-icon-theme-fashion/scalable/actions/media-playback-pause-symbolic.svg" :
"file:///usr/share/icons/ukui-icon-theme-fashion/scalable/actions/ukui-play-full-symbolic.svg"
}
}
MouseArea {
Layout.preferredHeight: 28
Layout.fillWidth: true
onClicked: {
mprisModel.operation(mprisView.model.index(index, 0), MprisProperties.Next, [])
}
Image {
height: 16
width: 16
anchors.centerIn: parent
source: "file:///usr/share/icons/ukui-icon-theme-fashion/scalable/actions/media-skip-forward-symbolic.svg"
}
}
}
}
}
}

View File

@ -14,7 +14,7 @@ PipeWireSourceItem {
anchors.fill: parent
ScreencastingRequest {
ScreenCastingRequest {
id: waylandItem
uuid: toolTipDelegate.Window.visibility === Window.Hidden ? "" : thumbnailSourceItem.winId
}

View File

@ -1,58 +1,48 @@
import QtQuick 2.12
import QtQuick.Layouts 1.12
import org.ukui.windowThumbnail 1.0
Item {
id: thumbnailSourceItem
Layout.fillWidth: true
Layout.fillHeight: true
clip: true
property var winId: ""
property var winId
property string desktopEntry: ""
property alias thumbnailMprisModel: mprisModel
WindowThumbnailMprisModel {
id: mprisModel
winID: thumbnailSourceItem.winId
}
Loader {
id: thumbnailLoader
active: Number.isInteger(thumbnailSourceItem.winId)
&& !windowThumbnailConfig.pipewireThumbnailEnable
&& windowThumbnailConfig.realTimeThumbnailEnable
&& mprisModel.count <= 0
visible: active
anchors.fill: parent
visible: windowThumbnailConfig.realTimeThumbnailEnable
sourceComponent: {
if (mprisModel.count > 0) {
return mprisPlayerComponent;
} else {
if (windowThumbnailConfig.pipewireThumbnailEnable) {
return piperWireThumbnailComponent;
} else {
return x11ThumbnailComponent;
}
}
}
Component {
id: x11Thumbnail
id: x11ThumbnailComponent
XWindowThumbnail {
Layout.fillWidth: true
Layout.fillHeight: true
winId: thumbnailSourceItem.winId
}
}
sourceComponent: x11Thumbnail;
Component {
id: piperWireThumbnailComponent
PipeWireThumbnail { }
}
Component {
id: mprisPlayerComponent
MprisPlayerThumbnail { }
}
}
Loader {
id: pipeWireLoader
active: Number.isInteger(thumbnailSourceItem.winId)
&& windowThumbnailConfig.pipewireThumbnailEnable
&& windowThumbnailConfig.enableRealTimeThumbnail
&& mprisModel.count <= 0
visible: active
anchors.fill: parent
asynchronous: true
Layout.fillWidth: true
Layout.fillHeight: true
source: "PipeWireThumbnail.qml"
}
Loader {
id: mprisLoader
active: mprisModel.count > 0
visible: active
anchors.fill: parent
asynchronous: true
Layout.fillWidth: true
Layout.fillHeight: true
source: "MprisPlayerThumbnail.qml"
}
}
}

View File

@ -38,7 +38,8 @@ void WindowThumbnailPlugin::registerTypes(const char *uri)
qmlRegisterUncreatableType<Screencasting>(uri, 1, 0, "Screencasting", "Only enumeration variables are required");
qmlRegisterUncreatableType<MprisProperties>(uri, 1, 0, "MprisProperties", "Only enumeration variables are required");
qRegisterMetaType<MprisProperties::Operations>("MprisProperties::Operations");
qRegisterMetaType<MprisProperties::Properties>("MprisProperties::Properties");
}
void WindowThumbnailPlugin::initializeEngine(QQmlEngine *engine, const char *uri)