Warning, /plasma/aura-browser/app/qml/views/TileViewTabs.qml is written in an unsupported language. File is not indexed.

0001 /*
0002     SPDX-FileCopyrightText: 2019 Aditya Mehra <aix.m@outlook.com>
0003     SPDX-FileCopyrightText: 2019 Marco Martin <mart@kde.org>
0004 
0005     SPDX-License-Identifier: GPL-2.0-or-later
0006 */
0007 
0008 import QtQuick 2.10
0009 import QtQuick.Layouts 1.3
0010 import QtQuick.Window 2.10
0011 import QtQuick.Controls 2.10 as Controls
0012 import Aura 1.0 as Aura
0013 import Qt5Compat.GraphicalEffects
0014 import org.kde.kirigami as Kirigami
0015 
0016 FocusScope {
0017     id: root
0018     signal activated
0019     property string title
0020     property alias view: view
0021     property alias delegate: view.delegate
0022     property alias model: view.model
0023     property alias currentIndex: view.currentIndex
0024     property alias currentItem: view.currentItem
0025 
0026     implicitHeight: view.implicitHeight + header.implicitHeight
0027 
0028     //TODO:dynamic
0029     property int columns: Math.max(3, Math.floor(width / (Kirigami.Units.gridUnit * 15)))
0030 
0031     property alias cellWidth: view.cellWidth
0032     readonly property real screenRatio: view.Window.window ? view.Window.window.width / view.Window.window.height : 1.6
0033 
0034     property Item navigationUp
0035     property Item navigationDown
0036 
0037     Kirigami.Heading {
0038         id: header
0039         anchors {
0040             left: parent.left
0041             right: parent.right
0042             top: parent.top
0043         }
0044         text: title
0045         color: Kirigami.Theme.textColor
0046         layer.enabled: true
0047         layer.effect: DropShadow {
0048             horizontalOffset: 0
0049             verticalOffset: 2
0050             radius: 8.0
0051             samples: 17
0052             color: Qt.rgba(0,0,0,0.6)
0053         }
0054     }
0055     
0056     ListView {
0057         id: view
0058         anchors {
0059             left: parent.left
0060             right: parent.right
0061             top: header.bottom
0062             bottom: parent.bottom
0063         }
0064         focus: true
0065 
0066         z: activeFocus ? 10: 1
0067         keyNavigationEnabled: true
0068         //Centering disabled as experiment
0069         //highlightRangeMode: ListView.ApplyRange
0070         highlightFollowsCurrentItem: true
0071         snapMode: ListView.SnapToItem
0072         cacheBuffer: width
0073         implicitHeight: Math.floor(cellWidth/screenRatio)
0074 
0075         highlight: Rectangle {
0076             color: Kirigami.Theme.linkColor
0077         }
0078 
0079         readonly property int cellWidth: Math.floor(width / columns)
0080         //preferredHighlightBegin: width/view.columns
0081         //preferredHighlightEnd: width/view.columns * 2
0082 
0083         displayMarginBeginning: rotation.angle != 0 ? width*2 : 0
0084         displayMarginEnd: rotation.angle != 0 ? width*2 : 0
0085         highlightMoveDuration: Kirigami.Units.longDuration
0086         transform: Rotation {
0087             id: rotation
0088             axis { x: 0; y: 1; z: 0 }
0089             angle: 0
0090             property real targetAngle: 30
0091             Behavior on angle {
0092                 SmoothedAnimation {
0093                     duration: Kirigami.Units.longDuration * 10
0094                 }
0095             }
0096             origin.x: width/2
0097         }
0098 
0099         Timer {
0100             id: rotateTimeOut
0101             interval: 25
0102         }
0103         Timer {
0104             id: rotateTimer
0105             interval: 500
0106             onTriggered: {
0107                 if (rotateTimeOut.running) {
0108                     rotation.angle = rotation.targetAngle;
0109                     restart();
0110                 } else {
0111                     rotation.angle = 0;
0112                 }
0113             }
0114         }
0115         spacing: 0
0116         orientation: ListView.Horizontal
0117 
0118         opacity: Kirigami.ScenePosition.y >= 0
0119         Behavior on opacity {
0120             OpacityAnimator {
0121                 duration: Kirigami.Units.longDuration * 2
0122                 easing.type: Easing.InOutQuad
0123             }
0124         }
0125 
0126         property real oldContentX
0127         onContentXChanged: {
0128             if (oldContentX < contentX) {
0129                 rotation.targetAngle = 30;
0130             } else {
0131                 rotation.targetAngle = -30;
0132             }
0133             Controls.ScrollBar.horizontal.opacity = 1;
0134             if (!rotateTimeOut.running) {
0135                 rotateTimer.restart();
0136             }
0137             rotateTimeOut.restart();
0138             oldContentX = contentX;
0139         }
0140         Controls.ScrollBar.horizontal: Controls.ScrollBar {
0141             id: scrollBar
0142             opacity: 0
0143             interactive: false
0144             onOpacityChanged: disappearTimer.restart()
0145             Timer {
0146                 id: disappearTimer
0147                 interval: 1000
0148                 onTriggered: scrollBar.opacity = 0;
0149             }
0150             Behavior on opacity {
0151                 OpacityAnimator {
0152                     duration: Kirigami.Units.longDuration
0153                     easing.type: Easing.InOutQuad
0154                 }
0155             }
0156         }
0157 
0158         move: Transition {
0159             SmoothedAnimation {
0160                 property: "x"
0161                 duration: Kirigami.Units.longDuration
0162             }
0163         }
0164 
0165         KeyNavigation.left: root
0166         KeyNavigation.right: root
0167 
0168         Keys.onDownPressed: (event)=> {
0169             Aura.NavigationSoundEffects.playMovingSound();
0170             if (!navigationDown) {
0171                 return;
0172             }
0173 
0174             if (navigationDown instanceof TileView) {
0175                 navigationDown.currentIndex = navigationDown.view.indexAt(navigationDown.view.mapFromItem(currentItem, cellWidth/2, height/2).x, height/2);
0176                 if (navigationDown.currentIndex < 0) {
0177                     navigationDown.currentIndex = view.currentIndex > 0 ? navigationDown.view.count - 1 : 0
0178                 }
0179             }
0180 
0181             navigationDown.forceActiveFocus();
0182         }
0183 
0184         Keys.onUpPressed: (event)=> {
0185             Aura.NavigationSoundEffects.playMovingSound();
0186             if (!navigationUp) {
0187                 return;
0188             }
0189 
0190             if (navigationUp instanceof TileView) {
0191                 navigationUp.view.currentIndex = navigationUp.view.indexAt(navigationUp.view.contentItem.mapFromItem(currentItem, cellWidth/2, height/2).x, height/2);
0192                 if (navigationUp.currentIndex < 0) {
0193                     navigationUp.currentIndex = view.currentIndex > 0 ? navigationUp.view.count - 1 : 0
0194                 }
0195             }
0196 
0197             navigationUp.forceActiveFocus();
0198         }
0199 
0200         Keys.onPressed: (event)=> {
0201             switch (event.key) {
0202                 case Qt.Key_Right:
0203                 case Qt.Key_Left:
0204                 case Qt.Key_Tab:
0205                 case Qt.Key_Backtab:
0206                     Aura.NavigationSoundEffects.playMovingSound();
0207                     break;
0208                 default:
0209                     break;
0210             }
0211         }
0212     }
0213 }