Throttle PRK.Client swapchain rebuilds during window resizing
Outcome Make drag resizing responsive on Wayland by coalescing resize notifications and bounding expensive Vulkan presentation rebuilds, while always converging to the final drawable size. Evidence and scope PRK.Client/PRK.GraphicsEngine/Window.cs forwards both Resize and FramebufferResize to Engine.OnResize. RendererVulkan.Resize sets _swapchainRefreshPending but immediately calls RefreshPresentation, rebuilding the swapchain, render/reflection targets and synchronization resources after GPU idle. Acquire/present out-of-date and suboptimal paths also rebuild directly. Extend the existing pending-refresh/frame-loop and GPU maintenance/lifetime patterns rather than adding parallel timers or platform-specific resize handling. Preserve Engine.Display.cs synchronous explicit Display Apply/refusal/rollback behavior, including VSync changes at unchanged dimensions. Proposed behavior Coalesce passive notifications to the latest logical/framebuffer state. Use a monotonic, testable throttle, 500 ms (at most two resize-driven rebuilds per second; reduced after user reported continued lag at four per second), with final dimensions applied within one interval plus the next eligible frame once dragging stops. Do not use trailing-only debounce that freezes all resizing until dragging ends. Skip redundant extent-only refreshes, but retain explicit presentation-policy refreshes. Route Vulkan resize invalidations through the same scheduling policy. Continue presenting with the old swapchain only while valid; if out of date, skip drawing until eligible without blocking updates/network/input or introducing busy spinning. Update dependent UI sizing together with a successful refresh and keep camera/picking coordinate mappings correct while extents differ. Acceptance criteria - High-frequency and duplicate window/framebuffer notifications do not cause per-event GPU idle/rebuilds; sustained resize-driven rebuilds are capped at two per second, including acquire/present invalidations. - Final nonzero framebuffer extent is applied within the bounded settling delay; logical-only and framebuffer-only changes are handled correctly. - Minimize/zero extent, restore, DPI/monitor changes, shutdown and repeated invalidations remain safe; no stale picking/UI extent or synchronization/resource-lifetime regressions. - Explicit Display Apply and rollback remain synchronous and correctly surface failures; same-size VSync changes still refresh presentation. - Client builds and focused scheduling/display/lifetime regression tests pass. Reuse ManualTimeProvider and existing graphics/Vulkan test suites. User verifies native Wayland drag behavior and rebuild counts; no assistant GUI launches or visual verification without explicit permission. Clearly report any unverified platform behavior. Implementation and validation Committed as d5d3e5c06 (fix: Prevent client window resize stalls) on fix/throttle-client-resizing and pushed with upstream; working tree clean. Passive callbacks retain logical size without GPU work; the frame loop samples the latest framebuffer. PresentationRefreshSchedule uses monotonic time and a 500 ms interval, consolidating framebuffer changes and acquire/present invalidations. Out-of-date drawing pauses with a temporary 60 fps loop cap (lower configured caps preserved). Camera projection uses the active swapchain aspect; UI resources refresh through the shared path. Explicit Resize remains immediate for Display Apply/rollback and same-size VSync refreshes, with zero-extent deferral preserved. Client build passes with zero warnings/errors. Latest graphics/GUI/input/lifetime validation: 313 passed, 13 opt-in native-window/asset-preview tests skipped. The two-per-second flood and 500 ms boundary expectations failed against the previous interval and passed after lowering the cap. Refresh-event regressions reproduced 501 frame polls from one event batch under the default unguarded loop and pass with one frame under the guard. Deferred GUI-layout/painting and transformed pointer/picker click regressions failed under live viewport resizing and now pass. Client build again passes with zero warnings/errors. Allocator tests: 71 passed. Headless software-Vulkan validation: 11 passed after installing Vulkan loader/drivers/validation layers in a disposable container only. git diff --check passes. Tests cover resize floods, final-size convergence, duplicate extents, repeated invalidations, monotonic timing, minimize/restore, explicit refresh/rollback scheduling, unavailable-surface pacing and mismatched GUI/picker extents. Additional resize fixes: source inspection of Silk.NET 2.23.0 GlfwWindow and its default Run extension confirms that native refresh callbacks invoke the full frame delegate from inside DoEvents. Window.Open now uses WindowFrameLoop with a reentrancy guard: poll the batch, update/render/pace once, preserving closing checks and guard recovery on failures. UIRenderer.PrepareFrame previously relaid out against every live logical size, changing render scale and forcing GuiSurface full repaint/upload even with a throttled swapchain. GUI layout/render scale now stay committed to presentation dimensions; SetInputWindowSize maps live pointer coordinates to that displayed layout without paint/layout invalidation, and successful presentation refresh commits both dimensions. Source/repro evidence confirms these extra-work paths, but their contribution to the user's actual Wayland stall remains unmeasured. User acceptance: the user reports testing completed, all platforms behave correctly, and no slowdown occurs during resizing. Combined with deterministic rebuild-frequency/final-size, explicit refresh/rollback scheduling, close/error handling and resource-lifetime regressions, this satisfies the outstanding acceptance outcomes. Assistant native-window automation and asset previews remain skipped; no assistant GUI or screenshot verification was launched. Constraints Native GUI/visual verification remains user-owned. No major rendering architecture refactor or new user-facing setting was introduced. Pull request PR #2634: https://git.project-rk.com/prk/engines/pulls/2634 Head fix/throttle-client-resizing → base develop. Ready for review; includes only this session's resize work.
Checklist
5 of 5 complete- Verify a deterministic resize policy coalesces event floods, bounds rebuild frequency and applies final dimensions without starvation.
- Integrate deferred passive resizing and acquire/present invalidations into one frame-loop refresh path; verify zero-extent, duplicate events and coordinate consistency.
- Preserve and regression-test synchronous Display Apply/rollback, same-size VSync refreshes and renderer shutdown/resource safety.
- Pass client build and focused graphics/Vulkan tests; obtain user Wayland drag-resize verification with measured rebuild frequency and final-size convergence.
- Verify refresh-event floods cannot reenter updates/rendering/pacing, and deferred logical resizing does not relayout/repaint unchanged GUI while live pointer/picker mappings remain correct.
- Area
- Project Rubi-Ka
- Project
- engines
- Kind
- Bug
- Task ID
tsk_snq32497yu- Updated