Skip to content

Feature/ctrl + D分离窗口显示窗口控件 + 解决linux环境下无法最大化的问题 - #662

Open
zx1095971114 wants to merge 2 commits into
ZToolsCenter:mainfrom
zx1095971114:feature/linux-toolbar
Open

Feature/ctrl + D分离窗口显示窗口控件 + 解决linux环境下无法最大化的问题#662
zx1095971114 wants to merge 2 commits into
ZToolsCenter:mainfrom
zx1095971114:feature/linux-toolbar

Conversation

@zx1095971114

Copy link
Copy Markdown

变更内容

本 PR 修复 ZTools 分离窗口在 Linux 平台 的两个问题,涉及 2 个 commit:

  1. e79a3e4 Linux 分离窗口显示最小化/最大化/关闭按钮

    • DetachedTitlebar.vueplatform 类型扩展为 'darwin' | 'win32' | 'linux'
    • 窗口控制按钮的 v-if 条件同步匹配 linux,让 Linux 用户也能在独立窗口右上角看到最小化、最大化、关闭按钮
    • 背景:分离窗口以 frame: false 创建,Linux WM 不会自动绘制窗口控件,必须由 HTML 自绘
  2. 25d43cc Linux 分离窗口 maximize 时同步 WebContentsView bounds(保守修复)

    • detachedWindowManager.ts 新增 maximize / unmaximize 监听器,触发 syncPluginViewBoundsOnly
    • syncAfterStateChange 在三个时间点同步:立即、setImmediate、100ms,覆盖 WM 异步处理状态切换的不同延迟
    • resize 监听器增加 win.isMaximized() / win.isFullScreen() 守卫:最大化/全屏触发的 resize 不写数据库,避免把屏幕工作区尺寸误存为下次 Ctrl+D 的"默认尺寸"
    • 背景:Linux WM 走 _NET_WM_STATE_MAXIMIZED_* 时常不发 ConfigureNotify,resize 事件可能不触发,导致 pluginView 保持旧 bounds、看起来"窗口最大化但内容没放大"

文件改动

文件 变更
src/main/core/detachedWindowManager.ts +30 / -0
src/renderer/src/components/detached/DetachedTitlebar.vue +3 / -3

动机

Linux 平台上分离窗口体验存在两个缺陷:

场景 修复前 修复后
用户在 Linux 上分离插件窗口 标题栏没有最小化/最大化/关闭按钮,只能从 Dock/任务栏操作 右上角显示完整控件,符合 Linux 用户预期
用户在 Linux 上最大化分离窗口 窗口框架最大化,但 pluginView 保持原大小,内容没跟上 pluginView 与窗口同步最大化

截图

改动前linux的无窗口控件
img

改动前linux调出窗口控件后点击最大化按钮
img_1

改动后linux的窗口控件可见
img_2

改动后linux窗口最大化时内容等比例放大
img_3

手动验证(Linux GNOME Wayland / KDE X11)

  1. 窗口控件可见性

    • 打开任意插件 → 按 Ctrl+D 分离窗口
    • 预期:右上角出现最小化 / 最大化 / 关闭按钮,与 Windows 客户端一致
  2. 最大化同步

    • 分离窗口 → 点击最大化按钮(或双击标题栏)
    • 预期:pluginView 内容随窗口一起放大,无"窗口大、内容小"的撕裂感
    • 取消最大化:预期:pluginView 缩回原尺寸
  3. 持久化不被污染

    • 分离窗口 → 调整到一个非最大化的尺寸(记住这个尺寸)→ 关闭窗口
    • 再次分离同一插件 → 恢复成上次的非最大化尺寸(不是屏幕工作区尺寸)
  4. 不影响其他平台

    • macOS:分离窗口已有原生交通灯按钮,本变更不影响
    • Windows:分离窗口已有 HTML 自绘按钮,本变更不影响(仅扩展 v-if 条件)

相关 Issue

影响范围

  • Linux:完整支持(控件可见 + 最大化同步)
  • macOS / Windows:不受影响(v-if 仅扩展,maximize 监听器为 no-op,因为 Windows 上 maximize 事件正常触发 resize)
  • 其他平台:不受影响

检查清单

  • pnpm typecheck:node 通过
  • pnpm typecheck:web 通过
  • pnpm lint(改动文件)通过 — detachedWindowManager.ts / DetachedTitlebar.vue 均为 0 错误
  • 提交信息符合 conventional commits 格式(fix: + 详细 body)
  • any 使用
  • 命名规范符合(camelCase)
  • Linux 上手动验证通过

zx1095971114 and others added 2 commits August 29, 2026 14:21
分离窗口在主进程中以 frame:false 创建,因此 Linux 上窗口管理器不会自动绘制窗口控件。\n扩展 DetachedTitlebar.vue 的 platform 类型为 'darwin' | 'win32' | 'linux',\n并将窗口控制按钮的 v-if 条件改为同时匹配 win32 和 linux,让 Linux 用户\n也能在独立窗口右上角看到最小化、最大化、关闭按钮。

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
回到只动 resize 监听器旁加 maximize/unmaximize 兜底,不再触碰 IPC
handler、BrowserWindow 几何和持久化逻辑。

修复:
- win.on('maximize'/'unmaximize', ...) 时调用 syncPluginViewBoundsOnly,
  通过 syncPluginViewBoundsOnly → pluginView.setBounds 把 pluginView
  位置拉到新窗口尺寸。Linux 上 WM 走 _NET_WM_STATE_MAXIMIZED_* 时常
  不发 ConfigureNotify,resize 事件可能不触发,导致 pluginView 保持
  旧 bounds、看起来“窗口最大化但内容没放大”。这个兜底就是为了补上
  这种情况。
- syncAfterStateChange 在三个时间点同步:立即、setImmediate、100ms,
  覆盖 WM 异步处理状态切换的不同延迟。
- resize 监听器增加 win.isMaximized()/isFullScreen() 守卫:最大化/
  全屏触发的 resize 不写数据库,避免把屏幕工作区尺寸误存为下次
  Ctrl+D 的“默认尺寸”。

注意:syncPluginViewBoundsOnly 内部不调用 schedulePersistWindowSize,
也不修改 BrowserWindow 几何。持久化逻辑完全由 resize 事件处理,
最大化/全屏状态下被守卫拦截。
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant