// SPDX-FileCopyrightText: 2020 George Florea Bănuș // SPDX-FileCopyrightText: 2026 Tri Vo Khac // SPDX-License-Identifier: GPL-3.0-or-later import QtQuick import QtQuick.Controls import QtQuick.Layouts import org.kde.ki18n import org.kde.kirigami as Kirigami // Toolbar above the video: open buttons, track menus, translation progress, settings. ToolBar { id: root // Space activates the focused control before the window's playback action. The // controls take focus only from Tab, so a click leaves Space for playback. Keys.onShortcutOverride: event => { if (event.key === Qt.Key_Space && event.modifiers === Qt.NoModifier) { event.accepted = true } } required property Actions actions required property MpvItem mpv required property TranslationService translator // False in full screen and when the user hides the toolbar. property bool shown: true property bool menuBarShown: true readonly property bool isSmallSize: width < Kirigami.Units.gridUnit * 34 readonly property int buttonSize: isSmallSize ? Kirigami.Units.iconSizes.small : Kirigami.Units.iconSizes.smallMedium position: ToolBar.Header state: shown ? "visible" : "hidden" RowLayout { width: parent.width spacing: Kirigami.Units.mediumSpacing HamburgerMenu { actions: root.actions mpv: root.mpv visible: !root.menuBarShown focusPolicy: Qt.TabFocus icon.width: root.buttonSize icon.height: root.buttonSize } ToolButton { action: root.actions.openFile focusPolicy: Qt.TabFocus icon.width: root.buttonSize icon.height: root.buttonSize display: root.isSmallSize ? AbstractButton.IconOnly : AbstractButton.TextBesideIcon ToolTip.text: text ToolTip.visible: hovered ToolTip.delay: Kirigami.Units.toolTipDelay } ToolButton { action: root.actions.openUrl focusPolicy: Qt.TabFocus icon.width: root.buttonSize icon.height: root.buttonSize display: root.isSmallSize ? AbstractButton.IconOnly : AbstractButton.TextBesideIcon ToolTip.text: text ToolTip.visible: hovered ToolTip.delay: Kirigami.Units.toolTipDelay } ToolSeparator {} ToolButton { id: subtitleButton text: KI18n.i18nc("@action:intoolbar", "Subtitles") icon.name: "add-subtitle" icon.width: root.buttonSize icon.height: root.buttonSize focusPolicy: Qt.TabFocus enabled: root.mpv.fileLoaded opacity: enabled ? 1.0 : 0.6 display: root.isSmallSize ? AbstractButton.IconOnly : AbstractButton.TextBesideIcon ToolTip.text: text ToolTip.visible: hovered ToolTip.delay: Kirigami.Units.toolTipDelay Accessible.role: Accessible.ButtonMenu down: subtitleMenu.visible onPressed: subtitleMenu.open() SubtitleTracksMenu { id: subtitleMenu mpv: root.mpv isPrimary: true y: parent.height modal: true dim: false // The track list is empty for files without subtitles, but a file can // still be added. enabled: true MenuSeparator {} AppMenuItem { action: root.actions.translateSubtitle } AppMenuItem { action: root.actions.addSubtitle } } } ToolButton { text: KI18n.i18nc("@action:intoolbar", "Audio") icon.name: "audio-volume-high" icon.width: root.buttonSize icon.height: root.buttonSize focusPolicy: Qt.TabFocus enabled: root.mpv.audioTracks.length > 0 opacity: enabled ? 1.0 : 0.6 display: root.isSmallSize ? AbstractButton.IconOnly : AbstractButton.TextBesideIcon ToolTip.text: text ToolTip.visible: hovered ToolTip.delay: Kirigami.Units.toolTipDelay Accessible.role: Accessible.ButtonMenu down: audioMenu.visible onPressed: audioMenu.open() AudioTracksMenu { id: audioMenu mpv: root.mpv y: parent.height modal: true dim: false } } // Translation progress, with a way to stop it. RowLayout { visible: root.translator.busy spacing: Kirigami.Units.smallSpacing Layout.leftMargin: Kirigami.Units.largeSpacing Kirigami.Icon { source: "translate" implicitWidth: Kirigami.Units.iconSizes.small implicitHeight: Kirigami.Units.iconSizes.small } ProgressBar { from: 0 to: 1 value: root.translator.progress indeterminate: root.translator.progress === 0 Layout.preferredWidth: Kirigami.Units.gridUnit * 6 } Label { text: root.translator.statusText elide: Text.ElideRight visible: !root.isSmallSize Layout.maximumWidth: Kirigami.Units.gridUnit * 14 } ToolButton { action: root.actions.cancelTranslation display: AbstractButton.IconOnly focusPolicy: Qt.TabFocus ToolTip.text: text ToolTip.visible: hovered ToolTip.delay: Kirigami.Units.toolTipDelay } } Item { Layout.fillWidth: true } ToolButton { action: root.actions.configure focusPolicy: Qt.TabFocus icon.width: root.buttonSize icon.height: root.buttonSize display: root.isSmallSize ? AbstractButton.IconOnly : AbstractButton.TextBesideIcon ToolTip.text: text ToolTip.visible: hovered ToolTip.delay: Kirigami.Units.toolTipDelay } } states: [ State { name: "hidden" PropertyChanges { root.height: 0 root.opacity: 0 root.visible: false } }, State { name: "visible" PropertyChanges { root.height: root.implicitHeight root.opacity: 1 root.visible: true } } ] transitions: [ Transition { from: "visible" to: "hidden" SequentialAnimation { ParallelAnimation { NumberAnimation { target: root property: "opacity" duration: Kirigami.Units.veryShortDuration easing.type: Easing.Linear } NumberAnimation { target: root property: "height" duration: Kirigami.Units.veryShortDuration easing.type: Easing.Linear } } PropertyAction { target: root property: "visible" value: false } } }, Transition { from: "hidden" to: "visible" SequentialAnimation { PropertyAction { target: root property: "visible" value: true } ParallelAnimation { NumberAnimation { target: root property: "height" duration: Kirigami.Units.veryShortDuration easing.type: Easing.Linear } NumberAnimation { target: root property: "opacity" duration: Kirigami.Units.veryShortDuration easing.type: Easing.Linear } } } } ] }