From 18b672d2fd0368d3986d0917044d0ded767a24c8 Mon Sep 17 00:00:00 2001 From: NamedKitten Date: Sat, 13 Oct 2018 19:57:17 +0100 Subject: [PATCH] Add mouse movement stop to hide controls. --- src/qml/main.qml | 873 ++++++++++++++++++++++++----------------------- 1 file changed, 444 insertions(+), 429 deletions(-) diff --git a/src/qml/main.qml b/src/qml/main.qml index bced9dc..eafae50 100644 --- a/src/qml/main.qml +++ b/src/qml/main.qml @@ -123,7 +123,8 @@ ApplicationWindow { var args = Qt.application.arguments var len = Qt.application.arguments.length var argNo = 0 - renderer.setOption("ytdl-format", "bestvideo[width<=" + Screen.width + "][height<=" + Screen.height + "]+bestaudio") + renderer.setOption("ytdl-format", "bestvideo[width<=" + Screen.width + + "][height<=" + Screen.height + "]+bestaudio") if (len > 1) { for (argNo = 0; argNo < len; argNo++) { var argument = args[argNo] @@ -132,7 +133,7 @@ ApplicationWindow { if (argument.length > 0) { var splitArg = argument.split(/=(.+)/) renderer.setOption(splitArg[0], splitArg[1]) - } + } } else { renderer.command(["loadfile", argument, "append-play"]) } @@ -170,470 +171,484 @@ ApplicationWindow { function setTitle() { titleLabel.text = renderer.getProperty("media-title") } - } - Dialog { - id: loadDialog - title: "URL / File Path" - standardButtons: StandardButton.Cancel | StandardButton.Open - - onAccepted: { - renderer.command(["loadfile", pathText.text]) - pathText.text = "" + function hideControls() { + controlsBar.visible = false + controlsBackground.visible = false + titleBar.visible = false + titleBackground.visible = false + controlsBar.height = 0 } - TextField { - id: pathText - text: "/home/kitteh/babyshark.mkv" - placeholderText: qsTr("URL / File Path") - } - } - - MouseArea { - id: mouseAreaBar - x: 0 - y: parent.height - width: parent.width - height: controlsBar.height + progressBar.height - anchors.bottom: parent.bottom - anchors.bottomMargin: 0 - hoverEnabled: true - onEntered: { + function showControls() { updateControls() controlsBar.visible = true controlsBackground.visible = true titleBar.visible = true titleBackground.visible = true - controlsBar.height = 35 + controlsBar.height = renderer.height / 16 } - } - MouseArea { - id: mouseAreaPlayer - width: parent.width - anchors.bottom: mouseAreaBar.top - anchors.bottomMargin: 0 - anchors.right: parent.right - anchors.rightMargin: 0 - anchors.left: parent.left - anchors.leftMargin: 0 - anchors.top: titleBar.bottom - anchors.topMargin: 0 - hoverEnabled: true - onClicked: loadDialog.open() - onEntered: { - if (subtitlesMenu.visible) { - return - } else { - controlsBar.visible = false - controlsBackground.visible = false - titleBar.visible = false - titleBackground.visible = false - controlsBar.height = 0 + Dialog { + id: loadDialog + title: "URL / File Path" + standardButtons: StandardButton.Cancel | StandardButton.Open + + onAccepted: { + renderer.command(["loadfile", pathText.text]) + pathText.text = "" + } + + TextField { + id: pathText + text: "/home/kitteh/babyshark.mkv" + placeholderText: qsTr("URL / File Path") } } - } - Rectangle { - id: titleBackground - height: titleBar.height - anchors.top: parent.top - anchors.left: parent.left - anchors.right: parent.right - Layout.fillWidth: true - Layout.fillHeight: true - color: "black" - opacity: 0.6 - } - - Rectangle { - id: titleBar - height: renderer.height / 16 - anchors.right: parent.right - anchors.rightMargin: parent.width / 128 - anchors.left: parent.left - anchors.leftMargin: parent.width / 128 - anchors.top: parent.top - - visible: true - color: "transparent" - - Text { - id: titleLabel - text: "Title" - color: "white" + MouseArea { + id: mouseAreaBar + x: 0 + y: parent.height width: parent.width - height: parent.height - anchors.left: parent.left + height: controlsBar.height + progressBar.height anchors.bottom: parent.bottom - anchors.bottomMargin: 4 - anchors.topMargin: 4 + anchors.bottomMargin: 0 + hoverEnabled: true + onEntered: { + mouseAreaPlayerTimer.stop() + } + } + + MouseArea { + id: mouseAreaPlayer + width: parent.width + anchors.bottom: mouseAreaBar.top + anchors.bottomMargin: 0 + anchors.right: parent.right + anchors.rightMargin: 0 + anchors.left: parent.left + anchors.leftMargin: 0 + anchors.top: titleBar.bottom + anchors.topMargin: 0 + hoverEnabled: true + onClicked: loadDialog.open() + Timer { + id: mouseAreaPlayerTimer + interval: 2000 + running: false + repeat: false + onTriggered: { + renderer.hideControls() + } + } + onPositionChanged: { + renderer.showControls() + mouseAreaPlayerTimer.restart() + } + } + + Rectangle { + id: titleBackground + height: titleBar.height anchors.top: parent.top - font.family: notoFont.name - fontSizeMode: Text.Fit - minimumPixelSize: 10 - font.pixelSize: 72 - verticalAlignment: Text.AlignVCenter - renderType: Text.NativeRendering - opacity: 1 - } - } - - Rectangle { - id: controlsBackground - height: controlsBar.height + (progressBar.topPadding * 2) - (progressBackground.height * 2) - anchors.bottom: parent.bottom - anchors.left: parent.left - anchors.right: parent.right - Layout.fillWidth: true - Layout.fillHeight: true - color: "black" - opacity: 0.6 - } - - Rectangle { - id: controlsBar - height: renderer.height / 16 - anchors.right: parent.right - anchors.rightMargin: parent.width / 128 - anchors.left: parent.left - anchors.leftMargin: parent.width / 128 - anchors.bottom: parent.bottom - anchors.bottomMargin: 1 - visible: true - color: "transparent" - - Rectangle { - id: subtitlesMenuBackground - height: controlsBar.height + (progressBar.topPadding * 2) - - (progressBackground.height * 2) - anchors.fill: subtitlesMenu - Layout.fillWidth: true - Layout.fillHeight: true - visible: false - color: "black" - opacity: 0.6 - radius: 5 - } - - Rectangle { - id: subtitlesMenu - color: "transparent" - width: childrenRect.width - height: childrenRect.height - visible: false - anchors.right: subtitlesButton.right - anchors.bottom: progressBar.top - radius: 5 - - Text { - id: audioLabel - anchors.left: parent.left - anchors.right: parent.right - text: "Audio" - color: "white" - font.family: notoFont.name - font.pixelSize: 14 - renderType: Text.NativeRendering - horizontalAlignment: Text.AlignHCenter - opacity: 1 - } - ComboBox { - id: audioList - textRole: "key" - anchors.top: audioLabel.bottom - model: ListModel { - id: audioModel - } - onActivated: { - renderer.command(["set", "aid", String(audioModel.get( - index).value)]) - } - opacity: 1 - } - Text { - id: subLabel - anchors.left: parent.left - anchors.right: parent.right - text: "Subtitles" - color: "white" - font.family: notoFont.name - font.pixelSize: 14 - anchors.top: audioList.bottom - renderType: Text.NativeRendering - horizontalAlignment: Text.AlignHCenter - opacity: 1 - } - ComboBox { - id: subList - textRole: "key" - anchors.top: subLabel.bottom - model: ListModel { - id: subModel - } - onActivated: { - renderer.command(["set", "sid", String(subModel.get( - index).value)]) - } - opacity: 1 - } - Text { - id: vidLabel - anchors.left: parent.left - anchors.right: parent.right - text: "Video" - color: "white" - font.family: notoFont.name - font.pixelSize: 14 - anchors.top: subList.bottom - renderType: Text.NativeRendering - horizontalAlignment: Text.AlignHCenter - opacity: 1 - } - ComboBox { - id: vidList - textRole: "key" - anchors.top: vidLabel.bottom - model: ListModel { - id: vidModel - } - onActivated: { - renderer.command(["set", "vid", String(vidModel.get( - index).value)]) - } - opacity: 1 - } - } - - Slider { - id: progressBar - to: 1 - value: 0.0 - palette.dark: "#f00" - anchors.bottom: parent.top anchors.left: parent.left anchors.right: parent.right - anchors.bottomMargin: 0 + Layout.fillWidth: true + Layout.fillHeight: true + color: "black" + opacity: 0.6 + } - bottomPadding: 0 + Rectangle { + id: titleBar + height: renderer.height / 16 + anchors.right: parent.right + anchors.rightMargin: parent.width / 128 + anchors.left: parent.left + anchors.leftMargin: parent.width / 128 + anchors.top: parent.top - onMoved: { - renderer.command(["seek", progressBar.value, "absolute"]) + visible: true + color: "transparent" + + Text { + id: titleLabel + text: "Title" + color: "white" + width: parent.width + height: parent.height + anchors.left: parent.left + anchors.bottom: parent.bottom + anchors.bottomMargin: 4 + anchors.topMargin: 4 + anchors.top: parent.top + font.family: notoFont.name + fontSizeMode: Text.Fit + minimumPixelSize: 10 + font.pixelSize: 72 + verticalAlignment: Text.AlignVCenter + renderType: Text.NativeRendering + opacity: 1 + } + } + + Rectangle { + id: controlsBackground + height: controlsBar.height + (progressBar.topPadding * 2) + - (progressBackground.height * 2) + anchors.bottom: parent.bottom + anchors.left: parent.left + anchors.right: parent.right + Layout.fillWidth: true + Layout.fillHeight: true + color: "black" + opacity: 0.6 + } + + Rectangle { + id: controlsBar + height: renderer.height / 16 + anchors.right: parent.right + anchors.rightMargin: parent.width / 128 + anchors.left: parent.left + anchors.leftMargin: parent.width / 128 + anchors.bottom: parent.bottom + anchors.bottomMargin: 1 + visible: true + color: "transparent" + + Rectangle { + id: subtitlesMenuBackground + height: controlsBar.height + (progressBar.topPadding * 2) + - (progressBackground.height * 2) + anchors.fill: subtitlesMenu + Layout.fillWidth: true + Layout.fillHeight: true + visible: false + color: "black" + opacity: 0.6 + radius: 5 } - background: Rectangle { - id: progressBackground - x: progressBar.leftPadding - y: progressBar.topPadding + progressBar.availableHeight / 2 - height / 2 - implicitHeight: (renderer.height / 256) < 2 ? 2 : renderer.height / 256 - width: progressBar.availableWidth - height: implicitHeight - color: Qt.rgba(255, 255, 255, 0.4) + Rectangle { + id: subtitlesMenu + color: "transparent" + width: childrenRect.width + height: childrenRect.height + visible: false + anchors.right: subtitlesButton.right + anchors.bottom: progressBar.top + radius: 5 - Rectangle { - width: progressBar.visualPosition * parent.width - height: parent.height - color: "red" + Text { + id: audioLabel + anchors.left: parent.left + anchors.right: parent.right + text: "Audio" + color: "white" + font.family: notoFont.name + font.pixelSize: 14 + renderType: Text.NativeRendering + horizontalAlignment: Text.AlignHCenter + opacity: 1 + } + ComboBox { + id: audioList + textRole: "key" + anchors.top: audioLabel.bottom + model: ListModel { + id: audioModel + } + onActivated: { + renderer.command(["set", "aid", String( + audioModel.get(index).value)]) + } + opacity: 1 + } + Text { + id: subLabel + anchors.left: parent.left + anchors.right: parent.right + text: "Subtitles" + color: "white" + font.family: notoFont.name + font.pixelSize: 14 + anchors.top: audioList.bottom + renderType: Text.NativeRendering + horizontalAlignment: Text.AlignHCenter + opacity: 1 + } + ComboBox { + id: subList + textRole: "key" + anchors.top: subLabel.bottom + model: ListModel { + id: subModel + } + onActivated: { + renderer.command(["set", "sid", String( + subModel.get(index).value)]) + } + opacity: 1 + } + Text { + id: vidLabel + anchors.left: parent.left + anchors.right: parent.right + text: "Video" + color: "white" + font.family: notoFont.name + font.pixelSize: 14 + anchors.top: subList.bottom + renderType: Text.NativeRendering + horizontalAlignment: Text.AlignHCenter + opacity: 1 + } + ComboBox { + id: vidList + textRole: "key" + anchors.top: vidLabel.bottom + model: ListModel { + id: vidModel + } + onActivated: { + renderer.command(["set", "vid", String( + vidModel.get(index).value)]) + } opacity: 1 } } - handle: Rectangle { - x: progressBar.leftPadding + progressBar.visualPosition - * (progressBar.availableWidth - width) - y: progressBar.topPadding + progressBar.availableHeight / 2 - height / 2 - implicitWidth: 12 - implicitHeight: 12 - radius: 12 - color: "red" - border.color: "red" - } - } + Slider { + id: progressBar + to: 1 + value: 0.0 + palette.dark: "#f00" + anchors.bottom: parent.top + anchors.left: parent.left + anchors.right: parent.right + anchors.bottomMargin: 0 - Button { - id: playlistPrevButton - icon.name: "prev" - icon.source: "icons/prev.svg" - icon.color: "white" - display: AbstractButton.IconOnly - visible: false - width: 0 - onClicked: { - renderer.command(["playlist-prev"]) - updatePrev() - } - background: Rectangle { - color: "transparent" - } - } + bottomPadding: 0 - Button { - id: playPauseButton - icon.name: "pause" - icon.source: "icons/pause.svg" - icon.color: "white" - display: AbstractButton.IconOnly - anchors.left: playlistPrevButton.right - onClicked: { - updatePlayPause() - } - background: Rectangle { - color: "transparent" - } - } - - Button { - id: playlistNextButton - icon.name: "next" - icon.source: "icons/next.svg" - icon.color: "white" - display: AbstractButton.IconOnly - anchors.left: playPauseButton.right - onClicked: { - renderer.command(["playlist-next", "force"]) - } - background: Rectangle { - color: "transparent" - } - } - - Button { - id: volumeButton - icon.name: "volume-up" - icon.source: "icons/volume-up.svg" - icon.color: "white" - display: AbstractButton.IconOnly - anchors.left: playlistNextButton.right - onClicked: { - renderer.command(["cycle", "mute"]) - updateVolume() - } - background: Rectangle { - color: "transparent" - } - } - Slider { - id: volumeBar - to: 100 - value: 100 - palette.dark: "#f00" - - implicitWidth: Math.max( - background ? background.implicitWidth : 0, - (handle ? handle.implicitWidth : 0) - + leftPadding + rightPadding) - implicitHeight: Math.max( - background ? background.implicitHeight : 0, - (handle ? handle.implicitHeight : 0) - + topPadding + bottomPadding) - - anchors.left: volumeButton.right - anchors.top: parent.top - anchors.bottom: parent.bottom - onMoved: { - renderer.command(["set", "volume", Math.round( - volumeBar.value).toString()]) - updateVolume() - } - - handle: Rectangle { - x: volumeBar.leftPadding + volumeBar.visualPosition - * (volumeBar.availableWidth - width) - y: volumeBar.topPadding + volumeBar.availableHeight / 2 - height / 2 - implicitWidth: 12 - implicitHeight: 12 - radius: 12 - color: "#f6f6f6" - border.color: "#f6f6f6" - } - - background: Rectangle { - x: volumeBar.leftPadding - y: volumeBar.topPadding + volumeBar.availableHeight / 2 - height / 2 - implicitWidth: 60 - implicitHeight: 3 - width: volumeBar.availableWidth - height: implicitHeight - color: "#33333311" - Rectangle { - width: volumeBar.visualPosition * parent.width - height: parent.height - color: "white" + onMoved: { + renderer.command(["seek", progressBar.value, "absolute"]) } - } - } - Text { - id: timeLabel - text: "0:00 / 0:00" - color: "white" - anchors.left: volumeBar.right - anchors.bottom: parent.bottom - anchors.top: parent.top - padding: 5 - font.family: notoFont.name - font.pixelSize: 12 - verticalAlignment: Text.AlignVCenter - renderType: Text.NativeRendering - } + background: Rectangle { + id: progressBackground + x: progressBar.leftPadding + y: progressBar.topPadding + progressBar.availableHeight / 2 - height / 2 + implicitHeight: (renderer.height / 256) < 2 ? 2 : renderer.height / 256 + width: progressBar.availableWidth + height: implicitHeight + color: Qt.rgba(255, 255, 255, 0.4) - Button { - id: subtitlesButton - icon.name: "subtitles" - icon.source: "icons/subtitles.svg" - icon.color: "white" - Layout.alignment: Qt.AlignVCenter | Qt.AlignRight - anchors.right: settingsButton.left - display: AbstractButton.IconOnly - onClicked: { - tracksMenuUpdate() - subtitlesMenu.visible = !subtitlesMenu.visible - subtitlesMenuBackground.visible = !subtitlesMenuBackground.visible - } - background: Rectangle { - color: "transparent" - } - } + Rectangle { + width: progressBar.visualPosition * parent.width + height: parent.height + color: "red" + opacity: 1 + } + } - Button { - id: settingsButton - icon.name: "settings" - icon.source: "icons/settings.svg" - icon.color: "white" - Layout.alignment: Qt.AlignVCenter | Qt.AlignRight - anchors.right: fullscreenButton.left - display: AbstractButton.IconOnly - onClicked: { - loadDialog.open() - } - background: Rectangle { - color: "transparent" - } - } - - Button { - id: fullscreenButton - icon.name: "fullscreen" - icon.source: "icons/fullscreen.svg" - icon.color: "white" - Layout.alignment: Qt.AlignVCenter | Qt.AlignRight - anchors.right: parent.right - display: AbstractButton.IconOnly - onClicked: { - if (mainWindow.visibility != Window.FullScreen) { - lastScreenVisibility = mainWindow.visibility - mainWindow.visibility = Window.FullScreen - } else { - mainWindow.visibility = lastScreenVisibility + handle: Rectangle { + x: progressBar.leftPadding + progressBar.visualPosition + * (progressBar.availableWidth - width) + y: progressBar.topPadding + progressBar.availableHeight / 2 - height / 2 + implicitWidth: 12 + implicitHeight: 12 + radius: 12 + color: "red" + border.color: "red" } } - background: Rectangle { - color: "transparent" + Button { + id: playlistPrevButton + icon.name: "prev" + icon.source: "icons/prev.svg" + icon.color: "white" + display: AbstractButton.IconOnly + visible: false + width: 0 + onClicked: { + renderer.command(["playlist-prev"]) + updatePrev() + } + background: Rectangle { + color: "transparent" + } } - } - //} + Button { + id: playPauseButton + icon.name: "pause" + icon.source: "icons/pause.svg" + icon.color: "white" + display: AbstractButton.IconOnly + anchors.left: playlistPrevButton.right + onClicked: { + updatePlayPause() + } + background: Rectangle { + color: "transparent" + } + } + + Button { + id: playlistNextButton + icon.name: "next" + icon.source: "icons/next.svg" + icon.color: "white" + display: AbstractButton.IconOnly + anchors.left: playPauseButton.right + onClicked: { + renderer.command(["playlist-next", "force"]) + } + background: Rectangle { + color: "transparent" + } + } + + Button { + id: volumeButton + icon.name: "volume-up" + icon.source: "icons/volume-up.svg" + icon.color: "white" + display: AbstractButton.IconOnly + anchors.left: playlistNextButton.right + onClicked: { + renderer.command(["cycle", "mute"]) + updateVolume() + } + background: Rectangle { + color: "transparent" + } + } + Slider { + id: volumeBar + to: 100 + value: 100 + palette.dark: "#f00" + + implicitWidth: Math.max( + background ? background.implicitWidth : 0, + (handle ? handle.implicitWidth : 0) + + leftPadding + rightPadding) + implicitHeight: Math.max( + background ? background.implicitHeight : 0, + (handle ? handle.implicitHeight : 0) + + topPadding + bottomPadding) + + anchors.left: volumeButton.right + anchors.top: parent.top + anchors.bottom: parent.bottom + onMoved: { + renderer.command(["set", "volume", Math.round( + volumeBar.value).toString()]) + updateVolume() + } + + handle: Rectangle { + x: volumeBar.leftPadding + volumeBar.visualPosition + * (volumeBar.availableWidth - width) + y: volumeBar.topPadding + volumeBar.availableHeight / 2 - height / 2 + implicitWidth: 12 + implicitHeight: 12 + radius: 12 + color: "#f6f6f6" + border.color: "#f6f6f6" + } + + background: Rectangle { + x: volumeBar.leftPadding + y: volumeBar.topPadding + volumeBar.availableHeight / 2 - height / 2 + implicitWidth: 60 + implicitHeight: 3 + width: volumeBar.availableWidth + height: implicitHeight + color: "#33333311" + Rectangle { + width: volumeBar.visualPosition * parent.width + height: parent.height + color: "white" + } + } + } + + Text { + id: timeLabel + text: "0:00 / 0:00" + color: "white" + anchors.left: volumeBar.right + anchors.bottom: parent.bottom + anchors.top: parent.top + padding: 5 + font.family: notoFont.name + font.pixelSize: 12 + verticalAlignment: Text.AlignVCenter + renderType: Text.NativeRendering + } + + Button { + id: subtitlesButton + icon.name: "subtitles" + icon.source: "icons/subtitles.svg" + icon.color: "white" + Layout.alignment: Qt.AlignVCenter | Qt.AlignRight + anchors.right: settingsButton.left + display: AbstractButton.IconOnly + onClicked: { + tracksMenuUpdate() + subtitlesMenu.visible = !subtitlesMenu.visible + subtitlesMenuBackground.visible = !subtitlesMenuBackground.visible + } + background: Rectangle { + color: "transparent" + } + } + + Button { + id: settingsButton + icon.name: "settings" + icon.source: "icons/settings.svg" + icon.color: "white" + Layout.alignment: Qt.AlignVCenter | Qt.AlignRight + anchors.right: fullscreenButton.left + display: AbstractButton.IconOnly + onClicked: { + loadDialog.open() + } + background: Rectangle { + color: "transparent" + } + } + + Button { + id: fullscreenButton + icon.name: "fullscreen" + icon.source: "icons/fullscreen.svg" + icon.color: "white" + Layout.alignment: Qt.AlignVCenter | Qt.AlignRight + anchors.right: parent.right + display: AbstractButton.IconOnly + onClicked: { + if (mainWindow.visibility != Window.FullScreen) { + lastScreenVisibility = mainWindow.visibility + mainWindow.visibility = Window.FullScreen + } else { + mainWindow.visibility = lastScreenVisibility + } + } + + background: Rectangle { + color: "transparent" + } + } + + //} + } } } -