Skip to content

Introduce WebViewTarget - #38

Merged
DV8FromTheWorld merged 13 commits into
11.18.1-discord-1from
feat/web-view-target
Oct 1, 2026
Merged

DV8FromTheWorld merged 13 commits into
11.18.1-discord-1from
feat/web-view-target

Conversation

@DV8FromTheWorld

Copy link
Copy Markdown
Member

Our original intention with this overall fork is the ability to hold onto and reparent a native view for a WebView even when the ReactNative tree wants to tear it down. We do this by using webViewKey to be able to provide a stable identifier for the native WebView and when the RNWebView goes to create a WebView due to RNWebView being rendered we instead check if our map of WebViews already has a constructed view for that webViewKey, and instead reuse it.

That system requires that, from the ReactNative side, we have to use <WebView>. That component expects to receive everything it needs to fully init the iframe, and if one already exists, it just updates it. Because of this, the lifecycle of managing the RPC bridge and construction of views has to happen at the target render location.

This PR proposes an additional component: The WebViewTarget.
The point of the WebViewTarget is that it is basically a very thin component that only says "hey, if a WebView with webViewKey already exists, move it here. It doesn't do any view construction or teardown itself. It is only a marker for where the view should go in the view hierarchy.

This means that react native callers can instead have a single place where <WebView> is rendered in the app, a pool, and the targets can say where to place the view. It means we can centralize the RPC communication and allow react to drive the lifecycle of the view again by way of simple mount/unmount of the main <WebView>

This pattern of "one place owns the view" and "others reveal targets to place it" is directly inspired our solution for pooling, managing, and placing iframes on desktop via the DOM api: Element.moveBefore. This allow us MUCH more control over lifecycle and does so from a centralized place managing that lifecycle.

Comment on lines +117 to +121
webView.measure(
MeasureSpec.makeMeasureSpec(home.measuredWidth, MeasureSpec.EXACTLY),
MeasureSpec.makeMeasureSpec(home.measuredHeight, MeasureSpec.EXACTLY)
)
webView.layout(0, 0, webView.measuredWidth, webView.measuredHeight)

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Tiny DRY opportunity, we measure then layout three times in this class with w/h parameters. Doesn't seem likely to drift but 🤷

DV8FromTheWorld and others added 12 commits September 30, 2026 16:57
Allow underscore-prefixed unused args in eslint so the platform no-op
stubs for releaseWebView and injectJavaScriptWithWebViewKey pass lint.

Point the RN 0.68 boost podspec at archives.boost.io before pod install
on iOS and macOS, since the JFrog URL it ships with no longer serves the
tarball.

Run setup-gradle before node_modules is installed so wrapper validation
only covers our own wrapper, not unknown JARs bundled in dependencies.

Pin Windows CI to Node 20.12.1, the last release before Node started
rejecting .cmd spawns without a shell, which the RNW 0.68 CLI relies on.

Generated on: M2M-AKeener

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Assign getEventDispatcher() to a typed EventDispatcher local before
dispatching. RN 0.68 declares it as a generic <T> T, so chaining the
call inferred Object and failed to compile; newer RN returns
EventDispatcher directly, so this works on both.

Change the two boolean | operators in RN 0.68's Yoga to || before pod
install on iOS and macOS. Current Xcode warns on them and Yoga builds
with -Werror.

Build iOS for the generic simulator destination instead of looking up
an iPhone 13, which the macos-15 image doesn't ship.

Pin Windows CI to windows-2022, which has Windows SDK 10.0.19041.0
that react-native-windows 0.68 targets. windows-latest only has 26100.

Generated on: M2M-AKeener

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Pass _LIBCPP_ENABLE_CXX17_REMOVED_UNARY_BINARY_FUNCTION to xcodebuild on
iOS and macOS. Boost 1.76 uses std::unary_function, which Xcode 16's
libc++ drops in C++17 mode, so RCT-Folly failed to compile. It goes on
the xcodebuild command line because react-native-test-app owns the
Podfile's post_install hook.

Tag every workaround that only exists for the RN 0.68 example app with
TODO(rn-upgrade) so they can be found and removed during the upgrade.

Generated on: M2M-AKeener

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
RNCWebViewTarget and its manager use UIKit-only view APIs (UIView,
didMoveToWindow, layoutSubviews, UIViewAutoresizing), so the macOS build
failed to compile them. Guard both implementations with
!TARGET_OS_OSX, keeping the RNCWebViewDidRegisterNotification constant
outside the guard since RNCWebView posts it on every platform.

Add WebViewTarget.macos.tsx and WebViewTarget.windows.tsx stubs that
render nothing, matching the existing no-op stubs for the other
webViewKey features, so requireNativeComponent isn't called for a
native component those platforms don't register.

Generated on: M2M-AKeener

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
releaseWebView typed the WKWebView's superview as UIView, which doesn't
exist on macOS, so RNCWebViewManager.m failed to compile there. Switch
on TARGET_OS_OSX like the manager's view method already does.

Generated on: M2M-AKeener

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Discord doesn't ship this fork on macOS, and the macOS build hasn't
compiled for a long time: several webViewKey code paths use UIKit-only
APIs with no macOS branch. Rather than maintain macOS support nobody
uses, drop the workflow so CI covers the platforms Discord ships.

Generated on: M2M-AKeener

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Keep the macOS workflow but stop it running on pushes and pull requests.
Discord doesn't ship this fork on macOS, and the macOS build doesn't
compile because several webViewKey code paths use UIKit-only APIs.
It can still be run by hand from the Actions tab.

Generated on: M2M-AKeener

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@DV8FromTheWorld
DV8FromTheWorld merged commit 323a846 into 11.18.1-discord-1 Oct 1, 2026
5 checks passed
@DV8FromTheWorld
DV8FromTheWorld deleted the feat/web-view-target branch October 1, 2026 17:24
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.

2 participants