Skip to content

Migrating to gtk4/webkit6 - #1767

Open
Ranrar wants to merge 21 commits into
tauri-apps:devfrom
Ranrar:gtk4-webkit6
Open

Migrating to gtk4/webkit6#1767
Ranrar wants to merge 21 commits into
tauri-apps:devfrom
Ranrar:gtk4-webkit6

Conversation

@Ranrar

@Ranrar Ranrar commented Jul 14, 2026

Copy link
Copy Markdown

This PR is a community contribution for #1474 — migrating the Linux backend from gtk3/webkit2gtk 4.1 to gtk4 0.11 / webkit6 0.6.

I've been developing this on my fork for a while and posted status updates on the issue thread along the way (June 23 and June 30 comments on #1474). @johncarmack1984 reviewed the branch and validated it end-to-end inside a real Tauri app; his feedback has been incorporated. I'm submitting it here in the hope it's useful as a base for the migration — I'm happy to rework any part of it, split it into smaller PRs, or adjust the approach based on your review.

What this covers

From the checklist in #1474:

  • Upgrade gtkgtk4 0.11 and handle all resulting errors
  • Upgrade webkit2gtkwebkit6 0.6 and handle all resulting errors
  • Handle changes in a backwards-compatible way where possible — the breaking changes I couldn't avoid are listed below and were posted on the Upgrade wry to gtk4-rs and webkit6 #1474 thread for early feedback before opening this PR
  • Document migration errors and pitfalls — see MIGRATION.md and LINUX.md

cargo check and cargo clippy pass cleanly on default features. All CI workflows are updated to install libwebkitgtk-6.0-dev + libgtk-4-dev.

Breaking changes (feedback especially welcome here)

These are the changes I couldn't make backwards-compatible. Full details with before/after code are in MIGRATION.md; if any of them conflict with tauri's plans, I'm glad to revisit.

  1. Opaque WebViewHandle (cross-platform)NewWindowOpener::webview and NewWindowResponse::Create { webview } no longer expose raw platform types (webkit2gtk::WebView / ICoreWebView2 / Retained<WKWebView>). Platform access goes through extension traits: WebViewHandleExtUnix::as_webkit_webview(), WebViewHandleExtWindows::as_core_webview2(), WebViewHandleExtDarwin::as_wk_webview(). A WebViewHandle::from_webkit_webview constructor lets embedders wrap externally-built views (thanks @johncarmack1984 for the constructor commit).
  2. with_related_view takes WebViewHandle (Linux) instead of a raw webkit2gtk::WebView.
  3. wry::HardwareAccelerationPolicy — the policy enum is now a wry-owned type, so consumers no longer need a direct webkit6 dependency to set it. Variants (Always / Never) are unchanged.
  4. reparentreparent_gtk (Linux) — renamed because the new cross-platform inherent method WebView::reparent(&impl HasWindowHandle) would silently shadow the trait method at existing call sites.
  5. build_gtk container bound — now accepts gtk4::Widget (GTK4 removed the Container class). new_gtk was renamed to build_gtk.
  6. linux-body is now a default feature — WebKitGTK 6.x is above the v2.40 minimum it needed, so the silent empty-body behavior on Linux is gone. This changes what default-features = true consumers compile.
  7. System packageslibwebkit2gtk-4.1-devlibwebkitgtk-6.0-dev + libgtk-4-dev (per-distro table in MIGRATION.md).
  8. GTK init / event-loop pumpinggtk::init()gtk4::init(); the manual gtk::main_iteration_do(false) pattern is replaced by a new wry::pump_platform_events() helper for non-GTK windowing integration (winit et al.).

X11 embedding note: my June 30 status update listed raw-handle X11 embedding as broken by design under GTK4. That turned out to be solvable — build() / build_as_child() with an X11 handle now reparents the realized GTK surface's XID under the target window, and WebView::reparent can move it between windows. build_gtk remains the recommended path for code that must run on both X11 and Wayland; manual set_bounds caveats are documented on the builder.

New APIs and features

  • Wayland native embedding (new wayland cargo feature) — RawWindowHandle::Wayland support for realized GTK4 windows.
  • Wayland fractional scaling — via gdk4 v4_12 soft dependency, with integer fallback below 4.12.
  • New WebViewBuilderExtUnix / WebViewExtUnix APIs: scroll/focus/keyboard/motion handlers, clipboard (incl. X11 primary selection), cursor control, drag source, monitor-change and web-process-crash handlers, isolated per-webview data directories, cookie accept policy, theme control, hardware-acceleration policy, media-stream enable. Full table in MIGRATION.md §9, docs in LINUX.md. If this expands the API surface further than you'd like for the initial migration, I can split these into follow-up PRs.
  • IME fix: the set_enable_preedit(false) workaround for the Fcitx popup-at-(0,0) bug is removed (fixed upstream in WebKitGTK 2.44) — inline CJK composition now works.

Documentation added

Document Contents
MIGRATION.md Step-by-step consumer migration guide: system packages, Cargo.toml, GTK init/event loop, builder API, WebViewHandle, import paths, X11/Wayland embedding, behavioral differences, known issues
LINUX.md Platform development notes: example matrix (X11/Wayland), per-feature documentation for every new API, troubleshooting (GLIBC_PRIVATE, DMA-BUF, JSC traps)
.changes/ 40+ change entries; the headline entry is gtk4-webkit6-linux.md (minor bump), with individual entries per API addition and behavioral change — happy to consolidate or re-bump these to fit your release plan

A full set of GTK4-native gtk_* examples was added as Wayland-capable counterparts to every winit example (gtk_simple, gtk_multiwebview, gtk_multiwindow, gtk_streaming, gtk_transparent, gtk_permission_handler, gtk_opengl, …) — run commands in LINUX.md.

How it was tested

  • Wayland: native Ubuntu 26.04 — all GTK-native examples pass
  • X11: Manjaro XFCE4 (VM; limited EGL/DRM validation — no DMA-BUF/hardware rendering, so extra X11 testing on real hardware would be valuable)
  • Independent verification by @johncarmack1984: clean Debian trixie container (system WebKitGTK 6.0, GTK 4.18, Rust 1.96) — cargo check clean; plus an end-to-end run of a real Tauri app on the full gtk4 stack (this branch + feat(linux): port to gtk4 tao#1258 + feat(gtk): port the backend to gtk4 muda#369): window, rendering, keyboard input, and menus all working
  • CI: workflows updated for the gtk4/webkit6 packages; bench workflow sets WEBKIT_DISABLE_DMABUF_RENDERER=1 for headless xvfb

Related work

Open questions

Thanks to @johncarmack1984 for the detailed reviews, integration testing, and the WebViewHandle constructor; @conradhale and @rmakestrash-jpg for the tao groundwork; and @FabianLars and @tweidinger for guidance on direction. I know this is a big diff — if it's easier to review in stages, tell me how you'd like it split and I'll do the legwork.

Ranrar and others added 13 commits July 8, 2026 00:11
Resolves the unsoundness advisory GHSA-wrw7-89jp-8q8g (glib < 0.2)
by replacing gtk 0.18 and webkit2gtk 4.1 with gtk4 0.11 and webkit6 0.6.

- Cargo.toml: replace gtk, webkit2gtk, webkit2gtk-sys, javascriptcore-rs,
  gdkx11 with gtk4, webkit6, webkit6-sys, javascriptcore6, gdk4, gdk4-x11;
  remove tao dev-dependency; bump soup3 0.5→0.9
- src/webkitgtk/mod.rs: rewrite Linux backend against webkit6 API surface
- src/webkitgtk/web_context.rs: update URI scheme registration for webkit6
- src/webkitgtk/drag_drop.rs: replace deprecated gtk3 drag signals with
  GtkDropTarget; rename Leaving→Dropped state to match new drop flow
- src/webkitgtk/synthetic_mouse_events.rs: adapt to gtk4 event model
- src/lib.rs: update public API (gtk::Container→gtk::Widget bounds,
  webkit2gtk→webkit6 types); replace tao+gtk doc examples with gtk4+winit;
  update GTK event loop pump to glib::MainContext::default().iteration()
- src/error.rs: update glib error imports to webkit6::glib
- examples: update all Linux examples from tao+gtk to winit+gtk4

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Permissions:
- Wire up ClipboardPermissionRequest and MediaKeySystemPermissionRequest in
  the webkitgtk backend; update PermissionKind docs for webkit6

CI:
- Replace libwebkit2gtk-4.1-dev with libwebkitgtk-6.0-dev + libgtk-4-dev
- Add WEBKIT_DISABLE_DMABUF_RENDERER for headless Linux benchmark runs
- Fix stale action versions: checkout v6->v4, setup-python v6->v5

Bench/Tests:
- Migrate benchmark binaries from tao to winit 0.30 + gtk4
- Fix strace float parsing for European locales (strace >= 6.x)
- Handle missing mprof gracefully; fix binary size key (libtao->libwinit)

Docs:
- Update all install commands, event loop idiom, and API refs for gtk4/webkit6
- Rewrite README code examples to use gtk4 directly

Examples:
- Rewrite gtk_multiwebview using GTK4 Application + Box layout; works on both
  X11 and Wayland via build_gtk without extra configuration
- Fix gtk_opengl for webkit6

Layout:
- Set hexpand/vexpand on webview when parented to a GtkBox
Linux additions
---------------
- Add `with_enable_media_stream(bool)` and `with_enable_encrypted_media(bool)`
  to `WebViewBuilder`. On WebKitGTK6 both features are off by default;
  previously callers had to reach through `WebViewExtUnix::webview()` after
  construction. On Windows/macOS/Android/iOS the fields are accepted and
  ignored (those platforms enable both by default).

- Enable `linux-body` in the default feature set. Without it,
  `request.body()` in custom protocol handlers was silently empty on Linux
  while Windows and macOS always provided the body. WebKitGTK 6.x satisfies
  the v2.40 version constraint unconditionally, so the guard is always met.
  Updated `with_custom_protocol` and `with_asynchronous_custom_protocol`
  rustdoc to document the feature requirement.

- Add `WebViewBuilderExtUnix::with_hardware_acceleration_policy(policy)`.
  Allows forcing software rendering (`HardwareAccelerationPolicy::Never`)
  without the `WEBKIT_DISABLE_DMABUF_RENDERER=1` environment variable
  workaround. Useful in headless/CI environments where GPU compositing is
  unavailable.

- Add `WebViewBuilderExtUnix::with_on_web_content_process_terminate_handler(fn)`.
  Wires up WebKitGTK6's `web-process-terminated` signal. Brings Linux to
  parity with the equivalent `WebViewBuilderExtDarwin` handler.

- Add `WebViewBuilderExtUnix::with_theme(Theme)`. Sets GTK4's
  `gtk-application-prefer-dark-theme` display setting, which WebKitGTK reads
  to resolve the `prefers-color-scheme` CSS media feature. Mirrors
  `WebViewBuilderExtWindows::with_theme`. `Theme::Auto` is a no-op.

- Add `WebViewBuilderExtUnix::with_data_directory(path)`. Creates an isolated
  WebKit `NetworkSession` with persistent data stored under `path` rather than
  the default system-wide WebKit directory. Linux equivalent of
  `with_profile_name` (Windows) and `with_data_store_identifier` (macOS).
  Ignored when an explicit `WebContext` is also supplied.

- Add `WebViewExtUnix::data_directory() -> Option<PathBuf>`. Returns the base
  data directory from the underlying `NetworkSession`, giving callers a path
  for manual store management — the Linux equivalent of
  `fetch_data_store_identifiers` / `remove_data_store` on macOS.

- Add `WebContext::set_cookie_accept_policy(policy)` (Linux only). Delegates
  to `CookieManager::set_accept_policy` on the `NetworkSession`.

- Improve rustdoc on `with_hotkeys_zoom`, `with_accept_first_mouse`,
  `with_background_throttling`, and `with_general_autofill_enabled` to
  explicitly document their no-op status on unsupported platforms rather than
  silently discarding the value.

Cross-platform fixes
--------------------
- Fix `WebView::set_background_color` being a no-op on macOS without the
  `transparent` feature. `setUnderPageBackgroundColor` (public, macOS 12+) now
  runs unconditionally; `drawsBackground = false` (private KVC) remains behind
  `#[cfg(feature = "transparent")]`. Previously the entire block was gated on
  the feature, so the public setter never ran.

- Fix `close_devtools()` and `is_devtools_open()` being silent no-ops on
  Windows. `open_devtools` / `close_devtools` now maintain an `AtomicBool`.
  `close_devtools` enumerates top-level windows belonging to the WebView2
  browser process via `EnumWindows` and sends `WM_CLOSE` to any visible
  `Chrome_WidgetWin_1` window (the Chromium class used by the DevTools popup).

- Expand macOS `permission_handler` to cover Geolocation and Sensors.
  `requestGeolocationPermissionForOrigin` (macOS 12+) and
  `requestDeviceOrientationAndMotionPermissionForOrigin` added to
  `WKUIDelegate`, dispatching to `PermissionKind::Geolocation` and
  `PermissionKind::Sensors`. Notifications, ClipboardRead, and PointerLock
  have no `WKUIDelegate` hook and remain unroutable on macOS.

- Add `WebView::reparent<W: HasWindowHandle>(&self, window: &W) -> Result<()>`
  to the base `WebView` type. Replaces incompatible platform-specific
  signatures (`reparent(isize)` on Windows, `reparent(*mut NSWindow)` on
  macOS, `reparent(&W: IsA<Widget>)` on Linux). Implemented in all three
  backends; the Linux path uses `XReparentWindow` and updates the stored
  `x11_window` XID. `x11_window` is now a `Cell<c_ulong>` to allow mutation
  through a shared reference during reparent.

Examples
--------
- Add `examples/gtk_linux_features.rs`. Exercises the five new Linux-only
  builder APIs in a single GTK4 window: hardware acceleration policy (software
  rendering via `HardwareAccelerationPolicy::Never`), theme toggling (T key),
  web-process crash handler with auto-reload (C key), and isolated data
  directory via `with_data_directory` / `data_directory()` accessor.

- Update `examples/gtk_cookies.rs`. Demonstrates the new
  `WebContext::set_cookie_accept_policy` API: a `CookieAcceptPolicy::Never`
  context blocks HTTP `Set-Cookie` headers (httpbin's redirect cookie is
  suppressed) while programmatic `set_cookie()` calls still work.

- Update `examples/gtk_permission_handler.rs`. Removes the post-build
  workaround that reached into the raw webkit6 settings object to enable media
  stream and encrypted media APIs. Both are now set via the builder methods
  `with_enable_media_stream(true)` and `with_enable_encrypted_media(true)`.

- Update `examples/reparent.rs`. Qualifies the `reparent` call with
  `WebViewExtUnix::reparent(...)` to resolve the method ambiguity introduced
  by the new unified `WebView::reparent` on the base type.

Testing
-------
All changes were developed and tested on Linux (GTK4 / WebKitGTK 6.x).
The Windows and macOS cross-platform fixes (`set_background_color`,
`close_devtools`, macOS permission handler, and unified `reparent`) could
not be verified locally — Windows and macOS testing environments are not
available.
Add `--features wayland` to embed WebViews in GTK4-owned Wayland windows
via `RawWindowHandle::Wayland`. The backend locates the parent `GtkWindow`
by comparing `wl_surface` pointers across GTK toplevels, attaches a `GtkFixed`
(child mode) or `GtkBox` (full-window), and scales coordinates using
`scale_factor_wayland()` from the GDK surface.

Bug fixes bundled in this commit:
- Replace busy-spin GLib loop in cookie methods with `iteration(true)`
  to eliminate full-CPU spin while awaiting async cookie callbacks
- Remove direct `widget.size_allocate()` calls (GTK3-era API invalid in
  GTK4); use `GtkFixed::move_()` + `set_size_request()` instead
- Replace string-based container type detection (`type_().name()`) with
  `dynamic_cast_ref::<gtk::Fixed>()`/`<gtk::Box>()` to correctly match
  subclasses
- Fix `reparent_window()` for child-mode Wayland WebViews — now
  finds-or-creates a `GtkFixed` instead of always creating a `GtkBox`
- Return `Error::WaylandNotSupported` (with actionable hint) when a
  Wayland handle is passed without the `wayland` feature enabled
- Drop cleanup now clears the host `GtkWindow`'s child widget for reuse

Add `gdk4-wayland` optional dep and `wayland` feature to `Cargo.toml`.
Update `LINUX.md` and module docs to document the new embedding path,
HiDPI/fractional-scale notes, and limitations.
New APIs:
- WebViewHandle opaque type (all platforms); WebViewHandleExtUnix/Windows/Darwin traits
- HardwareAccelerationPolicy Wry-owned enum; drops webkit6 dep from callers
- Focus, keyboard, motion, pointer enter/leave, scroll, drag-source,
  monitors-changed handlers via GTK4 event controllers
- Clipboard read/write, primary clipboard read/write, set_cursor_from_name

Bug fixes:
- Cookie methods use block_on + _future() instead of mpsc + spin-loop
- DragDropEvent::Enter fires at hover on Wayland (DropTarget preload)
- New-window fallback to plain gtk::Window avoids panic
- Container dispatch via dynamic_cast_ref replaces type name strings
- Remove set_enable_preedit(false) workaround (fixed in WebKitGTK 2.44)
- Unified fractional scale helper (X11 + Wayland via gdk4/v4_12)
- AccessibleRole::None on GtkBox wrappers for AT-SPI passthrough
- size_allocate removed; GtkFixed::move_ + set_size_request used instead
- WaylandWindowNotFound error variant with actionable diagnostic message

BREAKING CHANGE: NewWindowOpener::webview and NewWindowResponse::Create { webview }
renamed to handle: WebViewHandle; with_related_view accepts WebViewHandle.
Increase gtk_simple default size to 1280×800. Set homogeneous on all
Box containers in gtk_multiwebview so webviews share space equally in
both axes, preventing one view from expanding on right-click.
- Rename `WebViewExtUnix::reparent` to `WebViewExtUnix::reparent_gtk` to avoid method collision with the inherent `WebView::reparent`.
- Introduce `WebViewHandle::from_webkit_webview(webkit6::WebView) -> WebViewHandle` to allow wrapping externally created webviews.
- Update documentation and examples to reflect these changes.
Pulls in 2 upstream doc-only commits (drag-drop handler platform notes).
Copilot AI review requested due to automatic review settings July 14, 2026 07:58
@Ranrar
Ranrar requested review from a team as code owners July 14, 2026 07:58
@socket-security

socket-security Bot commented Jul 14, 2026

Copy link
Copy Markdown

Review the following changes in direct dependencies. Learn more about Socket for GitHub.

Diff Package Supply Chain
Security
Vulnerability Quality Maintenance License
Addedwebkit6-sys@​0.6.08110093100100
Updatedserde@​1.0.218 ⏵ 1.0.2288110093100100
Addedgdk4@​0.11.210010093100100
Addedgdk4-wayland@​0.11.010010093100100
Addedgdk4-x11@​0.11.010010093100100
Addedgtk4@​0.11.310010093100100
Addedjavascriptcore6@​0.6.010010093100100
Addedwebkit6@​0.6.110010093100100
Updatedsoup3@​0.5.0 ⏵ 0.9.099 -1100100 +8100100

View full report

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR migrates wry’s Linux backend from GTK3/WebKit2GTK (4.1) to GTK4/WebKitGTK (webkit6), updates supporting APIs/docs/CI, and adds new examples and benchmark adjustments to validate the new stack across X11 and Wayland.

Changes:

  • Upgrade Linux dependencies and backend code to gtk4 + webkit6, including related platform glue (events, drag/drop, synthetic input, web context/session).
  • Introduce/extend cross-platform surface-level APIs (e.g., opaque WebViewHandle, unified reparent helpers, permission routing updates).
  • Update examples, benchmarks, CI workflows, and changelog entries to match the new GTK4/WebKitGTK6 requirements and capabilities (incl. Wayland feature path).

Reviewed changes

Copilot reviewed 94 out of 96 changed files in this pull request and generated 4 comments.

Show a summary per file
File Description
src/wkwebview/mod.rs macOS WKWebView background color behavior; add reparent_window helper
src/wkwebview/class/wry_web_view_ui_delegate.rs Add macOS geolocation/sensors permission callbacks; adapt new-window plumbing to WebViewHandle
src/webview2/mod.rs Track devtools state on Windows; implement best-effort devtools close; add reparent_window helper
src/webkitgtk/web_context.rs Migrate context/session logic to webkit6 NetworkSession; update custom protocol plumbing; add cookie policy setter
src/webkitgtk/synthetic_mouse_events.rs Port back/forward synthetic mouse events to GTK4 controllers/gesture APIs
src/webkitgtk/drag_drop.rs Port drag/drop to GTK4 controllers; improve Wayland enter-path availability via preload
src/web_context.rs Add Linux-only cookie accept policy API
src/permissions.rs Update permission support documentation (macOS + webkit6 Linux additions)
src/error.rs Switch GTK error types to webkit6 glib; add Wayland-specific error variants/messages
README.md Update docs/examples for GTK4/WebKitGTK6, Wayland/X11 features, and event pumping helper
examples/winit.rs Replace GTK3 event pumping with GTK4 main context iteration
examples/window_border.rs Port example from tao to winit; update Linux event pumping; restructure app lifecycle
examples/wgpu.rs Replace GTK3 event pumping with GTK4 main context iteration
examples/transparent.rs Port example from tao to winit; add resize-driven bounds updates; GTK4 event pumping
examples/streaming/index.html Improve streaming demo UI and add remote HTTPS test mode
examples/streaming.rs Port from tao to winit; add resize handling; improve streaming MIME handling
examples/simple.rs Port from tao to winit; add resize handling; update drag-drop logging for new event ordering
examples/reparent.rs Restructure to separate non-Linux winit vs Linux GTK4 paths; update reparent calls
examples/permission_handler.rs Port from tao to winit; add resize handling; GTK4 event pumping
examples/multiwindow.rs Port from tao to winit; add resize handling; GTK4 event pumping
examples/multiwebview.rs Replace GTK3 init/Wayland panic with GTK4 init; update X11 hook gating
examples/custom_titlebar.rs Port from tao to winit; update cursor API usage; add resize handling + GTK4 pumping
examples/custom_protocol.rs Port from tao to winit; add resize handling; GTK4 event pumping
examples/cookies.rs Port from tao to winit; add resize handling; GTK4 event pumping
examples/async_custom_protocol.rs Port from tao to winit; add resize handling; GTK4 event pumping
examples/gtk_window_border.rs New GTK4-native (Wayland-capable) window border example
examples/gtk_transparent.rs New GTK4-native transparent example
examples/gtk_streaming.rs New GTK4-native streaming custom-protocol example
examples/gtk_simple.rs New GTK4-native minimal example
examples/gtk_opengl.rs Rework OpenGL example into GTK4-native implementation + non-Linux stub
examples/gtk_multiwindow.rs New GTK4-native multiwindow example
examples/gtk_linux_features.rs New GTK4-native demo covering new Linux-specific builder/runtime APIs
examples/gtk_custom_titlebar.rs New GTK4-native custom titlebar example
examples/gtk_custom_protocol.rs New GTK4-native custom protocol example
examples/gtk_cookies.rs New GTK4-native cookie management example
examples/gtk_async_custom_protocol.rs New GTK4-native async custom protocol example
Cargo.toml Switch Linux deps to gtk4/webkit6/js core 6; add wayland feature; enable linux-body by default; drop tao dev-dep
bench/tests/src/hello_world.rs Port bench harness from tao to winit; add GTK4 path for Linux/BSD
bench/tests/src/custom_protocol.rs Port bench harness from tao to winit; add GTK4 path for Linux/BSD
bench/tests/src/cpu_intensive.rs Port bench harness from tao to winit; add GTK4 path for Linux/BSD
bench/tests/Cargo.toml Replace tao with winit; add gtk4 dep on Linux/BSD
bench/src/utils.rs Make strace parsing tolerant of locale decimal separators
bench/src/run_benchmark.rs Make benchmarks more robust (missing tools); rename size metrics to winit; adjust paths and time format parsing
.gitignore Ignore bench workspace lockfiles
.github/workflows/clippy-fmt.yml Install libwebkitgtk-6.0-dev + libgtk-4-dev on Ubuntu
.github/workflows/build.yml Install libwebkitgtk-6.0-dev + libgtk-4-dev (+ at-spi2-core) on Ubuntu; update labels
.github/workflows/bench.yml Update checkout/python actions; install GTK4/WebKitGTK6; set DMA-BUF disable env for headless runs
.changes/windows-devtools-close-unimplemented.md Changelog: implement Windows devtools close/state
.changes/unified-reparent.md Changelog: add unified reparent API
.changes/streaming-mime-improvements.md Changelog: streaming example improvements
.changes/permission-handler.md Changelog: permission API wording updates for webkit6/macOS
.changes/macos-set-background-color-no-feature.md Changelog: macOS background color fix without transparent feature
.changes/macos-permission-handler-geolocation-sensors.md Changelog: macOS geolocation + sensors permission support
.changes/linux-webview-handle-api.md Changelog: Linux WebViewHandle::from_webkit_webview
.changes/linux-web-process-terminated-handler.md Changelog: Linux web-process-terminated builder hook
.changes/linux-wayland-native-embed.md Changelog: native Wayland embedding feature
.changes/linux-wayland-fractional-scale.md Changelog: Wayland scaling helper
.changes/linux-wayland-doc-update.md Changelog: Wayland documentation updates
.changes/linux-wayland-bug-fixes.md Changelog: Wayland embedding bug fixes
.changes/linux-typed-container-dispatch.md Changelog: typed container downcasts
.changes/linux-theme-control.md Changelog: theme control on Linux
.changes/linux-silent-noop-docs.md Changelog: clarify no-op builder methods
.changes/linux-scroll-handler.md Changelog: scroll handler on Linux
.changes/linux-scale-factor-unified.md Changelog: unified scale factor helper
.changes/linux-reparent-gtk.md Changelog: rename Unix reparent trait method
.changes/linux-remove-size-allocate.md Changelog: remove internal GTK layout calls
.changes/linux-primary-clipboard.md Changelog: X11 primary selection APIs
.changes/linux-opaque-webview-handle.md Changelog: introduce opaque WebViewHandle
.changes/linux-newwindow-plain-window.md Changelog: fix Linux NewWindowResponse Allow on plain Window
.changes/linux-motion-handler.md Changelog: pointer motion handlers on Linux
.changes/linux-monitors-changed-handler.md Changelog: monitor change handler
.changes/linux-media-stream-builder.md Changelog: media stream/encrypted media builder flags
.changes/linux-keyboard-handler.md Changelog: keyboard handler
.changes/linux-ime-preedit-gtk4.md Changelog: remove IME workaround on gtk4/webkit6
.changes/linux-hardware-acceleration-wry-type.md Changelog: wry-owned hardware accel policy
.changes/linux-hardware-acceleration-policy.md Changelog: hardware acceleration policy builder
.changes/linux-focus-handler.md Changelog: focus handler
.changes/linux-drag-source.md Changelog: drag source handler
.changes/linux-dnd-enter-data-coverage.md Changelog: Wayland drag enter paths fix
.changes/linux-data-directory.md Changelog: per-webview data directory
.changes/linux-data-directory-accessor.md Changelog: data directory accessor
.changes/linux-cursor-from-name.md Changelog: cursor override API
.changes/linux-cookie-blocking-iteration.md Changelog: cookie methods future/block_on refactor
.changes/linux-cookie-accept-policy.md Changelog: cookie accept policy API
.changes/linux-clipboard-write.md Changelog: clipboard write API
.changes/linux-clipboard-read.md Changelog: clipboard read API
.changes/linux-body-default.md Changelog: enable linux-body by default
.changes/linux-accessible-role-passthrough.md Changelog: accessibility role passthrough tweaks
.changes/gtk4-webkit6-linux.md Changelog: headline GTK4/WebKitGTK6 migration entry

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment thread src/wkwebview/mod.rs
Comment on lines +1305 to +1323
pub(crate) fn reparent_window(&self, window: &impl HasWindowHandle) -> crate::Result<()> {
let ns_view = match window.window_handle()?.as_raw() {
RawWindowHandle::AppKit(w) => w.ns_view.as_ptr(),
#[cfg(target_os = "ios")]
RawWindowHandle::UiKit(w) => w.ui_view.as_ptr(),
_ => return Err(crate::Error::UnsupportedWindowHandle),
};

unsafe {
let ns_view: &objc2_app_kit::NSView = &*(ns_view as *const objc2_app_kit::NSView);
if let Some(ns_window) = ns_view.window() {
self.reparent(Retained::as_ptr(&ns_window) as *mut NSWindow)
} else {
// view not yet attached to a window — add directly as subview
ns_view.addSubview(&self.webview);
Ok(())
}
}
}
Comment thread bench/src/utils.rs
Comment on lines +117 to +121
// strace >= 6.x uses the system locale for decimal/thousands separators
// (e.g. "0,40" instead of "0.40" on many European locales). Normalise to
// dot-decimal so Rust's float parser can handle both formats.
let normalise_float = |s: &str| s.replace(',', ".");
let parse_f64 = |s: &str| str::parse::<f64>(&normalise_float(s)).unwrap();
Comment thread examples/winit.rs
gtk::main_iteration_do(false);
}
}
while gtk4::glib::MainContext::default().iteration(false) {}
Comment thread examples/window_border.rs
Comment on lines 15 to 17
enum UserEvent {
TogglShadows,
}
@johncarmack1984

Copy link
Copy Markdown

Confirming the verification I'm tagged in above. In a clean Debian trixie container (system WebKitGTK 6.0, GTK 4.18, Rust 1.96), cargo check passes on default features. End to end, a real Tauri app on this branch plus tao#1258 and muda#369 runs with working windows, rendering, keyboard input, and native menus. Happy to re-run both after the rebase on dev, and again as the branch evolves.

@Ranrar

Ranrar commented Jul 14, 2026

Copy link
Copy Markdown
Author

@johncarmack1984 When you have the time, can you review the MIGRATION.md and add comments and and thoughts.

@johncarmack1984

Copy link
Copy Markdown

Glad to. Calibration first: I'm an outside contributor here, same as you. Nothing below carries maintainer weight, and the review that moves this PR is the wry team's. What I can offer is that I've built against this exact rev, so I read the doc against the code and against what I actually hit.

Overall it's a good guide. The section order matches the order a real migration hits things, and the "why" notes are the part most migration docs skip. The reparent section explaining the inherent-method shadowing is exactly the kind of thing that saves someone a silent wrong call. Same for the known-issues entries naming what isn't a wry bug.

Three concrete items:

  1. Section 8, the Wayland example won't compile: WebViewBuilder::new_as_child(&parent) doesn't exist on this branch or on dev. It was removed back in wry 0.46. Current form is WebViewBuilder::new().with_bounds(..).with_url(..).build_as_child(&parent), which is what I ran against this rev.

  2. Section 11 could use one more env var next to the DMABUF one: WEBKIT_DISABLE_SANDBOX_THIS_IS_DANGEROUS=1. In unprivileged containers, which is most CI, WebKit's bwrap sandbox aborts before you get a window. First wall I hit; one-line fix.

  3. Section 10: LINUX.md says the IME fix assumes webkitgtk-6.0 >= 2.44, but MIGRATION.md doesn't carry that. The compile gate is v2_42, so a 2.42 or 2.43 runtime gets the old preedit bug back with no workaround left in the code. Worth one line stating the runtime floor.

Minor: section 3 says when to call pump_platform_events(). The inverse deserves a sentence too: a GTK-based host loop shouldn't also call it, that loop is already draining.

Everything else I checked holds: the dep and feature tables, the webkit6::gtk re-export paths in the builder bounds, the WebViewHandle accessors matching the Windows and macOS naming, the preedit workaround actually being gone. Happy to re-read after the rebase, along with the re-verify I already owe you.

@Ranrar

Ranrar commented Jul 16, 2026

Copy link
Copy Markdown
Author

Thanks for the review, @johncarmack1984

Fixed:

  • §3: noted that a GTK-owned host loop shouldn't also call pump_platform_events(), since it's already draining the same GMainContext.
  • §8 Wayland example: WebViewBuilder::new_as_child(&parent)WebViewBuilder::new().with_bounds(..).with_url(..).build_as_child(&parent) (same error existed in LINUX.md's Wayland section too, fixed there as well).
  • §10: noted the runtime floor — the feature gate is v2_42 at compile time, but the preedit fix needs webkitgtk-6.0 ≥ 2.44 at runtime.
  • §11: added WEBKIT_DISABLE_SANDBOX_THIS_IS_DANGEROUS=1 as a known issue for bwrap sandbox failures in unprivileged CI/containers.

Also found and fixed an unrelated IPC panic while in there: the script-message callback in attach_ipc_handler unwrapped webview.uri() and the resulting Request build, both of which could panic inside a GObject trampoline that can't unwind (no URI loaded yet, or a file:/// base with empty authority that http::Uri rejects) — aborting the whole process instead of just the callback. It now falls back to about:blank.

@johncarmack1984

Copy link
Copy Markdown

Re-ran both after the merge with dev, at 0411857. Same trixie setup (GTK 4.18.6, WebKitGTK 2.52.3, Rust 1.97): cargo check passes on default features. The same Tauri app on this branch plus tao#1258 and muda#369 still runs end to end: windows, rendering, keyboard input, native menus. Consumer note: my tauri fork needed four lines for the reparent_gtk and handle renames, and MIGRATION.md already documents both. The doc holds up in practice. gtk_simple also renders on both X11 and headless Wayland at this rev.

@Ranrar

Ranrar commented Jul 23, 2026

Copy link
Copy Markdown
Author

Hi! Just a small follow-up since it's been a little while.

I know it's the middle of summer, and this PR touches almost 100 files, so I completely understand that it takes time to review.

I've kept this PR up to date by merging the latest upstream changes twice, so it should still be based on the current dev.

Since opening this PR, I've also started porting my own application (Marco) to use this GTK4/WebKit6 branch of Wry on Linux instead of using webkit6 directly. The goal is to use Wry as the webview abstraction on both Linux and Windows, rather than maintaining separate webview implementations.

The Marco port is still a work in progress, but the Wry implementation is already working well in practice and has been tested in a real application.

Whenever someone has time to review, I'd really appreciate any feedback — whether it's about the overall direction or specific implementation details. If there are changes you'd like to see before this can move forward, I'm happy to make them.

Brings in wry 0.56.0 and the breaking removal of the `protocol`,
`transparent`, and `fullscreen` feature flags.

Conflict resolutions:
- Cargo.toml: adopt upstream feature removals; keep this branch's
  `linux-body` (no webkit2gtk/v2_40 gate) and its inclusion in `default`.
  `tao` dev-dependency stays dropped since examples use winit/gtk4.
- examples: apply upstream's `protocol` de-gating to this branch's
  winit/gtk4 rewrites, including the gtk_* examples upstream doesn't have.
- src/lib.rs, README.md: keep gtk4/webkit6 docs; add upstream's
  `mac-proxy` feature entry and document the branch's `wayland` feature.
- src/wkwebview/mod.rs: un-gate the `drawsBackground` call in
  `set_background_color`, matching upstream now that `transparent` is gone.
- .changes/permission-handler.md: deleted, consumed by upstream's 0.56.0 release.
Ranrar and others added 2 commits August 7, 2026 08:14
Brings in 4 upstream commits:
- fix(android): override getDefaultVideoPoster to suppress placeholder (tauri-apps#1804)
- fix(windows): ignore `MoveFocus` error on creation (tauri-apps#1799)
- docs(android): why `WEBVIEW_ATTRIBUTES` exists (tauri-apps#1801)
- fix(bench): rlib location on new nightly (tauri-apps#1800)

Conflict in bench/src/run_benchmark.rs: upstream reworked `rlib_size` to
take a bare library name and return `Result`, while this branch had
switched the second measured rlib from tao to winit (this branch uses
winit instead of tao for examples/dev-deps). Resolved by keeping
upstream's new signature and calling it with "winit".
Pre-existing rustfmt violations in code added by this branch. CI runs
`cargo fmt --all -- --check` on stable, so these would block the PR.
Mechanical reformat only, no behavior change.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
# Conflicts:
#	Cargo.lock
#	src/webkitgtk/mod.rs
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants