Repository navigation
feat(dock): support compositor-driven dock resize - #1732
Conversation
Reviewer's GuideThe dock now negotiates compositor-owned interactive resizing through the Treeland layer-shell extension, passing Wayland input and size constraints to the compositor and adapting the QML drag state machine to consume compositor-driven size and lifecycle updates, with legacy client-side resizing retained as a fallback. Sequence diagram for compositor-driven dock resizesequenceDiagram
actor User
participant DragArea
participant DockPanel
participant LayerShell as LayerShellExtension
participant Compositor
User->>DragArea: onPressed
DragArea->>DockPanel: beginDockResize(edges)
DockPanel->>LayerShell: getLayerShellExtensionObject(surface)
DockPanel->>LayerShell: beginResize(seat, serial, edges, constraints)
LayerShell->>Compositor: begin_resize(...)
Compositor-->>LayerShell: resizing(1)
LayerShell-->>DockPanel: resizingChanged(true)
DockPanel-->>DragArea: onIsResizingChanged(true)
Compositor-->>DragArea: configure size
DragArea->>DragArea: update dockSize from width or height
User-->>Compositor: release pointer
Compositor-->>LayerShell: resizing(0)
LayerShell-->>DockPanel: resizingChanged(false)
DockPanel-->>DragArea: onIsResizingChanged(false)
DragArea->>DragArea: finishResize()
Flow diagram for dock resize fallbackflowchart TD
Press["Dock drag begins"] --> Begin["Panel.beginDockResize(edges)"]
Begin --> Available{"Layer-shell extension active and Wayland handles available?"}
Available -->|Yes| Compositor["Compositor owns resize"]
Compositor --> Ignore["Ignore client-side position calculations"]
Ignore --> Configure["Apply compositor-driven width or height"]
Configure --> End["resizingChanged(false) and finishResize()"]
Available -->|No| Legacy["Use legacy client-side drag logic"]
Legacy --> End
File-Level Changes
Tips and commandsInteracting with Sourcery
Customizing Your ExperienceAccess your dashboard to:
Getting Help
|
There was a problem hiding this comment.
Hey - I've found 2 issues
Prompt for AI Agents
Please address the comments from this code review:
## Individual Comments
### Comment 1
<location path="panels/dock/package/main.qml" line_range="656-671" />
<code_context>
recentDeltas = []
Panel.requestClosePopup()
+
+ var edges = 0
+ if (Panel.position === Dock.Bottom) {
+ edges = Dock.ResizeEdgeTop
+ } else if (Panel.position === Dock.Top) {
+ edges = Dock.ResizeEdgeBottom
+ } else if (Panel.position === Dock.Right) {
+ edges = Dock.ResizeEdgeLeft
+ } else if (Panel.position === Dock.Left) {
+ edges = Dock.ResizeEdgeRight
+ }
+ dock.resizingReceived = false
+ var accepted = Panel.beginDockResize(edges)
</code_context>
<issue_to_address>
**issue (bug_risk):** The mouse release can arrive before the compositor's asynchronous `resizing(1)` event. In that order `resizingReceived` is still false, so `finishResize()` clears `compositorOwnsResize` and releases the grab even though the compositor resize has already been requested; the later compositor resize events then run against a completed client drag and the resize state is lost.
**Triggers:** When the user presses and releases quickly before the compositor's `resizing(1)` event reaches the client.
**Suggested fix:** Track that a compositor resize was requested independently of receipt of `resizing(1)`, and defer finishing the drag until the compositor explicitly reports the resize has ended.
</issue_to_address>
### Comment 2
<location path="panels/dock/layershellextension.h" line_range="47-48" />
<code_context>
+
+ void beginResize(struct ::wl_seat *seat, uint32_t serial, uint32_t edges, int32_t minWidth, int32_t minHeight, int32_t maxWidth, int32_t maxHeight);
+
+ // Rejects begin_resize once that surface is destroyed; callers compare it
+ // against the window's current wl_surface and re-bind when it changed.
+ struct ::wl_surface *nativeSurface() const;
+
+Q_SIGNALS:
</code_context>
<issue_to_address>
**nitpick:** The comment says the wrapper rejects `begin_resize` after the surface is destroyed, but `nativeSurface()` only returns a stored pointer and performs no validity check or rejection. The actual safety behavior depends entirely on the caller comparing the pointer, so the wrapper's documented contract is false and future callers can invoke the protocol operation with a stale surface association.
**Suggested fix:** Change the comment to describe the caller-side comparison, or make `beginResize()` validate the native surface/object lifetime before issuing the request.
```suggestion
// Returns the surface associated with this object; callers compare it
// against the window's current wl_surface and re-bind when it changed.
```
</issue_to_address>8190fb2 to
95bdff6
Compare
|
TAG Bot New tag: 2.0.54 |
11e2004 to
cf178d8
Compare
bc5a552 to
3eafd46
Compare
|
TAG Bot New tag: 2.0.55 |
|
TAG Bot New tag: 2.0.56 |
|
TAG Bot New tag: 2.0.57 |
|
TAG Bot New tag: 2.0.58 |
Add a client wrapper for the treeland layer-shell-extension protocol and wire it into the dock so the compositor owns the interactive resize (referenced protocol PR linuxdeepin/treeland-protocols#104). 加入 layer-shell-extension 协议客户端封装,合成器接管 dock 交互缩放, 替代客户端自身拖拽逻辑。 Log: dock 支持合成器接管缩放 PMS: BUG-294673 Influence: 合成器接管 dock 缩放交互,状态机改为 compositorOwnsResize 驱动, 拖拽期间屏蔽客户端手动计算,flow 与可执行尺寸更稳定。
deepin pr auto review🤖 AI 代码审查报告📊 总体评价
🔍 详细分析1. 语法逻辑 ❌评价: 一般 ❌ 不通过 潜在问题:
建议: 1.将 m_dockShellExtensionObject 非空检查移至 getLayerShellExtensionObject() 调用之前,避免创建未使用的协议对象 2. 代码质量 ✅评价: 良好 ✅ 通过 潜在问题:
建议: 1.为私有 API 使用添加版本守卫和文档说明 3. 代码性能 ✅评价: 优秀 ✅ 通过 潜在问题: 建议: 无优化建议 4. 代码安全 🔒评价: 良好 ✅ 通过
安全漏洞详情:
建议: 1.为 m_nativeSurface 添加生命周期管理或销毁监听器 💡 改进建议代码示例// 修复1: 将 m_dockShellExtensionObject 检查移至 getLayerShellExtensionObject() 之前
bool DockPanel::beginResize()
{
// ... switch position ...
if (!m_dockShellExtensionManager) {
qCWarning(dockLog) << "beginResize: layer shell extension manager is null";
return false;
}
if (!m_dockShellExtensionManager->isActive()) {
qCWarning(dockLog) << "beginResize: layer shell extension manager inactive";
return false;
}
// 先检查是否已在缩放中,避免创建未使用的协议对象
if (m_dockShellExtensionObject) {
qCWarning(dockLog) << "beginResize: resize already in progress";
return false;
}
// 然后再创建协议对象
auto *dockSurface = m_dockShellExtensionManager->getLayerShellExtensionObject(surface);
if (!dockSurface) {
qCWarning(dockLog) << "beginResize: failed to get layer shell extension object";
return false;
}
// ... continue with resize ...
}
// 修复2: 替换 Q_UNREACHABLE() 为安全返回
default:
qCWarning(dockLog) << "beginResize: unknown position" << position();
return false;
// 修复3: QML 中检查返回值
if (dock.compositorDrivenResize) {
if (!Panel.beginResize()) {
// 回退到客户端拖拽逻辑
dock.compositorDrivenResize = false
}
}本报告由 AI 代码审查工具自动生成 |
|
/forcemerge |
|
[APPROVALNOTIFIER] This PR is NOT APPROVED This pull-request has been approved by: gugullll, mhduiy The full list of commands accepted by this bot can be found here. DetailsNeeds approval from an approver in each of these files:Approvers can indicate their approval by writing |
|
This pr force merged! (status: blocked) |
Add a client wrapper for the treeland layer-shell-extension protocol and wire it into the dock so the compositor owns the interactive resize (referenced protocol PR linuxdeepin/treeland-protocols#104).
加入 layer-shell-extension 协议客户端封装,合成器接管 dock 交互缩放,
替代客户端自身拖拽逻辑。
Log: dock 支持合成器接管缩放
PMS: BUG-294673
Influence: 合成器接管 dock 缩放交互,状态机改为 compositorOwnsResize 驱动,
拖拽期间屏蔽客户端手动计算,flow 与可执行尺寸更稳定。
Summary by Sourcery
Enable the compositor to own dock resize interactions while retaining client-side resizing as a fallback on unsupported platforms.
New Features:
Enhancements:
Build: