aerothemeplasma/Plasma/Plasma Widgets/User/Task Icons/org.kde.plasma.seventasks/contents/ui/MouseHandler.qml
wackyideas 165fa81da4 Fixes incorrect behaviour when using SevenTasks while it is configured to sort tasks manually.
Expected behaviour:

1. Dragging pinned tasks around should update their position correctly and keep that position permanently
2. Dragging items that are NOT tasks should focus the task that is being hovered over for easier drag and drop functionality

Actual behaviour:

1. Dragging pinned tasks around seemingly works, until the task manager is updated in any kind of way, at which point the positions are reverted back to the original state.
2. Dragging items that aren't tasks will only focus the hovered task if previous dragging actions didn't occur between two or more tasks. After that, trying to drag items onto the taskbar will cause the task that was dragged last time to move around according to the mouse's position.
2022-09-12 20:37:06 +02:00

188 lines
5.5 KiB
QML

/*
SPDX-FileCopyrightText: 2012-2016 Eike Hein <hein@kde.org>
SPDX-License-Identifier: GPL-2.0-or-later
*/
import QtQuick 2.0
import org.kde.draganddrop 2.0
import org.kde.taskmanager 0.1 as TaskManager
import "code/tools.js" as TaskTools
Item {
signal urlsDropped(var urls)
property Item target
property Item ignoredItem
property bool moved: false
property bool isGroupDialog: false
property alias hoveredItem: dropHandler.hoveredItem
property alias handleWheelEvents: wheelHandler.active
Timer {
id: ignoreItemTimer
repeat: false
interval: 750
onTriggered: {
ignoredItem = null;
}
}
Connections {
target: tasks
function onDragSourceChanged() {
if (!dragSource) {
ignoredItem = null;
ignoreItemTimer.stop();
}
}
}
DropArea {
id: dropHandler
anchors.fill: parent
preventStealing: true;
property Item hoveredItem
//ignore anything that is neither internal to TaskManager or a URL list
onDragEnter: {
if (event.mimeData.formats.indexOf("text/x-plasmoidservicename") >= 0) {
event.ignore();
}
}
onDragMove: {
if (target.animating) {
return;
}
//var above = target.childAt(event.x, event.y);
let above;
if (isGroupDialog) {
above = target.itemAt(event.x, event.y);
} else {
above = target.childAt(event.x, event.y);
}
if (!above) {
hoveredItem = null;
activationTimer.stop();
return;
}
// If we're mixing launcher tasks with other tasks and are moving
// a (small) launcher task across a non-launcher task, don't allow
// the latter to be the move target twice in a row for a while, as
// it will naturally be moved underneath the cursor as result of the
// initial move, due to being far larger than the launcher delegate.
// TODO: This restriction (minus the timer, which improves things)
// has been proven out in the EITM fork, but could be improved later
// by tracking the cursor movement vector and allowing the drag if
// the movement direction has reversed, establishing user intent to
// move back.
if (!plasmoid.configuration.separateLaunchers && tasks.dragSource != null
&& tasks.dragSource.m.IsLauncher === true && above.m.IsLauncher !== true
&& above === ignoredItem) {
return;
} else {
ignoredItem = null;
}
if (tasksModel.sortMode === TaskManager.TasksModel.SortManual && tasks.dragSource) {
// Reject drags between different TaskList instances.
if (tasks.dragSource.parent !== above.parent) {
return;
}
var insertAt = TaskTools.insertIndexAt(above, event.x, event.y);
if (tasks.dragSource !== above && tasks.dragSource.itemIndex !== insertAt) {
if (!!tasks.groupDialog) {
tasksModel.move(tasks.dragSource.itemIndex, insertAt,
tasksModel.makeModelIndex(tasks.groupDialog.visualParent.itemIndex));
} else {
tasksModel.move(tasks.dragSource.itemIndex, insertAt);
}
ignoredItem = above;
ignoreItemTimer.restart();
}
} else if (!tasks.dragSource && hoveredItem !== above) {
hoveredItem = above;
activationTimer.restart();
}
tasksModel.syncLaunchers();
}
onDragLeave: {
hoveredItem = null;
activationTimer.stop();
}
onDrop: {
// Reject internal drops.
if (event.mimeData.formats.indexOf("application/x-orgkdeplasmataskmanager_taskbuttonitem") >= 0) {
event.ignore();
return;
}
// Reject plasmoid drops.
if (event.mimeData.formats.indexOf("text/x-plasmoidservicename") >= 0) {
event.ignore();
return;
}
if (event.mimeData.hasUrls) {
parent.urlsDropped(event.mimeData.urls);
return;
}
}
Timer {
id: activationTimer
interval: 250
repeat: false
onTriggered: {
if (parent.hoveredItem.m.IsGroupParent === true) {
groupDialog.visualParent = parent.hoveredItem;
groupDialog.visible = true;
} else if (parent.hoveredItem.m.IsLauncher !== true) {
tasksModel.requestActivate(parent.hoveredItem.modelIndex());
}
}
}
}
MouseArea {
id: wheelHandler
anchors.fill: parent
enabled: active && plasmoid.configuration.wheelEnabled
property bool active: true
property int wheelDelta: 0;
onWheel: {
if (!active) {
wheel.accepted = false;
return;
}
wheelDelta = TaskTools.wheelActivateNextPrevTask(null, wheelDelta, wheel.angleDelta.y);
}
}
}