add type annotations to taskswitcher QML and do more explicit typing

This commit is contained in:
Luis Büchi 2025-06-26 16:30:41 +02:00
parent 2689913bc2
commit 5d33295443
7 changed files with 45 additions and 43 deletions

View file

@ -1,4 +1,5 @@
// SPDX-FileCopyrightText: 2021-2023 Devin Lin <devin@kde.org> // SPDX-FileCopyrightText: 2021-2023 Devin Lin <devin@kde.org>
// SPDX-FileCopyrightText: 2025 Luis Büchi <luis.buechi@kdemail.net>
// SPDX-License-Identifier: LGPL-2.0-or-later // SPDX-License-Identifier: LGPL-2.0-or-later
import QtQuick import QtQuick
@ -65,7 +66,7 @@ Flickable {
} }
} }
function resetPosition() { function resetPosition(): void {
oldContentX = startContentX; oldContentX = startContentX;
contentX = startContentX; contentX = startContentX;
} }

View file

@ -1,6 +1,6 @@
// SPDX-FileCopyrightText: 2015 Marco Martin <notmart@gmail.com> // SPDX-FileCopyrightText: 2015 Marco Martin <notmart@gmail.com>
// SPDX-FileCopyrightText: 2021-2023 Devin Lin <devin@kde.org> // SPDX-FileCopyrightText: 2021-2023 Devin Lin <devin@kde.org>
// SPDX-FileCopyrightText: 2024 Luis Büchi <luis.buechi@kdemail.net> // SPDX-FileCopyrightText: 2024-2025 Luis Büchi <luis.buechi@kdemail.net>
// SPDX-License-Identifier: GPL-2.0-or-later // SPDX-License-Identifier: GPL-2.0-or-later
import QtQuick import QtQuick
@ -41,18 +41,18 @@ Item {
opacity: 1 - dragOffset / taskSwitcher.height opacity: 1 - dragOffset / taskSwitcher.height
//BEGIN functions //BEGIN functions
function closeApp() { function closeApp(): void {
delegate.window.closeWindow(); delegate.window.closeWindow();
} }
function activateApp() { function activateApp(): void {
if (!ShellSettings.Settings.convergenceModeEnabled) { if (!ShellSettings.Settings.convergenceModeEnabled) {
delegate.window.setMaximize(true, true); delegate.window.setMaximize(true, true);
} }
taskSwitcherHelpers.openApp(model.index); taskSwitcherHelpers.openApp(model.index);
} }
function minimizeApp() { function minimizeApp(): void {
delegate.window.minimized = true; delegate.window.minimized = true;
} }
//END functions //END functions

View file

@ -1,4 +1,5 @@
// SPDX-FileCopyrightText: 2021 Devin Lin <devin@kde.org> // SPDX-FileCopyrightText: 2021 Devin Lin <devin@kde.org>
// SPDX-FileCopyrightText: 2025 Luis Büchi <luis.buechi@kdemail.net>
// SPDX-License-Identifier: GPL-2.0-or-later // SPDX-License-Identifier: GPL-2.0-or-later
import QtQuick import QtQuick
@ -41,17 +42,17 @@ MouseArea {
return taskYBase - trackFingerYOffsetClamped; return taskYBase - trackFingerYOffsetClamped;
} }
function getTaskAt(index) { function getTaskAt(index: int): Task {
return repeater.itemAt(index); return repeater.itemAt(index);
} }
function closeAll() { function closeAll(): void {
for (let i = 0; i < repeater.count; i++) { for (let i = 0; i < repeater.count; i++) {
repeater.itemAt(i).closeApp(); repeater.itemAt(i).closeApp();
} }
} }
function minimizeAll() { function minimizeAll(): void {
for (let i = 0; i < repeater.count; i++) { for (let i = 0; i < repeater.count; i++) {
let item = repeater.itemAt(i); let item = repeater.itemAt(i);
@ -62,7 +63,7 @@ MouseArea {
} }
} }
function jumpToFirstVisibleWindow() { function jumpToFirstVisibleWindow(): void {
for (let i = 0; i < repeater.count; i++) { for (let i = 0; i < repeater.count; i++) {
let item = repeater.itemAt(i); let item = repeater.itemAt(i);
@ -94,7 +95,7 @@ MouseArea {
} }
// dynamic task offset animation duration based off of the touch position and task scale // dynamic task offset animation duration based off of the touch position and task scale
function dynamicDuration(left = true) { function dynamicDuration(left = true): int {
// if the close animation is running, use the standard long duration time for consistency // if the close animation is running, use the standard long duration time for consistency
let duration = Kirigami.Units.longDuration * 1.75 let duration = Kirigami.Units.longDuration * 1.75
if (!taskSwitcherHelpers.closeAnim.running && taskSwitcherHelpers.notHomeScreenState && taskSwitcherHelpers.gestureState != TaskSwitcherHelpers.GestureStates.HorizontalSwipe && !taskSwitcherHelpers.isInTaskScrubMode) { if (!taskSwitcherHelpers.closeAnim.running && taskSwitcherHelpers.notHomeScreenState && taskSwitcherHelpers.gestureState != TaskSwitcherHelpers.GestureStates.HorizontalSwipe && !taskSwitcherHelpers.isInTaskScrubMode) {
@ -117,7 +118,7 @@ MouseArea {
property bool setOffsetDurationImmediately: true property bool setOffsetDurationImmediately: true
// set the task offset value with an animation unless specified otherwise // set the task offset value with an animation unless specified otherwise
function setTaskOffsetValue(value, immediately = false, taskEasing = ((taskSwitcherHelpers.notHomeScreenState || (value != 0)) && (baseTaskOffset != taskSwitcherHelpers.taskOffsetValue)) ? Easing.InOutQuart : Easing.OutQuart) { function setTaskOffsetValue(value: int, immediately = false, taskEasing = ((taskSwitcherHelpers.notHomeScreenState || (value != 0)) && (baseTaskOffset != taskSwitcherHelpers.taskOffsetValue)) ? Easing.InOutQuart : Easing.OutQuart): void {
if (baseTaskOffset == value && immediately) { if (baseTaskOffset == value && immediately) {
baseTaskOffset = value + 1; baseTaskOffset = value + 1;
} }

View file

@ -1,6 +1,6 @@
// SPDX-FileCopyrightText: 2015 Marco Martin <notmart@gmail.com> // SPDX-FileCopyrightText: 2015 Marco Martin <notmart@gmail.com>
// SPDX-FileCopyrightText: 2021-2024 Devin Lin <devin@kde.org> // SPDX-FileCopyrightText: 2021-2024 Devin Lin <devin@kde.org>
// SPDX-FileCopyrightText: 2024 Luis Büchi <luis.buechi@kdemail.net> // SPDX-FileCopyrightText: 2024-2025 Luis Büchi <luis.buechi@kdemail.net>
// SPDX-License-Identifier: GPL-2.0-or-later // SPDX-License-Identifier: GPL-2.0-or-later
import QtQuick import QtQuick
@ -46,7 +46,7 @@ FocusScope {
id: haptics id: haptics
} }
property var tasksModel: TaskSwitcherPlugin.TaskFilterModel { property TaskSwitcherPlugin.TaskFilterModel tasksModel: TaskSwitcherPlugin.TaskFilterModel {
screenName: root.targetScreen.name screenName: root.targetScreen.name
windowModel: root.state.taskModel windowModel: root.state.taskModel
} }
@ -87,7 +87,7 @@ FocusScope {
initialSetup(); initialSetup();
} }
function initialSetup() { function initialSetup(): void {
taskSwitcherHelpers.cancelAnimations(); taskSwitcherHelpers.cancelAnimations();
state.updateWasInActiveTask(KWinComponents.Workspace.activeWindow); state.updateWasInActiveTask(KWinComponents.Workspace.activeWindow);
@ -143,15 +143,15 @@ FocusScope {
} }
// called by c++ plugin // called by c++ plugin
function hideAnimation() { function hideAnimation(): void {
closeAnim.restart(); closeAnim.restart();
} }
function instantHide() { function instantHide(): void {
root.state.deactivate(true); root.state.deactivate(true);
} }
function hide() { function hide(): void {
root.state.deactivate(false); root.state.deactivate(false);
} }
@ -159,7 +159,7 @@ FocusScope {
target: root.state target: root.state
// task scrub mode allows scrubbing through a number of tasks with a mostly horizontal motion // task scrub mode allows scrubbing through a number of tasks with a mostly horizontal motion
function taskScrubMode() { function taskScrubMode(): void {
taskList.setTaskOffsetValue(0, false, Easing.OutQuart); taskList.setTaskOffsetValue(0, false, Easing.OutQuart);
if (!taskSwitcherHelpers.isInTaskScrubMode) { if (!taskSwitcherHelpers.isInTaskScrubMode) {
backgroundColorOpacity = 1; backgroundColorOpacity = 1;
@ -180,7 +180,7 @@ FocusScope {
} }
} }
function onTouchPositionChanged() { function onTouchPositionChanged(): void {
let unmodifiedYposition = Math.abs(state.touchYPosition) let unmodifiedYposition = Math.abs(state.touchYPosition)
if (taskSwitcherHelpers.isInTaskScrubMode || // once in scrub mode, let's not allow to go out, that can result in inconsistent UX if (taskSwitcherHelpers.isInTaskScrubMode || // once in scrub mode, let's not allow to go out, that can result in inconsistent UX
(Math.abs(state.xVelocity) > Math.abs(state.yVelocity) * 3 && // gesture needs to be almost completely horizontal (Math.abs(state.xVelocity) > Math.abs(state.yVelocity) * 3 && // gesture needs to be almost completely horizontal
@ -220,7 +220,7 @@ FocusScope {
} }
} }
function updateTaskSwitcherState() { function updateTaskSwitcherState(): void {
let unmodifiedYposition = Math.abs(state.touchYPosition) let unmodifiedYposition = Math.abs(state.touchYPosition)
// if the touch is above heightThreshold, set reachedHeightThreshold to true // if the touch is above heightThreshold, set reachedHeightThreshold to true
@ -309,13 +309,13 @@ FocusScope {
// returns to the currently centered app. usually used to "back out" of the switcher // returns to the currently centered app. usually used to "back out" of the switcher
// if accidentally invoked, but can also be used to switch to an adjacent app and then open it // if accidentally invoked, but can also be used to switch to an adjacent app and then open it
function returnToApp() { function returnToApp(): void {
let newIndex = taskSwitcherHelpers.getNearestTaskIndex(); let newIndex = taskSwitcherHelpers.getNearestTaskIndex();
taskSwitcherHelpers.openApp(newIndex); taskSwitcherHelpers.openApp(newIndex);
} }
// diagonal quick switch gesture logic // diagonal quick switch gesture logic
function quickSwitch() { function quickSwitch(): void {
// should "quick switch" to adjacent app in task switcher, but only if we were in an app before // should "quick switch" to adjacent app in task switcher, but only if we were in an app before
let unmodifiedYposition = Math.abs(state.touchYPosition) let unmodifiedYposition = Math.abs(state.touchYPosition)
let newIndex = state.currentTaskIndex; let newIndex = state.currentTaskIndex;
@ -361,7 +361,7 @@ FocusScope {
} }
// Logic for deciding how to handle the end of a gesture input // Logic for deciding how to handle the end of a gesture input
function onGestureInProgressChanged() { function onGestureInProgressChanged(): void {
taskSwitcherHelpers.fromButton = false; taskSwitcherHelpers.fromButton = false;
if (state.gestureInProgress) { if (state.gestureInProgress) {
taskSwitcherHelpers.currentDisplayTask = state.currentTaskIndex; taskSwitcherHelpers.currentDisplayTask = state.currentTaskIndex;
@ -409,11 +409,11 @@ FocusScope {
} }
} }
function onVelocityChanged() { function onVelocityChanged(): void {
} }
function onXPositionChanged() { function onXPositionChanged(): void {
taskSwitcherHelpers.updateTaskIndex(); taskSwitcherHelpers.updateTaskIndex();
} }
} }
@ -425,7 +425,7 @@ FocusScope {
onTriggered: taskSwitcherHelpers.taskSwitchCanLaunch = true; onTriggered: taskSwitcherHelpers.taskSwitchCanLaunch = true;
} }
function setTaskDrawerState(value) { function setTaskDrawerState(value: int): void {
if (taskSwitcherHelpers.gestureState != TaskSwitcherHelpers.GestureStates.TaskSwitcher && value == TaskSwitcherHelpers.GestureStates.TaskSwitcher) { if (taskSwitcherHelpers.gestureState != TaskSwitcherHelpers.GestureStates.TaskSwitcher && value == TaskSwitcherHelpers.GestureStates.TaskSwitcher) {
// vibrate only if switching to task drawer // vibrate only if switching to task drawer
if (!taskSwitcherHelpers.hasVibrated) { if (!taskSwitcherHelpers.hasVibrated) {

View file

@ -1,5 +1,5 @@
// SPDX-FileCopyrightText: 2021 Devin Lin <devin@kde.org> // SPDX-FileCopyrightText: 2021 Devin Lin <devin@kde.org>
// SPDX-FileCopyrightText: 2024 Luis Büchi <luis.buechi@kdemail.net> // SPDX-FileCopyrightText: 2024-2025 Luis Büchi <luis.buechi@kdemail.net>
// SPDX-License-Identifier: GPL-2.0-or-later // SPDX-License-Identifier: GPL-2.0-or-later
import QtQuick 2.15 import QtQuick 2.15
@ -175,7 +175,7 @@ QtObject {
xAnim.stop(); xAnim.stop();
} }
function getTaskIndexFromWindow(window) { function getTaskIndexFromWindow(window: KWinComponents.Window): int {
for (let i = 0; i < taskSwitcher.tasksModel.rowCount(); i++) { for (let i = 0; i < taskSwitcher.tasksModel.rowCount(); i++) {
const modelWindow = taskSwitcher.tasksModel.data(taskSwitcher.tasksModel.index(i, 0), Qt.DisplayRole); const modelWindow = taskSwitcher.tasksModel.data(taskSwitcher.tasksModel.index(i, 0), Qt.DisplayRole);
if (modelWindow == window) { if (modelWindow == window) {
@ -185,20 +185,20 @@ QtObject {
return 0; return 0;
} }
function getTaskIndexFromXPosition() { function getTaskIndexFromXPosition(): int {
let candidateIndex = Math.round(-root.state.xPosition / (taskSpacing + taskWidth)); let candidateIndex = Math.round(-root.state.xPosition / (taskSpacing + taskWidth));
return Math.max(0, Math.min(taskSwitcher.tasksCount - 1, candidateIndex)); return Math.max(0, Math.min(taskSwitcher.tasksCount - 1, candidateIndex));
} }
// TODO either use updateTaskIndex to always have the "newest current task index" in the state var or use "getNearestTaskIndex", not both it's redundant // TODO either use updateTaskIndex to always have the "newest current task index" in the state var or use "getNearestTaskIndex", not both it's redundant
function updateTaskIndex() { function updateTaskIndex(): void {
// only set if not gesture currently in progress to prevent glitching // only set if not gesture currently in progress to prevent glitching
if (!(state.gestureInProgress || root.closeAnim.running || root.openAppAnim.running) || root.isInTaskScrubMode) { if (!(state.gestureInProgress || root.closeAnim.running || root.openAppAnim.running) || root.isInTaskScrubMode) {
root.state.currentTaskIndex = getTaskIndexFromXPosition(); root.state.currentTaskIndex = getTaskIndexFromXPosition();
} }
} }
function open() { function open(): void {
root.gestureState = TaskSwitcherHelpers.GestureStates.TaskSwitcher; root.gestureState = TaskSwitcherHelpers.GestureStates.TaskSwitcher;
openAnim.restart(); openAnim.restart();
@ -206,7 +206,7 @@ QtObject {
taskList.setTaskOffsetValue(0, false, Easing.OutQuart); taskList.setTaskOffsetValue(0, false, Easing.OutQuart);
} }
function close() { function close(): void {
// update the task offset position // update the task offset position
taskList.setTaskOffsetValue(homeOffsetValue + 0.25, false, Easing.Linear); taskList.setTaskOffsetValue(homeOffsetValue + 0.25, false, Easing.Linear);
@ -218,7 +218,7 @@ QtObject {
closeFactorAnim.restart(); closeFactorAnim.restart();
} }
function openApp(index, duration = Kirigami.Units.shortDuration, horizontalEasing = Easing.OutBack) { function openApp(index: int, duration = Kirigami.Units.shortDuration, horizontalEasing = Easing.OutBack): void {
// cancel any opening animations ongoing // cancel any opening animations ongoing
openAnim.stop(); openAnim.stop();
cancelAnimations(); cancelAnimations();
@ -229,24 +229,24 @@ QtObject {
} }
// get the xPosition where the task will be centered on the screen // get the xPosition where the task will be centered on the screen
function xPositionFromTaskIndex(index) { function xPositionFromTaskIndex(index: int): int {
return -index * (taskWidth + taskSpacing); return -index * (taskWidth + taskSpacing);
} }
// instantly go to the task index // instantly go to the task index
function goToTaskIndex(index) { function goToTaskIndex(index: int): void {
root.state.xPosition = xPositionFromTaskIndex(index); root.state.xPosition = xPositionFromTaskIndex(index);
} }
// go to the task index, animated // go to the task index, animated
function animateGoToTaskIndex(index, duration = Kirigami.Units.longDuration * 2, easing = Easing.OutExpo) { function animateGoToTaskIndex(index: int, duration = Kirigami.Units.longDuration * 2, easing = Easing.OutExpo): void {
xAnimDuration = duration; xAnimDuration = duration;
xAnimEasingType = easing; xAnimEasingType = easing;
xAnim.to = xPositionFromTaskIndex(index) - (gestureState == TaskSwitcherHelpers.GestureStates.HorizontalSwipe && !state.gestureInProgress && notHomeScreenState ? taskSpacing / 2 : 0); xAnim.to = xPositionFromTaskIndex(index) - (gestureState == TaskSwitcherHelpers.GestureStates.HorizontalSwipe && !state.gestureInProgress && notHomeScreenState ? taskSpacing / 2 : 0);
xAnim.restart(); xAnim.restart();
} }
function getNearestTaskIndex() { function getNearestTaskIndex(): int {
let newTaskIndex = getTaskIndexFromXPosition(); let newTaskIndex = getTaskIndexFromXPosition();
let currentTaskIndexPosition = xPositionFromTaskIndex(root.state.currentTaskIndex); let currentTaskIndexPosition = xPositionFromTaskIndex(root.state.currentTaskIndex);
if (root.state.xPosition > currentTaskIndexPosition) { if (root.state.xPosition > currentTaskIndexPosition) {
@ -269,14 +269,14 @@ QtObject {
} }
} }
} }
function snapToNearestTask() { function snapToNearestTask(): void {
let index = getNearestTaskIndex(); let index = getNearestTaskIndex();
animateGoToTaskIndex(index); animateGoToTaskIndex(index);
} }
// This is a workaround for flickable not actually flicking, so we just snap to the next task // This is a workaround for flickable not actually flicking, so we just snap to the next task
// based on old movement direction, ignoring momentum (because flickable doesn't give us any momentum) // based on old movement direction, ignoring momentum (because flickable doesn't give us any momentum)
function snapToNearestTaskWorkaround(movingRight) { function snapToNearestTaskWorkaround(movingRight: bool): void {
let currentTaskIndexPosition = xPositionFromTaskIndex(root.state.currentTaskIndex); let currentTaskIndexPosition = xPositionFromTaskIndex(root.state.currentTaskIndex);
if (root.state.xPosition > currentTaskIndexPosition) { if (root.state.xPosition > currentTaskIndexPosition) {
if (movingRight) { if (movingRight) {

View file

@ -48,12 +48,12 @@ class MobileTaskSwitcherState : public QObject
Q_PROPERTY(qreal yPosition READ yPosition WRITE setYPosition NOTIFY yPositionChanged) Q_PROPERTY(qreal yPosition READ yPosition WRITE setYPosition NOTIFY yPositionChanged)
Q_PROPERTY(bool gestureInProgress READ gestureInProgress NOTIFY gestureInProgressChanged) Q_PROPERTY(bool gestureInProgress READ gestureInProgress NOTIFY gestureInProgressChanged)
Q_PROPERTY(Status status READ status WRITE setStatus NOTIFY statusChanged) Q_PROPERTY(KWin::MobileTaskSwitcherState::Status status READ status WRITE setStatus NOTIFY statusChanged)
Q_PROPERTY(qint64 elapsedTimeSinceStart READ getElapsedTimeSinceStart) Q_PROPERTY(qint64 elapsedTimeSinceStart READ getElapsedTimeSinceStart)
Q_PROPERTY(qint64 doubleClickInterval READ getDoubleClickInterval) // is there a better way than to forward this? Q_PROPERTY(qint64 doubleClickInterval READ getDoubleClickInterval) // is there a better way than to forward this?
Q_PROPERTY(TaskModel *taskModel READ taskModel CONSTANT) Q_PROPERTY(KWin::TaskModel *taskModel READ taskModel CONSTANT)
QML_ELEMENT QML_ELEMENT
public: public:

View file

@ -20,7 +20,7 @@ namespace KWin
class TaskFilterModel : public QSortFilterProxyModel class TaskFilterModel : public QSortFilterProxyModel
{ {
Q_OBJECT Q_OBJECT
Q_PROPERTY(TaskModel *windowModel READ windowModel WRITE setWindowModel NOTIFY windowModelChanged) Q_PROPERTY(KWin::TaskModel *windowModel READ windowModel WRITE setWindowModel NOTIFY windowModelChanged)
Q_PROPERTY(QString screenName READ screenName WRITE setScreenName NOTIFY screenNameChanged) Q_PROPERTY(QString screenName READ screenName WRITE setScreenName NOTIFY screenNameChanged)
QML_ELEMENT QML_ELEMENT
@ -28,7 +28,7 @@ public:
explicit TaskFilterModel(QObject *parent = nullptr); explicit TaskFilterModel(QObject *parent = nullptr);
TaskModel *windowModel() const; TaskModel *windowModel() const;
void setWindowModel(TaskModel *taskModel); void setWindowModel(KWin::TaskModel *taskModel);
QString screenName() const; QString screenName() const;
void setScreenName(const QString &screenName); void setScreenName(const QString &screenName);