diff --git a/qml/AppItemDelegate.qml b/qml/AppItem.qml similarity index 73% rename from qml/AppItemDelegate.qml rename to qml/AppItem.qml index c8ad550..4a2af8b 100644 --- a/qml/AppItemDelegate.qml +++ b/qml/AppItem.qml @@ -18,6 +18,25 @@ Item { signal onClicked + onXChanged: updateGeometryTimer.start() + onYChanged: updateGeometryTimer.start() + + function updateGeometry() { + appModel.updateGeometries(model.appId, Qt.rect(dockItem.mapToGlobal(0, 0).x, + dockItem.mapToGlobal(0, 0).y, + dockItem.width, dockItem.height)) + } + + Timer { + id: updateGeometryTimer + interval: 800 + repeat: false + + onTriggered: { + updateGeometry() + } + } + Menu { id: contextMenu @@ -53,12 +72,15 @@ Item { } DockItem { + id: dockItem anchors.fill: parent iconName: model.iconName isActive: model.isActive popupText: model.visibleName enableActivateDot: model.windowCount !== 0 + onPositionChanged: updateGeometry() + onPressed: updateGeometry() onClicked: appModel.clicked(model.appId) onRightClicked: contextMenu.open() } diff --git a/qml/DockItem.qml b/qml/DockItem.qml index 44c863e..398cf1f 100644 --- a/qml/DockItem.qml +++ b/qml/DockItem.qml @@ -1,7 +1,7 @@ import QtQuick 2.12 import QtQuick.Controls 2.5 -Rectangle { +MouseArea { id: dockItem width: root.height height: root.height @@ -17,6 +17,7 @@ Rectangle { property double iconSizeRatio: 0.8 property var iconName + signal pressed() signal clicked() signal rightClicked() @@ -27,8 +28,6 @@ Rectangle { } } - color: "transparent" - Image { id: icon source: { @@ -128,6 +127,8 @@ Rectangle { hoverEnabled: true acceptedButtons: Qt.LeftButton | Qt.RightButton + onPressed: dockItem.pressed() + onClicked: { if (mouse.button === Qt.LeftButton) dockItem.clicked() diff --git a/qml/main.qml b/qml/main.qml index 775c532..cb5ef57 100644 --- a/qml/main.qml +++ b/qml/main.qml @@ -45,7 +45,7 @@ Rectangle { model: appModel clip: true - delegate: AppItemDelegate { } + delegate: AppItem { } } } diff --git a/resources.qrc b/resources.qrc index 31dc592..345a611 100644 --- a/resources.qrc +++ b/resources.qrc @@ -2,7 +2,7 @@ qml/main.qml qml/DockItem.qml - qml/AppItemDelegate.qml + qml/AppItem.qml svg/launcher.svg qml/PopupTips.qml qml/Menu.qml diff --git a/src/applicationmodel.cpp b/src/applicationmodel.cpp index 11e9a58..3901214 100644 --- a/src/applicationmodel.cpp +++ b/src/applicationmodel.cpp @@ -190,6 +190,19 @@ void ApplicationModel::unPin(const QString &appId) savePinAndUnPinList(); } +void ApplicationModel::updateGeometries(const QString &id, QRect rect) +{ + ApplicationItem *item = findItemById(id); + + // If not found + if (!item) + return; + + for (quint64 id : item->wids) { + m_iface->setIconGeometry(id, rect); + } +} + ApplicationItem *ApplicationModel::findItemByWId(quint64 wid) { for (ApplicationItem *item : m_appItems) { @@ -389,11 +402,17 @@ void ApplicationModel::onWindowRemoved(quint64 wid) void ApplicationModel::onActiveChanged(quint64 wid) { - beginResetModel(); + // Using this method will cause the listview scrollbar to reset. + // beginResetModel(); for (ApplicationItem *item : m_appItems) { - item->isActive = item->wids.contains(wid); - } + if (item->isActive != item->wids.contains(wid)) { + item->isActive = item->wids.contains(wid); - endResetModel(); + QModelIndex idx = index(indexOf(item->id), 0, QModelIndex()); + if (idx.isValid()) { + emit dataChanged(idx, idx); + } + } + } } diff --git a/src/applicationmodel.h b/src/applicationmodel.h index f5209be..adb208f 100644 --- a/src/applicationmodel.h +++ b/src/applicationmodel.h @@ -34,6 +34,8 @@ class ApplicationModel : public QAbstractListModel Q_INVOKABLE void pin(const QString &appId); Q_INVOKABLE void unPin(const QString &appId); + Q_INVOKABLE void updateGeometries(const QString &id, QRect rect); + int iconSize() { return m_iconSize; } signals: diff --git a/src/xwindowinterface.cpp b/src/xwindowinterface.cpp index 994e600..3fbb8c2 100644 --- a/src/xwindowinterface.cpp +++ b/src/xwindowinterface.cpp @@ -168,6 +168,21 @@ QString XWindowInterface::desktopFilePath(quint64 wid) info.windowClassName()); } +void XWindowInterface::setIconGeometry(quint64 wid, const QRect &rect) +{ + NETWinInfo info(QX11Info::connection(), + wid, + (WId) QX11Info::appRootWindow(), + NET::WMIconGeometry, + QFlags(1)); + NETRect nrect; + nrect.pos.x = rect.x(); + nrect.pos.y = rect.y(); + nrect.size.height = rect.height(); + nrect.size.width = rect.width(); + info.setIconGeometry(nrect); +} + void XWindowInterface::onWindowadded(quint64 wid) { if (isAcceptableWindow(wid)) { diff --git a/src/xwindowinterface.h b/src/xwindowinterface.h index 7cecfa8..78e1046 100644 --- a/src/xwindowinterface.h +++ b/src/xwindowinterface.h @@ -33,6 +33,8 @@ class XWindowInterface : public QObject QString desktopFilePath(quint64 wid); + void setIconGeometry(quint64 wid, const QRect &rect); + signals: void windowAdded(quint64 wid); void windowRemoved(quint64 wid);