From 334a2c5606e970437f966ed062807ff0f501e030 Mon Sep 17 00:00:00 2001 From: William Candillon Date: Mon, 2 Feb 2026 08:28:46 +0100 Subject: [PATCH 01/10] :wrench: --- apps/example/ios/Podfile.lock | 112 ++++----- apps/example/src/Examples/WebGPU/List.tsx | 64 +++++ apps/example/src/Examples/WebGPU/Routes.ts | 5 + apps/example/src/Examples/WebGPU/Triangle.tsx | 181 ++++++++++++++ .../WebGPU/{WebGPU.tsx => Wireframes.tsx} | 2 +- apps/example/src/Examples/WebGPU/index.ts | 1 - apps/example/src/Examples/WebGPU/index.tsx | 39 +++ externals/skia | 2 +- packages/skia/android/CMakeLists.txt | 4 + .../skia/android/cpp/jni/JniWebGPUView.cpp | 67 +++++ .../cpp/rnskia-android/SkiaPlatformContext.h | 26 ++ .../reactnative/skia/RNSkiaPackage.java | 5 +- .../reactnative/skia/WebGPUSurfaceView.java | 41 ++++ .../reactnative/skia/WebGPUTextureView.java | 44 ++++ .../shopify/reactnative/skia/WebGPUView.java | 95 ++++++++ .../reactnative/skia/WebGPUViewAPI.java | 14 ++ .../reactnative/skia/WebGPUViewManager.java | 58 +++++ packages/skia/apple/RNSkUIKit.h | 13 + packages/skia/apple/SkiaPlatformContext.h | 20 ++ packages/skia/apple/SkiaPlatformContext.mm | 21 ++ packages/skia/apple/WebGPUMetalView.h | 12 + packages/skia/apple/WebGPUMetalView.mm | 93 +++++++ packages/skia/apple/WebGPUView.h | 20 ++ packages/skia/apple/WebGPUView.mm | 77 ++++++ packages/skia/cpp/rnskia/RNSkManager.cpp | 6 + packages/skia/cpp/rnwgpu/Canvas.h | 45 ++++ packages/skia/cpp/rnwgpu/PlatformContext.h | 18 ++ packages/skia/cpp/rnwgpu/SurfaceRegistry.h | 229 ++++++++++++++++++ .../skia/cpp/rnwgpu/api/GPUCanvasContext.cpp | 64 +++++ .../skia/cpp/rnwgpu/api/GPUCanvasContext.h | 65 +++++ packages/skia/cpp/rnwgpu/api/RNWebGPU.h | 62 +++++ .../api/descriptors/GPUCanvasConfiguration.h | 76 ++++++ packages/skia/package.json | 13 +- .../text/text-path-arabic-component-node.png | Bin 0 -> 31071 bytes .../src/specs/WebGPUViewNativeComponent.ts | 11 + packages/skia/src/views/WebGPUCanvas.tsx | 110 +++++++++ packages/skia/src/views/index.ts | 1 + 37 files changed, 1650 insertions(+), 66 deletions(-) create mode 100644 apps/example/src/Examples/WebGPU/List.tsx create mode 100644 apps/example/src/Examples/WebGPU/Routes.ts create mode 100644 apps/example/src/Examples/WebGPU/Triangle.tsx rename apps/example/src/Examples/WebGPU/{WebGPU.tsx => Wireframes.tsx} (99%) delete mode 100644 apps/example/src/Examples/WebGPU/index.ts create mode 100644 apps/example/src/Examples/WebGPU/index.tsx create mode 100644 packages/skia/android/cpp/jni/JniWebGPUView.cpp create mode 100644 packages/skia/android/cpp/rnskia-android/SkiaPlatformContext.h create mode 100644 packages/skia/android/src/main/java/com/shopify/reactnative/skia/WebGPUSurfaceView.java create mode 100644 packages/skia/android/src/main/java/com/shopify/reactnative/skia/WebGPUTextureView.java create mode 100644 packages/skia/android/src/main/java/com/shopify/reactnative/skia/WebGPUView.java create mode 100644 packages/skia/android/src/main/java/com/shopify/reactnative/skia/WebGPUViewAPI.java create mode 100644 packages/skia/android/src/main/java/com/shopify/reactnative/skia/WebGPUViewManager.java create mode 100644 packages/skia/apple/RNSkUIKit.h create mode 100644 packages/skia/apple/SkiaPlatformContext.h create mode 100644 packages/skia/apple/SkiaPlatformContext.mm create mode 100644 packages/skia/apple/WebGPUMetalView.h create mode 100644 packages/skia/apple/WebGPUMetalView.mm create mode 100644 packages/skia/apple/WebGPUView.h create mode 100644 packages/skia/apple/WebGPUView.mm create mode 100644 packages/skia/cpp/rnwgpu/Canvas.h create mode 100644 packages/skia/cpp/rnwgpu/PlatformContext.h create mode 100644 packages/skia/cpp/rnwgpu/SurfaceRegistry.h create mode 100644 packages/skia/cpp/rnwgpu/api/GPUCanvasContext.cpp create mode 100644 packages/skia/cpp/rnwgpu/api/GPUCanvasContext.h create mode 100644 packages/skia/cpp/rnwgpu/api/RNWebGPU.h create mode 100644 packages/skia/cpp/rnwgpu/api/descriptors/GPUCanvasConfiguration.h create mode 100644 packages/skia/src/__tests__/snapshots/text/text-path-arabic-component-node.png create mode 100644 packages/skia/src/specs/WebGPUViewNativeComponent.ts create mode 100644 packages/skia/src/views/WebGPUCanvas.tsx diff --git a/apps/example/ios/Podfile.lock b/apps/example/ios/Podfile.lock index f5b6ae7f22..a43dd699e5 100644 --- a/apps/example/ios/Podfile.lock +++ b/apps/example/ios/Podfile.lock @@ -2116,76 +2116,76 @@ SPEC CHECKSUMS: fmt: a40bb5bd0294ea969aaaba240a927bd33d878cdd glog: eb93e2f488219332457c3c4eafd2738ddc7e80b8 hermes-engine: b417d2b2aee3b89b58e63e23a51e02be91dc876d - RCT-Folly: 36fe2295e44b10d831836cc0d1daec5f8abcf809 + RCT-Folly: e78785aa9ba2ed998ea4151e314036f6c49e6d82 RCTDeprecation: b2eecf2d60216df56bc5e6be5f063826d3c1ee35 RCTRequired: 78522de7dc73b81f3ed7890d145fa341f5bb32ea RCTTypeSafety: c135dd2bf50402d87fd12884cbad5d5e64850edd React: b229c49ed5898dab46d60f61ed5a0bfa2ee2fadb React-callinvoker: 2ac508e92c8bd9cf834cc7d7787d94352e4af58f - React-Core: 13cdd1558d0b3f6d9d5a22e14d89150280e79f02 - React-CoreModules: b07a6744f48305405e67c845ebf481b6551b712a - React-cxxreact: 1055a86c66ac35b4e80bd5fb766aed5f494dfff4 + React-Core: 325b4f6d9162ae8b9a6ff42fe78e260eb124180d + React-CoreModules: 558041e5258f70cd1092f82778d07b8b2ff01897 + React-cxxreact: 8fff17cbe76e6a8f9991b59552e1235429f9c74b React-debug: 0a5fcdbacc6becba0521e910c1bcfdb20f32a3f6 - React-defaultsnativemodule: 4bb28fc97fee5be63a9ebf8f7a435cfe8ba69459 - React-domnativemodule: b36a11c2597243d7563985028c51ece988d8ae33 - React-Fabric: afc561718f25b2cd800b709d934101afe376a12c - React-FabricComponents: f4e0a4e18a27bf6d39cbf2a0b42f37a92fa4e37f - React-FabricImage: 37d8e8b672eda68a19d71143eb65148084efb325 + React-defaultsnativemodule: 618dc50a0fad41b489997c3eb7aba3a74479fd14 + React-domnativemodule: 7ba599afb6c2a7ec3eb6450153e2efe0b8747e9a + React-Fabric: 252112089d2c63308f4cbfade4010b6606db67d1 + React-FabricComponents: 3c0f75321680d14d124438ab279c64ec2a3d13c4 + React-FabricImage: 728b8061cdec2857ca885fd605ee03ad43ffca98 React-featureflags: 19682e02ef5861d96b992af16a19109c3dfc1200 - React-featureflagsnativemodule: d7cddf6d907b4e5ab84f9e744b7e88461656e48c - React-graphics: b0f78580cdaf5800d25437e3d41cc6c3d83b7aea - React-hermes: 71186f872c932e4574d5feb3ed754dda63a0b3bd - React-idlecallbacksnativemodule: dd2af19cdd3bc55149d17a2409ed72b694dfbe9c - React-ImageManager: a77dde8d5aa6a2b6962c702bf3a47695ef0aa32b - React-jserrorhandler: 9c14e89f12d5904257a79aaf84a70cd2e5ac07ba - React-jsi: 0775a66820496769ad83e629f0f5cce621a57fc7 - React-jsiexecutor: 2cf5ba481386803f3c88b85c63fa102cba5d769e - React-jsinspector: 8052d532bb7a98b6e021755674659802fb140cc5 - React-jsinspectortracing: bdd8fd0adcb4813663562e7874c5842449df6d8a - React-jsitracing: 2bab3bf55de3d04baf205def375fa6643c47c794 - React-logger: 795cd5055782db394f187f9db0477d4b25b44291 - React-Mapbuffer: 0502faf46cab8fb89cfc7bf3e6c6109b6ef9b5de - React-microtasksnativemodule: 663bc64e3a96c5fc91081923ae7481adc1359a78 - react-native-safe-area-context: 286b3e7b5589795bb85ffc38faf4c0706c48a092 - react-native-skia: 051de3960d565ea3e2440cfcf5f919bc95617ad3 - React-NativeModulesApple: 16fbd5b040ff6c492dacc361d49e63cba7a6a7a1 - React-perflogger: ab51b7592532a0ea45bf6eed7e6cae14a368b678 - React-performancetimeline: bc2e48198ec814d578ac8401f65d78a574358203 + React-featureflagsnativemodule: 23528c7e7d50782b7ef0804168ba40bbaf1e86ab + React-graphics: fefe48f71bfe6f48fd037f59e8277b12e91b6be1 + React-hermes: a9a0c8377627b5506ef9a7b6f60a805c306e3f51 + React-idlecallbacksnativemodule: 7e2b6a3b70e042f89cd91dbd73c479bb39a72a7e + React-ImageManager: e3300996ac2e2914bf821f71e2f2c92ae6e62ae2 + React-jserrorhandler: fa75876c662e5d7e79d6efc763fc9f4c88e26986 + React-jsi: f3f51595cc4c089037b536368f016d4742bf9cf7 + React-jsiexecutor: cca6c232db461e2fd213a11e9364cfa6fdaa20eb + React-jsinspector: 2bd4c9fddf189d6ec2abf4948461060502582bef + React-jsinspectortracing: a417d8a0ad481edaa415734b4dac81e3e5ee7dc6 + React-jsitracing: 1ff7172c5b0522cbf6c98d82bdbb160e49b5804e + React-logger: 018826bfd51b9f18e87f67db1590bc510ad20664 + React-Mapbuffer: 3c11cee7737609275c7b66bd0b1de475f094cedf + React-microtasksnativemodule: 843f352b32aacbe13a9c750190d34df44c3e6c2c + react-native-safe-area-context: 0f14bce545abcdfbff79ce2e3c78c109f0be283e + react-native-skia: 019216a54bc6f881d1a8aa86125b5eb6141d660b + React-NativeModulesApple: 88433b6946778bea9c153e27b671de15411bf225 + React-perflogger: 9e8d3c0dc0194eb932162812a168aa5dc662f418 + React-performancetimeline: 5a2d6efef52bdcefac079c7baa30934978acd023 React-RCTActionSheet: 592674cf61142497e0e820688f5a696e41bf16dd - React-RCTAnimation: 8fbb8dba757b49c78f4db403133ab6399a4ce952 - React-RCTAppDelegate: 7f88baa8cb4e5d6c38bb4d84339925c70c9ac864 - React-RCTBlob: f89b162d0fe6b570a18e755eb16cbe356d3c6d17 - React-RCTFabric: 8ad6d875abe6e87312cef90e4b15ef7f6bed72e6 - React-RCTFBReactNativeSpec: 8c29630c2f379c729300e4c1e540f3d1b78d1936 - React-RCTImage: ccac9969940f170503857733f9a5f63578e106e1 - React-RCTLinking: d82427bbf18415a3732105383dff119131cadd90 - React-RCTNetwork: 12ad4d0fbde939e00251ca5ca890da2e6825cc3c - React-RCTSettings: e7865bf9f455abf427da349c855f8644b5c39afa - React-RCTText: 2cdfd88745059ec3202a0842ea75a956c7d6f27d - React-RCTVibration: a3a1458e6230dfd64b3768ebc0a4aac430d9d508 + React-RCTAnimation: e6d669872f9b3b4ab9527aab283b7c49283236b7 + React-RCTAppDelegate: de2343fe08be4c945d57e0ecce44afcc7dd8fc03 + React-RCTBlob: 3e2dce94c56218becc4b32b627fc2293149f798d + React-RCTFabric: cac2c033381d79a5956e08550b0220cb2d78ea93 + React-RCTFBReactNativeSpec: d10ca5e0ccbfeac8c047361fedf8e4ac653887b6 + React-RCTImage: dc04b176c022d12a8f55ae7a7279b1e091066ae0 + React-RCTLinking: 88f5e37fe4f26fbc80791aa2a5f01baf9b9a3fd5 + React-RCTNetwork: f213693565efbd698b8e9c18d700a514b49c0c8e + React-RCTSettings: a2d32a90c45a3575568cad850abc45924999b8a5 + React-RCTText: 54cdcd1cbf6f6a91dc6317f5d2c2b7fc3f6bf7a0 + React-RCTVibration: 11dae0e7f577b5807bb7d31e2e881eb46f854fd4 React-rendererconsistency: 64e897e00d2568fd8dfe31e2496f80e85c0aaad1 - React-rendererdebug: a3f6d3ae7d2fa0035885026756281c07ee32479e + React-rendererdebug: 41ce452460c44bba715d9e41d5493a96de277764 React-rncore: 58748c2aa445f56b99e5118dad0aedb51c40ce9f - React-RuntimeApple: f0fda7bacabd32daa099cfda8f07466c30acd149 - React-RuntimeCore: 683ee0b6a76d4b4bf6fbf83a541895b4887cc636 + React-RuntimeApple: 7785ed0d8ae54da65a88736bb63ca97608a6d933 + React-RuntimeCore: 6029ea70bc77f98cfd43ebe69217f14e93ba1f12 React-runtimeexecutor: a188df372373baf5066e6e229177836488799f80 - React-RuntimeHermes: 907c8e9bec13ea6466b94828c088c24590d4d0b6 - React-runtimescheduler: a2e2a39125dd6426b5d8b773f689d660cd7c5f60 + React-RuntimeHermes: a264609c28b796edfffc8ae4cb8fad1773ab948b + React-runtimescheduler: 23ec3a1e0fb1ec752d1a9c1fb15258c30bfc7222 React-timing: bb220a53a795ed57976a4855c521f3de2f298fe5 - React-utils: 300d8bbb6555dcffaca71e7a0663201b5c7edbbc - ReactAppDependencyProvider: f2e81d80afd71a8058589e19d8a134243fa53f17 - ReactCodegen: 50b6e45bbbef9b39d9798820cdbe87bfc7922e22 - ReactCommon: 3d39389f8e2a2157d5c999f8fba57bd1c8f226f0 - ReactNativeHost: e96154926221741f253f2c1ded13c6959c5c3d43 - ReactTestApp-DevSupport: 6994b53b5b81139a8ce63e0776c726c95de079a1 + React-utils: 3b054aaebe658fc710a8d239d0e4b9fd3e0b78f9 + ReactAppDependencyProvider: a1fb08dfdc7ebc387b2e54cfc9decd283ed821d8 + ReactCodegen: e232f8db3a40721044ec81b9388f95a7afaad36a + ReactCommon: 0c097b53f03d6bf166edbcd0915da32f3015dd90 + ReactNativeHost: 1b6ccdcfc87bb31e772a5b3c3ca3b09c90954328 + ReactTestApp-DevSupport: ea18f446cff64b6c9a3e28788600c82ecf51bde6 ReactTestApp-Resources: 1bd9ff10e4c24f2ad87101a32023721ae923bccf - RNGestureHandler: 66e593addd8952725107cfaa4f5e3378e946b541 - RNReanimated: 858fe25904af44131b8b608a5005b64778609a6a - RNScreens: 0f01bbed9bd8045a8d58e4b46993c28c7f498f3c - RNSVG: 57b9a2e7d149f115d70848c3247f31c7010c6941 + RNGestureHandler: dcb1b1db024f3744b03af56d132f4f72c4c27195 + RNReanimated: d5f33d14a4d1da33a02d89124de233a64b3aaeaa + RNScreens: 790123c4a28783d80a342ce42e8c7381bed62db1 + RNSVG: 05a9310dfd69f18a69f6aa7ba5ddaa44bf24fd1c SocketRocket: d4aabe649be1e368d1318fdf28a022d714d65748 - Yoga: 9b7fb56e7b08cde60e2153344fa6afbd88e5d99f + Yoga: afd04ff05ebe0121a00c468a8a3c8080221cb14c PODFILE CHECKSUM: 87506345285a0371afb28b9c3e6daaa999c214f3 -COCOAPODS: 1.15.2 +COCOAPODS: 1.16.2 diff --git a/apps/example/src/Examples/WebGPU/List.tsx b/apps/example/src/Examples/WebGPU/List.tsx new file mode 100644 index 0000000000..de148ce772 --- /dev/null +++ b/apps/example/src/Examples/WebGPU/List.tsx @@ -0,0 +1,64 @@ +import * as React from "react"; +import { ScrollView, StyleSheet, Text, View, Pressable } from "react-native"; +import { useNavigation } from "@react-navigation/native"; +import type { NativeStackNavigationProp } from "@react-navigation/native-stack"; + +import type { Routes } from "./Routes"; + +export const examples = [ + { + screen: "Triangle", + title: "Triangle", + description: "Basic WebGPU Canvas rendering", + }, + { + screen: "Wireframes", + title: "Wireframes", + description: "3D wireframe models with offscreen rendering", + }, +] as const; + +const styles = StyleSheet.create({ + container: {}, + content: { + paddingBottom: 32, + }, + thumbnail: { + backgroundColor: "white", + padding: 32, + borderBottomWidth: StyleSheet.hairlineWidth, + }, + title: { + color: "black", + fontSize: 16, + fontWeight: "bold", + }, + description: { + color: "#666", + fontSize: 14, + marginTop: 4, + }, +}); + +export const List = () => { + const { navigate } = + useNavigation>(); + return ( + + {examples.map((example) => ( + { + navigate(example.screen as keyof Routes); + }} + testID={example.screen} + > + + {example.title} + {example.description} + + + ))} + + ); +}; diff --git a/apps/example/src/Examples/WebGPU/Routes.ts b/apps/example/src/Examples/WebGPU/Routes.ts new file mode 100644 index 0000000000..7e6b11222f --- /dev/null +++ b/apps/example/src/Examples/WebGPU/Routes.ts @@ -0,0 +1,5 @@ +export type Routes = { + List: undefined; + Wireframes: undefined; + Triangle: undefined; +}; diff --git a/apps/example/src/Examples/WebGPU/Triangle.tsx b/apps/example/src/Examples/WebGPU/Triangle.tsx new file mode 100644 index 0000000000..622fc7b137 --- /dev/null +++ b/apps/example/src/Examples/WebGPU/Triangle.tsx @@ -0,0 +1,181 @@ +import React, { useEffect, useRef } from "react"; +import { StyleSheet, View, Text } from "react-native"; +import type { WebGPUCanvasRef } from "@shopify/react-native-skia"; +import { WebGPUCanvas } from "@shopify/react-native-skia"; + +const triangleShader = ` +@vertex +fn vs_main(@builtin(vertex_index) vertexIndex: u32) -> @builtin(position) vec4f { + var pos = array( + vec2f( 0.0, 0.5), + vec2f(-0.5, -0.5), + vec2f( 0.5, -0.5) + ); + return vec4f(pos[vertexIndex], 0.0, 1.0); +} + +@fragment +fn fs_main() -> @location(0) vec4f { + return vec4f(1.0, 0.5, 0.2, 1.0); +} +`; + +export function Triangle() { + const canvasRef = useRef(null); + const animationRef = useRef(0); + const cleanupRef = useRef<(() => void) | null>(null); + + useEffect(() => { + // Small delay to ensure the canvas is mounted + const timeoutId = setTimeout(async () => { + if (!canvasRef.current) { + return; + } + + // Check if RNWebGPU is available (SK_GRAPHITE must be enabled) + if (typeof RNWebGPU === "undefined") { + console.warn( + "RNWebGPU is not available. Make sure SK_GRAPHITE is enabled." + ); + return; + } + + const ctx = canvasRef.current.getContext("webgpu"); + if (!ctx) { + console.warn("Failed to get WebGPU context"); + return; + } + + // Get the device from navigator.gpu + const adapter = await navigator.gpu.requestAdapter(); + if (!adapter) { + console.warn("Failed to get GPU adapter"); + return; + } + + const device = await adapter.requestDevice(); + + // Configure the context + const format = navigator.gpu.getPreferredCanvasFormat(); + ctx.configure({ + device, + format, + alphaMode: "opaque", + }); + + // Create shader module + const shaderModule = device.createShaderModule({ + code: triangleShader, + }); + + // Create render pipeline + const pipeline = device.createRenderPipeline({ + layout: "auto", + vertex: { + module: shaderModule, + entryPoint: "vs_main", + }, + fragment: { + module: shaderModule, + entryPoint: "fs_main", + targets: [{ format }], + }, + primitive: { + topology: "triangle-list", + }, + }); + + let running = true; + + const render = () => { + if (!running) { + return; + } + + const texture = ctx.getCurrentTexture(); + const renderPassDescriptor: GPURenderPassDescriptor = { + colorAttachments: [ + { + view: texture.createView(), + clearValue: { r: 0.1, g: 0.1, b: 0.1, a: 1.0 }, + loadOp: "clear", + storeOp: "store", + }, + ], + }; + + const commandEncoder = device.createCommandEncoder(); + const passEncoder = commandEncoder.beginRenderPass(renderPassDescriptor); + passEncoder.setPipeline(pipeline); + passEncoder.draw(3); + passEncoder.end(); + + device.queue.submit([commandEncoder.finish()]); + ctx.present(); + + animationRef.current = requestAnimationFrame(render); + }; + + animationRef.current = requestAnimationFrame(render); + + cleanupRef.current = () => { + running = false; + cancelAnimationFrame(animationRef.current); + }; + }, 100); + + return () => { + clearTimeout(timeoutId); + cleanupRef.current?.(); + }; + }, []); + + // Check if WebGPU is available + if (typeof RNWebGPU === "undefined") { + return ( + + + + WebGPU Canvas requires SK_GRAPHITE to be enabled. + + + Build react-native-skia with Graphite support to use this feature. + + + + ); + } + + return ( + + + + ); +} + +const styles = StyleSheet.create({ + container: { + flex: 1, + backgroundColor: "#1a1a1a", + }, + canvas: { + flex: 1, + }, + messageContainer: { + flex: 1, + justifyContent: "center", + alignItems: "center", + padding: 20, + }, + message: { + color: "#fff", + fontSize: 18, + textAlign: "center", + marginBottom: 10, + }, + submessage: { + color: "#888", + fontSize: 14, + textAlign: "center", + }, +}); diff --git a/apps/example/src/Examples/WebGPU/WebGPU.tsx b/apps/example/src/Examples/WebGPU/Wireframes.tsx similarity index 99% rename from apps/example/src/Examples/WebGPU/WebGPU.tsx rename to apps/example/src/Examples/WebGPU/Wireframes.tsx index b65b5f8dfa..d69b63d74c 100644 --- a/apps/example/src/Examples/WebGPU/WebGPU.tsx +++ b/apps/example/src/Examples/WebGPU/Wireframes.tsx @@ -124,7 +124,7 @@ type ObjectInfo = { // 0, 0, 0, 1, 0, // ]; -export function WebGPU() { +export function Wireframes() { const { width, height } = useWindowDimensions(); const [image, setImage] = useState(null); const renderRef = useRef<((ts: number) => void) | null>(null); diff --git a/apps/example/src/Examples/WebGPU/index.ts b/apps/example/src/Examples/WebGPU/index.ts deleted file mode 100644 index 89aa395b91..0000000000 --- a/apps/example/src/Examples/WebGPU/index.ts +++ /dev/null @@ -1 +0,0 @@ -export { WebGPU } from "./WebGPU"; diff --git a/apps/example/src/Examples/WebGPU/index.tsx b/apps/example/src/Examples/WebGPU/index.tsx new file mode 100644 index 0000000000..ddff78898f --- /dev/null +++ b/apps/example/src/Examples/WebGPU/index.tsx @@ -0,0 +1,39 @@ +import React from "react"; +import { createNativeStackNavigator } from "@react-navigation/native-stack"; + +import type { Routes } from "./Routes"; +import { List } from "./List"; +import { Triangle } from "./Triangle"; +import { Wireframes } from "./Wireframes"; + +const Stack = createNativeStackNavigator(); + +export const WebGPU = () => { + return ( + + null, + }} + /> + + null, + }} + /> + + ); +}; diff --git a/externals/skia b/externals/skia index ee20d565ac..f4ed99d244 160000 --- a/externals/skia +++ b/externals/skia @@ -1 +1 @@ -Subproject commit ee20d565acb08dece4a32e3f209cdd41119015ca +Subproject commit f4ed99d2443962782cf5f8b4dd27179f131e7cbe diff --git a/packages/skia/android/CMakeLists.txt b/packages/skia/android/CMakeLists.txt index 6dccb66ecf..6e5d48ec89 100644 --- a/packages/skia/android/CMakeLists.txt +++ b/packages/skia/android/CMakeLists.txt @@ -137,6 +137,7 @@ if(SK_GRAPHITE) "${PROJECT_SOURCE_DIR}/../cpp/rnwgpu/api/GPUAdapter.cpp" "${PROJECT_SOURCE_DIR}/../cpp/rnwgpu/api/GPUBindGroup.cpp" "${PROJECT_SOURCE_DIR}/../cpp/rnwgpu/api/GPUBuffer.cpp" + "${PROJECT_SOURCE_DIR}/../cpp/rnwgpu/api/GPUCanvasContext.cpp" "${PROJECT_SOURCE_DIR}/../cpp/rnwgpu/api/GPUCommandEncoder.cpp" "${PROJECT_SOURCE_DIR}/../cpp/rnwgpu/api/GPUComputePassEncoder.cpp" "${PROJECT_SOURCE_DIR}/../cpp/rnwgpu/api/GPUComputePipeline.cpp" @@ -150,6 +151,9 @@ if(SK_GRAPHITE) "${PROJECT_SOURCE_DIR}/../cpp/rnwgpu/api/GPUShaderModule.cpp" "${PROJECT_SOURCE_DIR}/../cpp/rnwgpu/api/GPUSupportedLimits.cpp" "${PROJECT_SOURCE_DIR}/../cpp/rnwgpu/api/GPUTexture.cpp" + + # WebGPU Canvas JNI bindings + "${PROJECT_SOURCE_DIR}/cpp/jni/JniWebGPUView.cpp" ) endif() diff --git a/packages/skia/android/cpp/jni/JniWebGPUView.cpp b/packages/skia/android/cpp/jni/JniWebGPUView.cpp new file mode 100644 index 0000000000..ecff186f20 --- /dev/null +++ b/packages/skia/android/cpp/jni/JniWebGPUView.cpp @@ -0,0 +1,67 @@ +#include +#include + +#ifdef SK_GRAPHITE +#include "webgpu/webgpu_cpp.h" +#include "rnwgpu/SurfaceRegistry.h" +#include "rnskia/RNDawnContext.h" +#endif + +extern "C" JNIEXPORT void JNICALL +Java_com_shopify_reactnative_skia_WebGPUView_onSurfaceCreate( + JNIEnv *env, jobject thiz, jobject jSurface, jint contextId, jfloat width, + jfloat height) { +#ifdef SK_GRAPHITE + auto window = ANativeWindow_fromSurface(env, jSurface); + auto ®istry = rnwgpu::SurfaceRegistry::getInstance(); + auto &dawnContext = RNSkia::DawnContext::getInstance(); + auto gpu = dawnContext.getWGPUInstance(); + + // Create surface from ANativeWindow + wgpu::SurfaceDescriptorFromAndroidNativeWindow androidSurfaceDesc; + androidSurfaceDesc.window = window; + wgpu::SurfaceDescriptor surfaceDescriptor; + surfaceDescriptor.nextInChain = &androidSurfaceDesc; + auto surface = gpu.CreateSurface(&surfaceDescriptor); + + registry + .getSurfaceInfoOrCreate(contextId, gpu, static_cast(width), + static_cast(height)) + ->switchToOnscreen(window, surface); +#endif +} + +extern "C" JNIEXPORT void JNICALL +Java_com_shopify_reactnative_skia_WebGPUView_onSurfaceChanged( + JNIEnv *env, jobject thiz, jobject surface, jint contextId, jfloat width, + jfloat height) { +#ifdef SK_GRAPHITE + auto ®istry = rnwgpu::SurfaceRegistry::getInstance(); + auto surfaceInfo = registry.getSurfaceInfo(contextId); + if (surfaceInfo) { + surfaceInfo->resize(static_cast(width), static_cast(height)); + } +#endif +} + +extern "C" JNIEXPORT void JNICALL +Java_com_shopify_reactnative_skia_WebGPUView_switchToOffscreenSurface( + JNIEnv *env, jobject thiz, jint contextId) { +#ifdef SK_GRAPHITE + auto ®istry = rnwgpu::SurfaceRegistry::getInstance(); + auto surfaceInfo = registry.getSurfaceInfo(contextId); + if (surfaceInfo) { + surfaceInfo->switchToOffscreen(); + } +#endif +} + +extern "C" JNIEXPORT void JNICALL +Java_com_shopify_reactnative_skia_WebGPUView_onSurfaceDestroy(JNIEnv *env, + jobject thiz, + jint contextId) { +#ifdef SK_GRAPHITE + auto ®istry = rnwgpu::SurfaceRegistry::getInstance(); + registry.removeSurfaceInfo(contextId); +#endif +} diff --git a/packages/skia/android/cpp/rnskia-android/SkiaPlatformContext.h b/packages/skia/android/cpp/rnskia-android/SkiaPlatformContext.h new file mode 100644 index 0000000000..23632892fd --- /dev/null +++ b/packages/skia/android/cpp/rnskia-android/SkiaPlatformContext.h @@ -0,0 +1,26 @@ +#pragma once + +#ifdef SK_GRAPHITE + +#include "rnwgpu/PlatformContext.h" + +namespace rnwgpu { + +class SkiaPlatformContext : public PlatformContext { +public: + SkiaPlatformContext() = default; + ~SkiaPlatformContext() = default; + + wgpu::Surface makeSurface(wgpu::Instance instance, void *surface, int width, + int height) override { + wgpu::SurfaceDescriptorFromAndroidNativeWindow androidSurfaceDesc; + androidSurfaceDesc.window = surface; + wgpu::SurfaceDescriptor surfaceDescriptor; + surfaceDescriptor.nextInChain = &androidSurfaceDesc; + return instance.CreateSurface(&surfaceDescriptor); + } +}; + +} // namespace rnwgpu + +#endif // SK_GRAPHITE diff --git a/packages/skia/android/src/main/java/com/shopify/reactnative/skia/RNSkiaPackage.java b/packages/skia/android/src/main/java/com/shopify/reactnative/skia/RNSkiaPackage.java index fa83eeebc8..08c598a392 100644 --- a/packages/skia/android/src/main/java/com/shopify/reactnative/skia/RNSkiaPackage.java +++ b/packages/skia/android/src/main/java/com/shopify/reactnative/skia/RNSkiaPackage.java @@ -42,7 +42,10 @@ public NativeModule getModule(String s, ReactApplicationContext reactApplication @Override public List createViewManagers(ReactApplicationContext reactContext) { - return Arrays.asList(new SkiaPictureViewManager()); + return Arrays.asList( + new SkiaPictureViewManager(), + new WebGPUViewManager() + ); } @Override diff --git a/packages/skia/android/src/main/java/com/shopify/reactnative/skia/WebGPUSurfaceView.java b/packages/skia/android/src/main/java/com/shopify/reactnative/skia/WebGPUSurfaceView.java new file mode 100644 index 0000000000..787bc0ac97 --- /dev/null +++ b/packages/skia/android/src/main/java/com/shopify/reactnative/skia/WebGPUSurfaceView.java @@ -0,0 +1,41 @@ +package com.shopify.reactnative.skia; + +import android.annotation.SuppressLint; +import android.content.Context; +import android.view.SurfaceHolder; +import android.view.SurfaceView; + +import androidx.annotation.NonNull; + +@SuppressLint("ViewConstructor") +public class WebGPUSurfaceView extends SurfaceView implements SurfaceHolder.Callback { + + WebGPUViewAPI mApi; + + public WebGPUSurfaceView(Context context, WebGPUViewAPI api) { + super(context); + mApi = api; + getHolder().addCallback(this); + } + + @Override + protected void onDetachedFromWindow() { + super.onDetachedFromWindow(); + mApi.surfaceDestroyed(); + } + + @Override + public void surfaceCreated(@NonNull SurfaceHolder holder) { + mApi.surfaceCreated(holder.getSurface()); + } + + @Override + public void surfaceChanged(@NonNull SurfaceHolder holder, int format, int width, int height) { + mApi.surfaceChanged(holder.getSurface()); + } + + @Override + public void surfaceDestroyed(@NonNull SurfaceHolder holder) { + mApi.surfaceOffscreen(); + } +} diff --git a/packages/skia/android/src/main/java/com/shopify/reactnative/skia/WebGPUTextureView.java b/packages/skia/android/src/main/java/com/shopify/reactnative/skia/WebGPUTextureView.java new file mode 100644 index 0000000000..747cd1b210 --- /dev/null +++ b/packages/skia/android/src/main/java/com/shopify/reactnative/skia/WebGPUTextureView.java @@ -0,0 +1,44 @@ +package com.shopify.reactnative.skia; + +import android.annotation.SuppressLint; +import android.content.Context; +import android.graphics.SurfaceTexture; +import android.view.Surface; +import android.view.TextureView; +import androidx.annotation.NonNull; + +@SuppressLint("ViewConstructor") +public class WebGPUTextureView extends TextureView implements TextureView.SurfaceTextureListener { + + WebGPUViewAPI mApi; + + public WebGPUTextureView(Context context, WebGPUViewAPI api) { + super(context); + mApi = api; + setOpaque(false); + setSurfaceTextureListener(this); + } + + @Override + public void onSurfaceTextureAvailable(@NonNull SurfaceTexture surfaceTexture, int width, int height) { + Surface surface = new Surface(surfaceTexture); + mApi.surfaceCreated(surface); + } + + @Override + public void onSurfaceTextureSizeChanged(@NonNull SurfaceTexture surfaceTexture, int width, int height) { + Surface surface = new Surface(surfaceTexture); + mApi.surfaceChanged(surface); + } + + @Override + public boolean onSurfaceTextureDestroyed(@NonNull SurfaceTexture surfaceTexture) { + mApi.surfaceDestroyed(); + return true; + } + + @Override + public void onSurfaceTextureUpdated(@NonNull SurfaceTexture surfaceTexture) { + // No implementation needed + } +} diff --git a/packages/skia/android/src/main/java/com/shopify/reactnative/skia/WebGPUView.java b/packages/skia/android/src/main/java/com/shopify/reactnative/skia/WebGPUView.java new file mode 100644 index 0000000000..b8f75d3ca2 --- /dev/null +++ b/packages/skia/android/src/main/java/com/shopify/reactnative/skia/WebGPUView.java @@ -0,0 +1,95 @@ +package com.shopify.reactnative.skia; + +import android.content.Context; +import android.view.Surface; +import android.view.View; + +import com.facebook.proguard.annotations.DoNotStrip; +import com.facebook.react.views.view.ReactViewGroup; + +public class WebGPUView extends ReactViewGroup implements WebGPUViewAPI { + + private int mContextId; + private boolean mTransparent = false; + private View mView = null; + + WebGPUView(Context context) { + super(context); + } + + public void setContextId(int contextId) { + mContextId = contextId; + } + + public void setTransparent(boolean value) { + Context ctx = getContext(); + if (value != mTransparent || mView == null) { + if (mView != null) { + removeView(mView); + } + mTransparent = value; + if (mTransparent) { + mView = new WebGPUTextureView(ctx, this); + } else { + mView = new WebGPUSurfaceView(ctx, this); + } + addView(mView); + } + } + + @Override + protected void onLayout(boolean changed, int left, int top, int right, int bottom) { + super.onLayout(changed, left, top, right, bottom); + if (mView != null) { + mView.layout(0, 0, this.getMeasuredWidth(), this.getMeasuredHeight()); + } + } + + @Override + public void surfaceCreated(Surface surface) { + float density = getResources().getDisplayMetrics().density; + float width = getWidth() / density; + float height = getHeight() / density; + onSurfaceCreate(surface, mContextId, width, height); + } + + @Override + public void surfaceChanged(Surface surface) { + float density = getResources().getDisplayMetrics().density; + float width = getWidth() / density; + float height = getHeight() / density; + onSurfaceChanged(surface, mContextId, width, height); + } + + @Override + public void surfaceDestroyed() { + onSurfaceDestroy(mContextId); + } + + @Override + public void surfaceOffscreen() { + switchToOffscreenSurface(mContextId); + } + + @DoNotStrip + private native void onSurfaceCreate( + Surface surface, + int contextId, + float width, + float height + ); + + @DoNotStrip + private native void onSurfaceChanged( + Surface surface, + int contextId, + float width, + float height + ); + + @DoNotStrip + private native void onSurfaceDestroy(int contextId); + + @DoNotStrip + private native void switchToOffscreenSurface(int contextId); +} diff --git a/packages/skia/android/src/main/java/com/shopify/reactnative/skia/WebGPUViewAPI.java b/packages/skia/android/src/main/java/com/shopify/reactnative/skia/WebGPUViewAPI.java new file mode 100644 index 0000000000..897a8bcb52 --- /dev/null +++ b/packages/skia/android/src/main/java/com/shopify/reactnative/skia/WebGPUViewAPI.java @@ -0,0 +1,14 @@ +package com.shopify.reactnative.skia; + +import android.view.Surface; + +public interface WebGPUViewAPI { + + void surfaceCreated(Surface surface); + + void surfaceChanged(Surface surface); + + void surfaceDestroyed(); + + void surfaceOffscreen(); +} diff --git a/packages/skia/android/src/main/java/com/shopify/reactnative/skia/WebGPUViewManager.java b/packages/skia/android/src/main/java/com/shopify/reactnative/skia/WebGPUViewManager.java new file mode 100644 index 0000000000..3065299e2b --- /dev/null +++ b/packages/skia/android/src/main/java/com/shopify/reactnative/skia/WebGPUViewManager.java @@ -0,0 +1,58 @@ +package com.shopify.reactnative.skia; + +import com.facebook.react.module.annotations.ReactModule; +import com.facebook.react.uimanager.ThemedReactContext; +import com.facebook.react.uimanager.annotations.ReactProp; +import com.facebook.react.views.view.ReactViewGroup; +import com.facebook.react.views.view.ReactViewManager; +import com.facebook.react.viewmanagers.WebGPUViewManagerDelegate; +import com.facebook.react.viewmanagers.WebGPUViewManagerInterface; + +import androidx.annotation.NonNull; +import androidx.annotation.Nullable; + +@ReactModule(name = WebGPUViewManager.NAME) +public class WebGPUViewManager extends ReactViewManager implements WebGPUViewManagerInterface { + + public static final String NAME = "WebGPUView"; + + protected WebGPUViewManagerDelegate mDelegate; + + public WebGPUViewManager() { + mDelegate = new WebGPUViewManagerDelegate(this); + } + + protected WebGPUViewManagerDelegate getDelegate() { + return mDelegate; + } + + @NonNull + @Override + public String getName() { + return NAME; + } + + @NonNull + @Override + public WebGPUView createViewInstance(@NonNull ThemedReactContext context) { + return new WebGPUView(context); + } + + @Override + @ReactProp(name = "transparent") + public void setTransparent(WebGPUView view, boolean value) { + view.setTransparent(value); + } + + @Override + @ReactProp(name = "contextId") + public void setContextId(WebGPUView view, int value) { + view.setContextId(value); + } + + @Override + public void onDropViewInstance(@NonNull ReactViewGroup view) { + super.onDropViewInstance(view); + ((WebGPUView) view).surfaceDestroyed(); + } +} diff --git a/packages/skia/apple/RNSkUIKit.h b/packages/skia/apple/RNSkUIKit.h new file mode 100644 index 0000000000..615fd149fa --- /dev/null +++ b/packages/skia/apple/RNSkUIKit.h @@ -0,0 +1,13 @@ +#pragma once + +#if !TARGET_OS_OSX +#import +#else +#import +#endif + +#if !TARGET_OS_OSX +typedef UIView RNSkPlatformView; +#else +typedef NSView RNSkPlatformView; +#endif diff --git a/packages/skia/apple/SkiaPlatformContext.h b/packages/skia/apple/SkiaPlatformContext.h new file mode 100644 index 0000000000..f755309205 --- /dev/null +++ b/packages/skia/apple/SkiaPlatformContext.h @@ -0,0 +1,20 @@ +#pragma once + +#ifdef SK_GRAPHITE + +#include "rnwgpu/PlatformContext.h" + +namespace rnwgpu { + +class SkiaPlatformContext : public PlatformContext { +public: + SkiaPlatformContext() = default; + ~SkiaPlatformContext() = default; + + wgpu::Surface makeSurface(wgpu::Instance instance, void *surface, int width, + int height) override; +}; + +} // namespace rnwgpu + +#endif // SK_GRAPHITE diff --git a/packages/skia/apple/SkiaPlatformContext.mm b/packages/skia/apple/SkiaPlatformContext.mm new file mode 100644 index 0000000000..f2f50acd13 --- /dev/null +++ b/packages/skia/apple/SkiaPlatformContext.mm @@ -0,0 +1,21 @@ +#ifdef SK_GRAPHITE + +#include "SkiaPlatformContext.h" + +#include + +namespace rnwgpu { + +wgpu::Surface SkiaPlatformContext::makeSurface(wgpu::Instance instance, + void *surface, int width, + int height) { + wgpu::SurfaceSourceMetalLayer metalSurfaceDesc; + metalSurfaceDesc.layer = surface; + wgpu::SurfaceDescriptor surfaceDescriptor; + surfaceDescriptor.nextInChain = &metalSurfaceDesc; + return instance.CreateSurface(&surfaceDescriptor); +} + +} // namespace rnwgpu + +#endif // SK_GRAPHITE diff --git a/packages/skia/apple/WebGPUMetalView.h b/packages/skia/apple/WebGPUMetalView.h new file mode 100644 index 0000000000..c17a710611 --- /dev/null +++ b/packages/skia/apple/WebGPUMetalView.h @@ -0,0 +1,12 @@ +#pragma once + +#import "RNSkUIKit.h" + +@interface WebGPUMetalView : RNSkPlatformView + +@property (nonatomic, strong) NSNumber *contextId; + +- (void)configure; +- (void)update; + +@end diff --git a/packages/skia/apple/WebGPUMetalView.mm b/packages/skia/apple/WebGPUMetalView.mm new file mode 100644 index 0000000000..b7404646fc --- /dev/null +++ b/packages/skia/apple/WebGPUMetalView.mm @@ -0,0 +1,93 @@ +#import "WebGPUMetalView.h" + +#ifdef SK_GRAPHITE + +#import "webgpu/webgpu_cpp.h" +#import + +#import "rnwgpu/SurfaceRegistry.h" +#import "rnskia/RNDawnContext.h" + +@implementation WebGPUMetalView { + BOOL _isConfigured; +} + +#if !TARGET_OS_OSX ++ (Class)layerClass { + return [CAMetalLayer class]; +} +#else // !TARGET_OS_OSX +- (instancetype)init { + self = [super init]; + if (self) { + self.wantsLayer = true; + self.layer = [CAMetalLayer layer]; + } + return self; +} +#endif // !TARGET_OS_OSX + +- (void)configure { + auto size = self.frame.size; + void *nativeSurface = (__bridge void *)self.layer; + auto ®istry = rnwgpu::SurfaceRegistry::getInstance(); + auto &dawnContext = RNSkia::DawnContext::getInstance(); + auto gpu = dawnContext.getWGPUInstance(); + + // Create the surface using Dawn's API directly + wgpu::SurfaceSourceMetalLayer metalSurfaceDesc; + metalSurfaceDesc.layer = nativeSurface; + wgpu::SurfaceDescriptor surfaceDescriptor; + surfaceDescriptor.nextInChain = &metalSurfaceDesc; + auto surface = gpu.CreateSurface(&surfaceDescriptor); + + registry + .getSurfaceInfoOrCreate([_contextId intValue], gpu, size.width, + size.height) + ->switchToOnscreen(nativeSurface, surface); +} + +- (void)update { + auto size = self.frame.size; + auto ®istry = rnwgpu::SurfaceRegistry::getInstance(); + auto surfaceInfo = registry.getSurfaceInfo([_contextId intValue]); + if (surfaceInfo) { + surfaceInfo->resize(size.width, size.height); + } +} + +- (void)dealloc { + auto ®istry = rnwgpu::SurfaceRegistry::getInstance(); + // Remove the surface info from the registry + registry.removeSurfaceInfo([_contextId intValue]); +} + +@end + +#else // SK_GRAPHITE + +// Stub implementation when GRAPHITE is not enabled +@implementation WebGPUMetalView + +#if !TARGET_OS_OSX ++ (Class)layerClass { + return [CAMetalLayer class]; +} +#else // !TARGET_OS_OSX +- (instancetype)init { + self = [super init]; + return self; +} +#endif // !TARGET_OS_OSX + +- (void)configure { + // No-op when GRAPHITE is not enabled +} + +- (void)update { + // No-op when GRAPHITE is not enabled +} + +@end + +#endif // SK_GRAPHITE diff --git a/packages/skia/apple/WebGPUView.h b/packages/skia/apple/WebGPUView.h new file mode 100644 index 0000000000..a3657d8727 --- /dev/null +++ b/packages/skia/apple/WebGPUView.h @@ -0,0 +1,20 @@ +#pragma once + +#ifdef RCT_NEW_ARCH_ENABLED + +#import "WebGPUMetalView.h" +#import +#if !TARGET_OS_OSX +#import +#else +#import +#endif + +NS_ASSUME_NONNULL_BEGIN + +@interface WebGPUView : RCTViewComponentView +@end + +NS_ASSUME_NONNULL_END + +#endif // RCT_NEW_ARCH_ENABLED diff --git a/packages/skia/apple/WebGPUView.mm b/packages/skia/apple/WebGPUView.mm new file mode 100644 index 0000000000..04f99e2c62 --- /dev/null +++ b/packages/skia/apple/WebGPUView.mm @@ -0,0 +1,77 @@ +#ifdef RCT_NEW_ARCH_ENABLED + +#import "WebGPUView.h" + +#import +#import +#import +#import + +#import "WebGPUMetalView.h" +#import "RCTFabricComponentsPlugins.h" + +using namespace facebook::react; + +@implementation WebGPUView + +- (instancetype)initWithFrame:(CGRect)frame { + if (self = [super initWithFrame:frame]) { + static const auto defaultProps = std::make_shared(); + _props = defaultProps; + } + return self; +} + ++ (ComponentDescriptorProvider)componentDescriptorProvider { + return concreteComponentDescriptorProvider(); +} + +- (void)prepareForRecycle { + [super prepareForRecycle]; + /* + It's important to destroy the Metal Layer before releasing a view + to the recycled pool to prevent displaying outdated content from + the last usage in the new context. + */ + self.contentView = nil; +} + +- (WebGPUMetalView *)getContentView { + if (!self.contentView) { + self.contentView = [WebGPUMetalView new]; + } + return (WebGPUMetalView *)self.contentView; +} + +- (void)updateProps:(const Props::Shared &)props + oldProps:(const Props::Shared &)oldProps { + const auto &oldViewProps = + *std::static_pointer_cast(_props); + const auto &newViewProps = + *std::static_pointer_cast(props); + + if (newViewProps.contextId != oldViewProps.contextId) { + /* + The context is set only once during mounting the component + and never changes because it isn't available for users to modify. + */ + WebGPUMetalView *metalView = [WebGPUMetalView new]; + self.contentView = metalView; + [metalView setContextId:@(newViewProps.contextId)]; + [metalView configure]; + } + + [super updateProps:props oldProps:oldProps]; +} + +- (void)updateLayoutMetrics:(const LayoutMetrics &)layoutMetrics + oldLayoutMetrics:(const LayoutMetrics &)oldLayoutMetrics { + [super updateLayoutMetrics:layoutMetrics oldLayoutMetrics:oldLayoutMetrics]; + [(WebGPUMetalView *)self.contentView update]; +} + +@end + +Class WebGPUViewCls(void) { return WebGPUView.class; } + +#endif // RCT_NEW_ARCH_ENABLED diff --git a/packages/skia/cpp/rnskia/RNSkManager.cpp b/packages/skia/cpp/rnskia/RNSkManager.cpp index 3d8d91e1c3..5fc17cbd6a 100644 --- a/packages/skia/cpp/rnskia/RNSkManager.cpp +++ b/packages/skia/cpp/rnskia/RNSkManager.cpp @@ -14,6 +14,7 @@ #ifdef SK_GRAPHITE #include "RNDawnContext.h" #include "rnwgpu/api/GPU.h" +#include "rnwgpu/api/RNWebGPU.h" #include "rnwgpu/api/descriptors/GPUBufferUsage.h" #include "rnwgpu/api/descriptors/GPUColorWrite.h" #include "rnwgpu/api/descriptors/GPUMapMode.h" @@ -100,6 +101,11 @@ void RNSkManager::installBindings() { rnwgpu::GPUShaderStage::create(*_jsRuntime)); _jsRuntime->global().setProperty(*_jsRuntime, "GPUTextureUsage", rnwgpu::GPUTextureUsage::create(*_jsRuntime)); + + // Install RNWebGPU global object for WebGPU Canvas support + auto rnWebGPU = std::make_shared(gpu, nullptr); + _jsRuntime->global().setProperty(*_jsRuntime, "RNWebGPU", + rnwgpu::RNWebGPU::create(*_jsRuntime, rnWebGPU)); #endif } } // namespace RNSkia diff --git a/packages/skia/cpp/rnwgpu/Canvas.h b/packages/skia/cpp/rnwgpu/Canvas.h new file mode 100644 index 0000000000..b92aa0e9cd --- /dev/null +++ b/packages/skia/cpp/rnwgpu/Canvas.h @@ -0,0 +1,45 @@ +#pragma once + +#include + +#include "jsi2/NativeObject.h" + +namespace rnwgpu { + +namespace jsi = facebook::jsi; + +class Canvas : public NativeObject { +public: + static constexpr const char *CLASS_NAME = "Canvas"; + + Canvas(void *nativeSurface, int width, int height) + : NativeObject(CLASS_NAME), _nativeSurface(nativeSurface), _width(width), + _height(height), _clientWidth(width), _clientHeight(height) {} + + void *getNativeSurface() { return _nativeSurface; } + + int getWidth() { return _width; } + int getHeight() { return _height; } + + int getClientWidth() { return _clientWidth; } + int getClientHeight() { return _clientHeight; } + + void setClientWidth(int width) { _clientWidth = width; } + void setClientHeight(int height) { _clientHeight = height; } + + static void definePrototype(jsi::Runtime &runtime, jsi::Object &prototype) { + installGetter(runtime, prototype, "width", &Canvas::getWidth); + installGetter(runtime, prototype, "height", &Canvas::getHeight); + installGetter(runtime, prototype, "clientWidth", &Canvas::getClientWidth); + installGetter(runtime, prototype, "clientHeight", &Canvas::getClientHeight); + } + +private: + void *_nativeSurface; + int _width; + int _height; + int _clientWidth; + int _clientHeight; +}; + +} // namespace rnwgpu diff --git a/packages/skia/cpp/rnwgpu/PlatformContext.h b/packages/skia/cpp/rnwgpu/PlatformContext.h new file mode 100644 index 0000000000..988ffb5ab9 --- /dev/null +++ b/packages/skia/cpp/rnwgpu/PlatformContext.h @@ -0,0 +1,18 @@ +#pragma once + +#include + +#include "webgpu/webgpu_cpp.h" + +namespace rnwgpu { + +class PlatformContext { +public: + PlatformContext() = default; + virtual ~PlatformContext() = default; + + virtual wgpu::Surface makeSurface(wgpu::Instance instance, void *surface, + int width, int height) = 0; +}; + +} // namespace rnwgpu diff --git a/packages/skia/cpp/rnwgpu/SurfaceRegistry.h b/packages/skia/cpp/rnwgpu/SurfaceRegistry.h new file mode 100644 index 0000000000..e41de864a6 --- /dev/null +++ b/packages/skia/cpp/rnwgpu/SurfaceRegistry.h @@ -0,0 +1,229 @@ +#pragma once + +#include +#include +#include +#include + +#include "webgpu/webgpu_cpp.h" + +namespace rnwgpu { + +struct NativeInfo { + void *nativeSurface; + int width; + int height; +}; + +struct Size { + int width; + int height; +}; + +class SurfaceInfo { +public: + SurfaceInfo(wgpu::Instance gpu, int width, int height) + : gpu(std::move(gpu)), width(width), height(height) {} + + ~SurfaceInfo() { surface = nullptr; } + + void reconfigure(int newWidth, int newHeight) { + std::unique_lock lock(_mutex); + config.width = newWidth; + config.height = newHeight; + _configure(); + } + + void configure(wgpu::SurfaceConfiguration &newConfig) { + std::unique_lock lock(_mutex); + config = newConfig; + config.width = width; + config.height = height; + config.presentMode = wgpu::PresentMode::Fifo; + _configure(); + } + + void unconfigure() { + std::unique_lock lock(_mutex); + if (surface) { + surface.Unconfigure(); + } else { + texture = nullptr; + } + } + + void *switchToOffscreen() { + std::unique_lock lock(_mutex); + // We only do this if the onscreen surface is configured. + auto isConfigured = config.device != nullptr; + if (isConfigured) { + wgpu::TextureDescriptor textureDesc; + textureDesc.usage = wgpu::TextureUsage::RenderAttachment | + wgpu::TextureUsage::CopySrc | + wgpu::TextureUsage::TextureBinding; + textureDesc.format = config.format; + textureDesc.size.width = config.width; + textureDesc.size.height = config.height; + texture = config.device.CreateTexture(&textureDesc); + } + surface = nullptr; + return nativeSurface; + } + + void switchToOnscreen(void *newNativeSurface, wgpu::Surface newSurface) { + std::unique_lock lock(_mutex); + nativeSurface = newNativeSurface; + surface = std::move(newSurface); + // If we are comming from an offscreen context, we need to configure the new + // surface + if (texture != nullptr) { + config.usage = config.usage | wgpu::TextureUsage::CopyDst; + _configure(); + // We flush the offscreen texture to the onscreen one + wgpu::CommandEncoderDescriptor encoderDesc; + auto device = config.device; + wgpu::CommandEncoder encoder = device.CreateCommandEncoder(&encoderDesc); + + wgpu::TexelCopyTextureInfo sourceTexture = {}; + sourceTexture.texture = texture; + + wgpu::TexelCopyTextureInfo destinationTexture = {}; + wgpu::SurfaceTexture surfaceTexture; + surface.GetCurrentTexture(&surfaceTexture); + destinationTexture.texture = surfaceTexture.texture; + + wgpu::Extent3D size = {sourceTexture.texture.GetWidth(), + sourceTexture.texture.GetHeight(), + sourceTexture.texture.GetDepthOrArrayLayers()}; + + encoder.CopyTextureToTexture(&sourceTexture, &destinationTexture, &size); + + wgpu::CommandBuffer commands = encoder.Finish(); + wgpu::Queue queue = device.GetQueue(); + queue.Submit(1, &commands); + surface.Present(); + texture = nullptr; + } + } + + void resize(int newWidth, int newHeight) { + std::unique_lock lock(_mutex); + width = newWidth; + height = newHeight; + } + + void present() { + std::unique_lock lock(_mutex); + if (surface) { + surface.Present(); + } + } + + wgpu::Texture getCurrentTexture() { + std::shared_lock lock(_mutex); + if (surface) { + wgpu::SurfaceTexture surfaceTexture; + surface.GetCurrentTexture(&surfaceTexture); + return surfaceTexture.texture; + } else { + return texture; + } + } + + NativeInfo getNativeInfo() { + std::shared_lock lock(_mutex); + return {.nativeSurface = nativeSurface, .width = width, .height = height}; + } + + Size getSize() { + std::shared_lock lock(_mutex); + return {.width = width, .height = height}; + } + + wgpu::SurfaceConfiguration getConfig() { + std::shared_lock lock(_mutex); + return config; + } + + wgpu::Device getDevice() { + std::shared_lock lock(_mutex); + return config.device; + } + +private: + void _configure() { + if (surface) { + surface.Configure(&config); + } else { + wgpu::TextureDescriptor textureDesc; + textureDesc.format = config.format; + textureDesc.size.width = config.width; + textureDesc.size.height = config.height; + textureDesc.usage = wgpu::TextureUsage::RenderAttachment | + wgpu::TextureUsage::CopySrc | + wgpu::TextureUsage::TextureBinding; + texture = config.device.CreateTexture(&textureDesc); + } + } + + mutable std::shared_mutex _mutex; + void *nativeSurface = nullptr; + wgpu::Surface surface = nullptr; + wgpu::Texture texture = nullptr; + wgpu::Instance gpu; + wgpu::SurfaceConfiguration config; + int width; + int height; +}; + +class SurfaceRegistry { +public: + static SurfaceRegistry &getInstance() { + static SurfaceRegistry instance; + return instance; + } + + SurfaceRegistry(const SurfaceRegistry &) = delete; + SurfaceRegistry &operator=(const SurfaceRegistry &) = delete; + + std::shared_ptr getSurfaceInfo(int id) { + std::shared_lock lock(_mutex); + auto it = _registry.find(id); + if (it != _registry.end()) { + return it->second; + } + return nullptr; + } + + void removeSurfaceInfo(int id) { + std::unique_lock lock(_mutex); + _registry.erase(id); + } + + std::shared_ptr addSurfaceInfo(int id, wgpu::Instance gpu, + int width, int height) { + std::unique_lock lock(_mutex); + auto info = std::make_shared(gpu, width, height); + _registry[id] = info; + return info; + } + + std::shared_ptr + getSurfaceInfoOrCreate(int id, wgpu::Instance gpu, int width, int height) { + std::unique_lock lock(_mutex); + auto it = _registry.find(id); + if (it != _registry.end()) { + return it->second; + } + auto info = std::make_shared(gpu, width, height); + _registry[id] = info; + return info; + } + +private: + SurfaceRegistry() = default; + mutable std::shared_mutex _mutex; + std::unordered_map> _registry; +}; + +} // namespace rnwgpu diff --git a/packages/skia/cpp/rnwgpu/api/GPUCanvasContext.cpp b/packages/skia/cpp/rnwgpu/api/GPUCanvasContext.cpp new file mode 100644 index 0000000000..217d8445d3 --- /dev/null +++ b/packages/skia/cpp/rnwgpu/api/GPUCanvasContext.cpp @@ -0,0 +1,64 @@ +#include "GPUCanvasContext.h" +#include "Convertors.h" +#include + +#ifdef __APPLE__ +namespace dawn::native::metal { + +void WaitForCommandsToBeScheduled(WGPUDevice device); + +} +#endif + +namespace rnwgpu { + +void GPUCanvasContext::configure( + std::shared_ptr configuration) { + Convertor conv; + wgpu::SurfaceConfiguration surfaceConfiguration; + surfaceConfiguration.device = configuration->device->get(); + if (configuration->viewFormats.has_value()) { + if (!conv(surfaceConfiguration.viewFormats, + surfaceConfiguration.viewFormatCount, + configuration->viewFormats.value())) { + throw std::runtime_error("Error with SurfaceConfiguration"); + } + } + if (!conv(surfaceConfiguration.usage, configuration->usage) || + !conv(surfaceConfiguration.format, configuration->format)) { + throw std::runtime_error("Error with SurfaceConfiguration"); + } + +#ifdef __APPLE__ + surfaceConfiguration.alphaMode = configuration->alphaMode; +#endif + surfaceConfiguration.presentMode = wgpu::PresentMode::Fifo; + _surfaceInfo->configure(surfaceConfiguration); +} + +void GPUCanvasContext::unconfigure() {} + +std::shared_ptr GPUCanvasContext::getCurrentTexture() { + auto prevSize = _surfaceInfo->getConfig(); + auto width = _canvas->getWidth(); + auto height = _canvas->getHeight(); + auto sizeHasChanged = prevSize.width != width || prevSize.height != height; + if (sizeHasChanged) { + _surfaceInfo->reconfigure(width, height); + } + auto texture = _surfaceInfo->getCurrentTexture(); + return std::make_shared(texture, ""); +} + +void GPUCanvasContext::present() { +#ifdef __APPLE__ + dawn::native::metal::WaitForCommandsToBeScheduled( + _surfaceInfo->getDevice().Get()); +#endif + auto size = _surfaceInfo->getSize(); + _canvas->setClientWidth(size.width); + _canvas->setClientHeight(size.height); + _surfaceInfo->present(); +} + +} // namespace rnwgpu diff --git a/packages/skia/cpp/rnwgpu/api/GPUCanvasContext.h b/packages/skia/cpp/rnwgpu/api/GPUCanvasContext.h new file mode 100644 index 0000000000..b005bbbe76 --- /dev/null +++ b/packages/skia/cpp/rnwgpu/api/GPUCanvasContext.h @@ -0,0 +1,65 @@ +#pragma once + +#include +#include +#include + +#include "descriptors/Unions.h" + +#include "webgpu/webgpu_cpp.h" + +#include "jsi2/NativeObject.h" + +#include "rnwgpu/Canvas.h" +#include "GPU.h" +#include "descriptors/GPUCanvasConfiguration.h" +#include "GPUTexture.h" +#include "rnwgpu/SurfaceRegistry.h" + +namespace rnwgpu { + +namespace jsi = facebook::jsi; + +class GPUCanvasContext : public NativeObject { +public: + static constexpr const char *CLASS_NAME = "GPUCanvasContext"; + + GPUCanvasContext(std::shared_ptr gpu, int contextId, int width, + int height) + : NativeObject(CLASS_NAME), _gpu(std::move(gpu)) { + _canvas = std::make_shared(nullptr, width, height); + auto ®istry = rnwgpu::SurfaceRegistry::getInstance(); + _surfaceInfo = + registry.getSurfaceInfoOrCreate(contextId, _gpu->get(), width, height); + } + +public: + std::string getBrand() { return CLASS_NAME; } + + std::shared_ptr getCanvas() { return _canvas; } + + static void definePrototype(jsi::Runtime &runtime, jsi::Object &prototype) { + installGetter(runtime, prototype, "__brand", &GPUCanvasContext::getBrand); + installGetter(runtime, prototype, "canvas", &GPUCanvasContext::getCanvas); + installMethod(runtime, prototype, "configure", + &GPUCanvasContext::configure); + installMethod(runtime, prototype, "unconfigure", + &GPUCanvasContext::unconfigure); + installMethod(runtime, prototype, "getCurrentTexture", + &GPUCanvasContext::getCurrentTexture); + installMethod(runtime, prototype, "present", &GPUCanvasContext::present); + } + + inline const wgpu::Surface get() { return nullptr; } + void configure(std::shared_ptr configuration); + void unconfigure(); + std::shared_ptr getCurrentTexture(); + void present(); + +private: + std::shared_ptr _canvas; + std::shared_ptr _surfaceInfo; + std::shared_ptr _gpu; +}; + +} // namespace rnwgpu diff --git a/packages/skia/cpp/rnwgpu/api/RNWebGPU.h b/packages/skia/cpp/rnwgpu/api/RNWebGPU.h new file mode 100644 index 0000000000..ace53b8980 --- /dev/null +++ b/packages/skia/cpp/rnwgpu/api/RNWebGPU.h @@ -0,0 +1,62 @@ +#pragma once + +#include +#include + +#include "jsi2/NativeObject.h" + +#include "rnwgpu/Canvas.h" +#include "GPU.h" +#include "GPUCanvasContext.h" +#include "rnwgpu/PlatformContext.h" + +namespace rnwgpu { + +namespace jsi = facebook::jsi; + +class RNWebGPU : public NativeObject { +public: + static constexpr const char *CLASS_NAME = "RNWebGPU"; + + explicit RNWebGPU(std::shared_ptr gpu, + std::shared_ptr platformContext) + : NativeObject(CLASS_NAME), _gpu(gpu), _platformContext(platformContext) { + } + + std::shared_ptr getGPU() { return _gpu; } + + bool getFabric() { return true; } + + std::shared_ptr + MakeWebGPUCanvasContext(int contextId, float width, float height) { + auto ctx = + std::make_shared(_gpu, contextId, width, height); + return ctx; + } + + std::shared_ptr getNativeSurface(int contextId) { + auto ®istry = rnwgpu::SurfaceRegistry::getInstance(); + auto info = registry.getSurfaceInfo(contextId); + if (info == nullptr) { + return std::make_shared(nullptr, 0, 0); + } + auto nativeInfo = info->getNativeInfo(); + return std::make_shared(nativeInfo.nativeSurface, nativeInfo.width, + nativeInfo.height); + } + + static void definePrototype(jsi::Runtime &runtime, jsi::Object &prototype) { + installGetter(runtime, prototype, "fabric", &RNWebGPU::getFabric); + installGetter(runtime, prototype, "gpu", &RNWebGPU::getGPU); + installMethod(runtime, prototype, "getNativeSurface", + &RNWebGPU::getNativeSurface); + installMethod(runtime, prototype, "MakeWebGPUCanvasContext", + &RNWebGPU::MakeWebGPUCanvasContext); + } + +private: + std::shared_ptr _gpu; + std::shared_ptr _platformContext; +}; + +} // namespace rnwgpu diff --git a/packages/skia/cpp/rnwgpu/api/descriptors/GPUCanvasConfiguration.h b/packages/skia/cpp/rnwgpu/api/descriptors/GPUCanvasConfiguration.h new file mode 100644 index 0000000000..9cccc66767 --- /dev/null +++ b/packages/skia/cpp/rnwgpu/api/descriptors/GPUCanvasConfiguration.h @@ -0,0 +1,76 @@ +#pragma once + +#include +#include + +#include "webgpu/webgpu_cpp.h" + +#include "jsi2/JSIConverter.h" + +#include "GPUDevice.h" + +namespace jsi = facebook::jsi; + +namespace rnwgpu { + +struct GPUCanvasConfiguration { + std::shared_ptr device; // GPUDevice + wgpu::TextureFormat format; // GPUTextureFormat + std::optional usage; // GPUTextureUsageFlags + std::optional> + viewFormats; // Iterable + wgpu::CompositeAlphaMode alphaMode = wgpu::CompositeAlphaMode::Opaque; +}; + +} // namespace rnwgpu + +namespace rnwgpu { + +template <> +struct JSIConverter> { + static std::shared_ptr + fromJSI(jsi::Runtime &runtime, const jsi::Value &arg, bool outOfBounds) { + auto result = std::make_unique(); + if (!outOfBounds && arg.isObject()) { + auto value = arg.getObject(runtime); + if (value.hasProperty(runtime, "device")) { + auto prop = value.getProperty(runtime, "device"); + result->device = JSIConverter>::fromJSI( + runtime, prop, false); + } + if (value.hasProperty(runtime, "format")) { + auto prop = value.getProperty(runtime, "format"); + result->format = + JSIConverter::fromJSI(runtime, prop, false); + } + if (value.hasProperty(runtime, "usage")) { + auto prop = value.getProperty(runtime, "usage"); + result->usage = + JSIConverter>::fromJSI(runtime, prop, false); + } + if (value.hasProperty(runtime, "viewFormats")) { + auto prop = value.getProperty(runtime, "viewFormats"); + result->viewFormats = JSIConverter< + std::optional>>::fromJSI(runtime, + prop, + false); + } + if (value.hasProperty(runtime, "alphaMode")) { + auto prop = value.getProperty(runtime, "alphaMode") + .asString(runtime) + .utf8(runtime); + if (prop == "premultiplied") { + result->alphaMode = wgpu::CompositeAlphaMode::Premultiplied; + } + } + } + + return result; + } + static jsi::Value toJSI(jsi::Runtime &runtime, + std::shared_ptr arg) { + throw std::runtime_error("Invalid GPUCanvasConfiguration::toJSI()"); + } +}; + +} // namespace rnwgpu diff --git a/packages/skia/package.json b/packages/skia/package.json index 7a1521d21a..6fdec8af36 100644 --- a/packages/skia/package.json +++ b/packages/skia/package.json @@ -12,11 +12,11 @@ "skia": { "version": "m144a", "checksums": { - "android-armeabi-v7a": "8ac74b79da5f3677ad9af50230be5523fee187c8528a038e41a5072aa6188dc4", - "android-arm64-v8a": "a1182264cfaf35ef9f85d6ce71ff482b0ac291331e6a01c333adb489ce30ff88", - "android-x86": "fcb5ce82fdc1d4fb630d9f7cac400efdb18df647213c0153a3859699624ca704", - "android-x86_64": "fcb5ce82fdc1d4fb630d9f7cac400efdb18df647213c0153a3859699624ca704", - "apple-xcframeworks": "6b255da9b9a175782981552bbb95f7a2fa170831a9cc1360ee7cc161575cde31" + "android-armeabi-v7a": "e406c3e8103a2efb6a514ac91346d7f9f81adbae14dc2d0e302e84fb8c5f80f7", + "android-arm64-v8a": "75069b0f7c66ad3382553e947d583265de033cc856c394110243da098306955f", + "android-x86": "714b93a7bdf005a23699f47e6255e4e690086c52a1998c20196a46f95b709b09", + "android-x86_64": "5bd2972d13293b09b35e2c0149b7d103dc4fb0f2837c3dd169ce06795b812714", + "apple-xcframeworks": "76b4eb044ec7dd4ca9c9c19cbbe07c4819cc3dd5dd142aca3a4ea5de01ba7501" } }, "skia-graphite": { @@ -160,7 +160,8 @@ }, "ios": { "componentProvider": { - "SkiaPictureView": "SkiaPictureView" + "SkiaPictureView": "SkiaPictureView", + "WebGPUView": "WebGPUView" } } }, diff --git a/packages/skia/src/__tests__/snapshots/text/text-path-arabic-component-node.png b/packages/skia/src/__tests__/snapshots/text/text-path-arabic-component-node.png new file mode 100644 index 0000000000000000000000000000000000000000..62c7ba318361d90a1cc1144d54059e66dc07230b GIT binary patch literal 31071 zcmeFZXIzhc{672*g$kuo(MG9MB%(=*glG>98kCUsE=n||X*IN@EiLV&jnbgB7wx_G z|2VJT>v!MJ?#K6ozXz9b)!BKTpZ7T4$8o&B-q#f`?xNgJNg|PUU6PkoCXu${k6TGQ zDDYeGW72c{MrNgaQHGRO$1;q+Y_pQNq`CvYoOc*`kw_e*OS0!w?Zd}99dxcPZ*HH` z=+izx&wPPvui?uJOnh1~+=oPhjZ=;<*i`ye3V&s)EDpH;Y1dOGqfgYv{`Z(U{pH_R z2gzndcC+hG)Q@*5+leoB%{of4NwU?ghOeHPypb2NcqXdi3e7e$S>o5BofYMZkGzOq zbI-_0wD=YHCjqKK~TTEvx56PTAU!nNSOFo@Q;=n_NuIu|rG|bF9 z-Q3(h=jGk{TN`>rEh(fmk(PE?%_4&iC7`xG+pOi`@{F;)lT)no@(f=9u2!MY3#7p`}NtY6L)sAu&|&$ zMbBhMMn-DazxAsAnL&krU=H{5qfXJvyihzoHkLB;xw%<2MZbiN^fSv;<<;A_{eLp= zw0<(C`uF{{M_gQ-b3H8+lh^yJZ$~(sxVXMn{`b@C5>*l&PWQ=?&VCCMP%5y!A6hlu zU83(A81?$K_q%r-YjaK4W_Y$Ioj!fKXLYjVSyWWi^G`fn!uN=}Slz=SW-Y%lsh+C+ z<@@(5!><^H^llC}#?OrZ{CRzCzD1urN8Dw_+K*jYs++7rR#v(6zn`h#=qQ$R?+;gZ zUHax`TecZ3Gc#}ZzHQN^w#gdl&v8RBMm0g&-^0ABmmbm_!()cLdd1{fyxNkctMd6X z<2Ewf>enYb>3o_e9+7RepS~tr{@-=4c5SRWEsTBnWc=;n=7tOIZ3hme;?;3OpN_);s1NgjQrwH%{^l~ zrimA6R;0_tW%xfo#3wu3COSaCcE4ulJA`sCzdu=C)E@WD##vE`|rKI6S>>GBlco|;1rXYnb}xp0i*u`(aJ)H z*{M#uZeCV8oD=?`thQF+*`K|%%6GBA@W?8dbc+x zYh2@GJ8;1FM(%^?dw)KCxREQEq?Y`?%Fo-&Z#&V^gf($8<#@9%!o#WY6SMC9*{i6i z$nx{DY#iDD(+rRQe|AN_pT3MjQ|;y@oM+Bxjj4Kh$x{&tr}Q}IL8lLr#$b8ouR(&0 ztgLpa7UKGdJ~K13Nz?mXf_jBJsHmtqid_zb@@wo97vSP*Bt;S5S^S(``Z+GT#eCmj zTY+7AD=(V#Q{tk3r+dC^y%HhDAZp%4FV4_#|Ia76TTUBm%kq~l(F(BR3M_c67zr5} znPYYnI#|@74gz%PTNheka~K)c(i7j z2Dc7-{o7bysoxjO?y9`sBQLQC4>7B=JDIiDQ_QzjjT7xx3g!e9M+C zhvpBxll9*F(9*KjZnHJRaQ@BzdyCEK`qJGlIBz+8@!^vvUika_*M3GktgWyA&!apC zUTF}2bL#$^NjV|Xlc!G=MtDn~vAcet&&(|kjUkWNrfB0}jX@<6`irp>cBP%20GsITI3}WdAz-w?|XsGAw6LqL8$k-p8E85A_4n_64<0=DpqB-^0sBupAzdGE^E5@bmM}jr^i=Tbq6+VT(50k#9paKia~0Qq*N- z>g%3R1GLVV0h!I<;9!r^(z9c&8L_3I$=+V7=(@tp-rnAn?GqCdOQY!}5Bn>3Aw+4d z{(b+i?9Y#=$zHf%fb=Cj8X7XOCFdief|ivP<@7-hlE@$-)^5B#SHnl{!UdloU(F=d z#2EU^3JQAu9!dSZi(yp)~25Q zJ`DU%_X%j<9B<2>;kr3L^2>gGCA-V&6vZAki5Huzo#MU94KZ?5@voZm{S)~}rx`xj z69oXsU^yow@&ba5IL_$_&kfOTXAjH2wG8%!d3k3PLixx^pDp^I%H(paxJ`BqcNRLF z=sWiNOHKW*;h~u;Nit zwUMT#X7y(3-Jg90pE5Hu?57PXy0|TxL&sn^u z`>XiNPniY8x^_0DmX;RfD!YXJqmyR8OaJ^~21ZM6 z96dwz;;uu1qfW6i^PReI^n>H4&z#|{aQE;ye3I3qtDhYyIX~YgD1a$RBYiiD5o&3zp^}o4*YoEW`YZkAeq7a8wK;J~LBTyDBI3xh z{8d*uQR!SSc~<8wXSu(2bg%%@g_@gp6*A)w6+;cN-R<{{YeRVXwu|kZnj2P$Z$+~{ zWVe`0hTOZ9@T3eSR zR;nF><|abwcbkgpC!<}yp$gp5)$``Dz>P|B{0f< zFYRNL@R+^|Uqj^M((+&w!*2?EGo$if})F{(Pt{JGs_nb#b!A zNy@;|!a~W1Rnk#4L}xA)QT?LEh?01v3U|2=Wel|ZN&+A}cH%@6zSL=Ez`OCNxvZ)P zGUZU{QLViy@2{M@ckk$PmNV|11$GCI9;L>8mm`jUrs;~)^H=I`mf?H9zSMV3wCu)B zya)?>zZhQL_{sQkyyo@mFAk}bht(LFbmnKvj14y>*sm>Rn4GyJ=c=2!U&Q3yqE5N( zSnKiT)EkVx`vmriGjPRL@^c8AswJtO!%OPv@88PE$f$YahHpfW(nv>MX06uEy?gi0 zjK96-!>5)McdUuNi`q-dZKKfS%&-btQmBFQ+g%FO4lRB5$%+wTj`ea^cof6WE>3h# zBdR*`tS*jOd-?4Lq;X8&Beg_2c){;_p84v+xMTgrE3D$Ssy-2?EoAVbuKs$YvX7Mi zvRji%&FsXhq^5*xz@}_7JkOPH_=n54qw6b0FD)&7@H6i&)>Za6r*?IFzSH7^OLLdh z=jn&Ocx*>3RGuEFp$jd!fxg1WbLN;FPVR!G$~rB{TLuRPZvJ?4a>ve{4Z{wUWfi4!lO>xQ zD$I7)*3C|W2J#9DW$bQi(e%;)f_f#c0t$+^*&ek53u;t8C3B z>L}NhMCCD*R58gxlm%j_LmxVyFv#nbbZ%}%oBF7vBr7K;Cwj_uROmTN#q%%pAFHM7 zNfr%qJ;fmNuOQ$WnOAcaao4FBXqd#TKh(N>`SJy?|LD~>B9DuTie$#>r8k?k>|VVU zH8&`GvXk_PP112_fW=d(*x4aIk!L=esl%O|s^{-ta%pMl<}}>{2%Vtv&%R4b_My`l zokk@Yj}M4$kUct--$^@6iL>V0tJbMcx(P5I#7v`2ZwuayHo_O!2$P9 zOzggP?OJM7?2#EMG9Pq=Z`w4`(b1Icblg`;QC6ngnjvVLAPf zqkBEyb>xCkEfErd&T|bHnZ#{VYF(69JW}qe-PE=AXe)9OU6|;kD$E=DQLsO~I5B_9 z+0J&KZfmZ2RPE$=Z7BcohdpN{9OvW{1{s^s^g|7P|Ngx+6dM3|7iC~z@Nl9d&v|kC z_U#8nMK#jT(7vVwTvRnGa#~bp-UB3|sQA2VmevE%ps`{Jl__gwBTB-7sAeSd+b&Ak z6pxE>2)evsK|wK@v#b*KG@bc2-|RNibPI?x40hi80yQ7;%~#Rc(Q!RScBhhMW5VLD zl&Dkp_iI@5DAR2Y;@Pq>Apv73psximw%%z8QBBcQGF9sVs3J5C0;!pB%xE57@yD(e|bS>q1irUJXk zO1$H_NV>p8Vn&d={onyXJS27GBCmj#!xqNd`6~qVi&H{#h{w}+T_(5Bq&PoV7m?kV z_WnQAf_W(KcRi-U#}7L585}EG82HtR_}8vKe`Wb98J{OvX#ks~a$c?d*|Vg&@H1Q4 z+1UXzy@TFn9M3L$MWAHb#CWroG`<8+oqX%W#u&+b8aB4H*}TQ>sy~0Uc=v&F2+dg> z`{VKC$+n&!a@YQRGA4ey>iYNWA_`e_e$+YkhZpCmfyb#lqjK}|qZhb*dL5h-g z)8qa3_phh%x3EN=0QZoc?vH-F6(v9;9giZtIIHk63<~lBxaV>}^w2)QVlj4V=h5E+ z=(YxpahJp->sMR<{Q2_hml|h|+or4k1gr3|FNY9 zal|C;DzSk^!BukV#0fg-wJDDpzw&3eBV*%R zK*mGeCDK7bK{R{!8VGL+{WsPHw&mMRrU@4tf7`di{axm4anWg8OUuSTXDGj7+%eUz zL+bf6CW)bjC`L)`A`LYs(v7sFrz<(Nsix_i0Z($IJWGpoRKJ)-+-^d3b^b=qy@oaw zri{e>*9;5|V=Y;p@?v6A&P(%3;&~8v6gNxsotrn`Ni2L5Dk(*xH5XQYB&h1_lXsit z|8o2Qf;CGOa@Mn(?5emXy}pg9I%4|24*#IzbF|W1pzRqqyYV))*c|KL{s3w9*5B%6 z57$?0u0%>`_1kVN_3ud?ILLjDMpg0ga9^Ln45MXBy8gv`_flk1u0=`lRYkps85_HI z!!lihN7_Df{HUqgMm-==jR{mtBc9u^K!b3f;vC7Zy4B%lO)o`Y)1YI z7~8Q|%45OTq-YN_8d?thu;9(%&YlU}&>@yQ>@ zQI{`=9aZwGF%l*Mhd5}|9gB@MhwrbB$NuE!98IEnQ`}Ktcg?t?If3K?=%UPtDbmGb z|8_$!Wfhgs{QCKcPVw$(E(~0nIro@BG;Sk3w6^|k=V>Q=l}I(iuC6Y=evnbWMjX0| zPPC?Iok-0|-FfliMbB}!jpd8u3G5D0Z1gsKS6r%{s=CX{WMUUU(4-xkAR}$8j0*X& zoY|X`lLMsa9vn>f{#w*?jH>aETaru)mYQ=>(USaHlGH9w<_$H)Uw#>4An7=F7T`^; zrb?4&oTmR$Fv^Bjy^o8#iR@-NaobPg6v#nMEv-a}4NNgRsHrht9>Sm!7#8*v_@fv6 z40qm^T-7NzdRo&I38?R0~L7g z+_~i(Crq*!ftki1{c+n|*Wms4@89hg*Pdiu`bDky^w{sJ7dzeGS^i7GC1XGxPR-BD z+1j3BlXmsP-w3jKh9}YfM7))yr7&{T6H`Us-)}GNr~5qDWHy(k`@vv+Df6TXjEqcs z_#CIi!N*r?vKe)W8NIvF2XH_qkyQG&U_sw`+Ou-JyU;;J>PX{{AG<1inCrG)v9hwV zcW~gPCyhvvRo@_CLfM*nBlq{|i}(37(!$Gfxclh|rbD;DwkEd#bOl}^#!*hfwQTs#@v2Wi# zP0ZGhOQr>gqe4w_{FpKw9oM$XZ>QR$VTgYjR!PBz9JqisT+P^+93EWLeK zbyvr~xu{7E)cU#cb`A5v%&e?(K;Y%fh~EKG#XI-iR)!OZ_C*Ze=&_u_!USFs6K5YLNX*7JnEVpQ zE^A+x9xto@@k33M<%9KbE1z z#i7H8YjQI`eQJJinQ<>2-Eo@{RnJ%Xc2Tpd{rhQX-i4;A%FQD=-rcE>M4?b^!$d6V zFG!)vKmrBEZz=vONlnEk`+mFncwzbbk-?PY$2}kqFbXI+?u|7+e*CzXx3`j)gQFu~ z>X~!Pn0OBmd4e|cwW?}6ZubJ95~wHX9+c}=U|7ewA*G=ORJpX7;r*{Eh@PWHj0BB^ zOZJ&wFY{-1|GT27s9qp&|MInKRmf{vcJ_3d+^j6sWJxC{r_gEe&rp~6cLgOb@$>VO$+npNcQw9`>O!&Q7&x2|gZ$5QY;<%U zLd8p4^z`&J^DN_kw+m6Kt#9h;>dMtry!!L!&n*NAakBs-{yjZ6i4KlOc?u#a-+Ea2 zgYCYfnvcMr)lC_e{rAo>KMFXgZyq z%YEe)$jk)3N&<_`&aa+w-M+}f zW9u6c(->5w+V9`X!Mlg_wS_P9iHb6otS=l04-fxn)*=XO^+D&yjVRS0jz-@*KU1sW zj*lUnofq5N+YcT(v<;(6Pen;09VpYfKNDP7LkNoB>$Gz`?O2w7?((b1@iXu^<{R`fG7_ABBSz2f}p9US8)DdN;@H6Jf zSj^SGTfXq_R z9Rf4X=cxC-mLR)U=FUY)xe&zG4tEl0f2H4a9Mc4xjTq`I$WYP zx0y9rwlcsFm6``7GG2u4TUU`&U_^xOKn@~eD~`ZZQ&x7{J|Vpni%8GVkdP-J5!k>O zlIyLt|M_DoVdv15x3H^*7|SOo(=Eh-5BB?WUa$D_g-qXNK2*KESyb%=$y6+o^VF$* zl1>Y%pO^GA3_Q>2to2`2iqOcs{X@3KQ=X4VNJVIi{67w`Bh5hoB>jp^Di}F&`#X^; zzpiFnM;**?UbaNc^+C9?pPUB5_+?MthLigG_3QcAQ`WaI+hXu3{GCr};*?Ye@sW9e z%R+Z4+z*AF$@x|u}lQ4 z=H2YjZl6q$d1a09m$UOvoxOdV8-|!;D9Fu8YE%ejb3)qM4d)S`5 zeR}|3(~zXbubQmBOI=<4h{}8FsoN9Fm?$M2X0|O(c30t$Xdw6Ce)^$3-Yx#R`KQn! z^S6c>)CwW+t*U9s@67bw)=y&Qe&3)_;(6R*#)uGAF<&Z;&Vz8O{CMl@6$6T3y!a#c z+FM&cNHT8V>@#kD*|NNVaJ`Os!QZO+l$z)^5!UnPWj#3-B;sU^+HmnFpn;EkpL9X> z%5K|_bJdBL5LBbfLdhT@{)9WnJG6)yvI4XfLOp8avY)g90U%=X^K3EHjH#t* zLy!GStG}PKiuVi-CeYmY{4n~Qknlw#KI+LZQsB-!r$xca0QLX`A>a6AdHGV%UJM4P zpJ#I)boPvl_(1O(Ij+*VveX~Yi@)O8&wB8XkYSaOb{c@i1ny{xpgdJ%nKsEXUpF;2 zCJ4)=<>gyQZrl(Rcf0@YJ(^Y|Iag;yaL~6w@bo^@}A?+j_^wj@t6YMHhCuNv)1$a^+eqPUxm+ zX2@{f_S)(;{jbJEUfxUQ3U}~pom@eb5K)%GC!tdk+9( zbxlo!nq$}LA3dz=G{bH zEIiE_;jp-wBSw`5z>=&ZT6X=}a-ufP&x#5{tdH{|Ck5^%tU#mp*$}?K$-FRSWq0LB z(etZciN0}OX`?^gFGFr$4%}+)<5#SVP zH~#IILfIh*0+j~<0TVcZ-(fGqKqu8AYDX+=75lTN)2J8)O+wxZ8r{Clch#?FVBiU6 zH=i)Nz-HKv0>eNIP=c-(GusT1-Z*>rE?@0Sq4Z3vAqBK>BA!5JWZyomRDl@^dc{K< zn+jyIMPK<&XzPUS0OR(zMH_S)Inc$-c>DDmlHlk>mV0CWs*AD=qyFUh=dUCPd-iCwKKS$L z@EcKcL2W5n__Hw)FKTzpF)$B#f$~%xKh-4~ ztB#=pwZWK1Wv8^;1`D*E0+}&iq2iw_bmzGEm>@!4LPnp*Oh5JKP87qEi4LQsmDOzL z;OMCDrC{z`Q$1hy3v@xtcXi0!$0huLpa6&FJ()!cE&nPIj;cA+b3(fLam{kdofdm! zzHl7!>8#xW zp$&Q#bd-GN1Yj@CLglTK=%wNnizGywX<;5!_{JSf8QfooY z!h^FDx;8{~P7V$dVWq&R^9X!fG$=BK%>SbIn$`3ST{v7k}jV?pj0@Fm8bng;wnIx@DZh#dA1GHb2H|~n zJJ;|661jyS7h~Pl0+S~UPBpnzXxtdp6Fc?N^@@7_{d_(*gYU%54sH*>HJgbFMtoB z&o5uSDhJ66YI`(IH@tq%Wi*MsBJYf{aKz6s^hEvf**0mz644t*Uo+5k9H9QzvavX1H$Hl zjLa5-s1&K+ENIKQpFF3kev|!;u43j3{ga7+m(e&!5bNL&eva;wQ9v)rDy$C1AXO!}rrl!0kn#$*_{I+6oPce58 zFM+be5ZV*()X8rzg)~mPf~0c%*76h0kNGg9Vxo4zh^6`Q=DEjJZ~n)hHq?|5AhVWU zveBsJDmUDI7i|#MoSTp(O+XITS#oii5*7)Bc81HUEyNJ7i02)E+k_)Iqp1{c?ihHV zWs&b7R2(CAhh`m=lF~DEiNfT{D?wYGjM_xmt~^0rzvYpiGQdwmvW8I4kG+eq{(f6* z#cjqy8&PoCblqIHi&!5_2cJv3 z3Ynk0dqH$!C*`{4$ulr-;xOq>3i0KG+YX&3+e*;`=813dPkTE*eFeN=zqDMR!bZuQ zYNt``yx6ya_D(=qLQq3Xql28OG4j<%H1oQN@Qun<_|Ef7*98RyA$7A8Zh}k}FZnh| zg8|6=Tc`sMA3mfx{0y*?Nw#DY7#^-wrN69wNMGL|xc33HRp3+4fr%W8o&Mugu{Xv14R9SAA_asn5~YLGuX6uVhI1kY9*2|LgJ z5QR6f4AvUnl?rJRoV%RexC|kiz)AZ9;&3m@iQv>LG=_KQpY6s_^c8mLW4FIEEvq~R zuDZ0)#~w}*;uisJ3IulS!szVi`45R`1a6 zXcbC}1%Os|TUKV~c{JgkzP>I0sx88}`!aK#JD@c7QpO_5@qzp;k_;FQ) zl*@j!yfE`U2ToCgjcGdn^r>&jv{5tIw)lq8C`qUH**aaJ-RyL@p!0MEqu3c9S|ueY z*Ub3pV0~&yAQ@0x_A7I|Xpm14ip#;jaz}$e4aMr@Ssuack&>FKl&XD_uv;7hBRXF+ zFo;l`l)O-D=kDJL=y4rl1oeSaDWwUM=JP`hTctPGGQVsTk5HjF-wg{3+h0`tLH8*o zf62yX)BCIEar!ovidtH48QRt5gdq5+xwhRi$Hh?*?Dv2+l< zHE7ZTn!W7Jn;ZlJZds!y@W9&D%TLH3ZG)%bOHIvA_}L8-45rH2-&~7( zkM!C`PM$d5hF;i9n0O+#o}S!(z3MrujjbRSK=jXvN* zB%hw~@nb1mddG2pgh+BHkL)b`MhrPr+KlkETPFatEl-$r7Z>SSaSCq(JULS2yu25c z{AhCqa?TxW4+v|bf5H%;HMrdS!$6;)PME*}&08WNSKP>LrhD&>9g-uyITfvk=USv{ zo;j#r0uVr{gQWi$R+(=J=}kPS#2~=v0maBkU}o7c^gMylu*-^*E9jH^ZNC%QS^-{^ z9)_f9jUJ(23(1n$Z)&P;U&ioFffBocP4l-n?Dy85Yy1m z@O&VRLjFq1#qlveIbGoNx9aM%nwm`N>3aS+fsCfWLR7UxKh)U+6+XlNl#gHxCJ2*m zw@rUc9UM|pZ0;OG13I#D*oC34g)XWD1J#w+!sLJyGfQyc9luq!%~N~?(`I(k^UR|X z0BuCw3$%#q+Vn-8B1bjsB{W-N_X9pxN^pV1S%eAd^4ThEBdqj% z{b^}w+R`mRgU8H%AB6>-4x-Fi6wseQA;e$7%z^nd!*$(}dcTM~ zjChoX#l;Vxd{+Q*5v;DK3xLOkvu7Wf9YB5mlT!xeJ3zO= zVHtX@#hbbl5HiD}{{kE~F=$E(jGMN$wgfA0vfQu<9ZSP!7qhTzGUFyl zGf@nHGhL{`7%R&miuD3m0{Eu>J*%pTu;l=gd6j>B$kJHO4yhZ z4MOhQx9jB<6}^}ygUq3Vc)i)9o`M=@l@J5_q>5T7&HrEb)mxe z)MWPDAkS@63MPaK#n`hBs~y)O#MI2_F5ngj;Jp9G)G5PCY6!nCuX$cFM}<1~)4C@O zYzY=BW?6@fcR-cCT_2g6HLwH95NiRgAi)DrlT|nuzHDdr3ft3g!<_@VKP9;S zvtSvfDj4;9fa%DK-@~5T3d=VLYd@I6hXph;u(;I&`i8KJP0jqhoYADjD=Enexgg9O zI%9uky;PI-D(Hh}MA-qRzsqy_G!y)np8-dHTOO=^dDe(Tpe3?LZTc8l_pS=iw;|I* zW`K(r`}+GU6t7OgY?d%H$jrtjXnXh2EeK7FK&+ndWH64*R>5WS>ZDm1HtKkd?%eT> zDDGOvPS_UGm-_l^_OQ6N4j(z~vXb>PQH94dss;GU#K@Za$g({}2fT6A--2-iSR6_kizg-KYOHSFP}Zyg@K3V#x~h1fY4M3fJK zZfzY8og?;v{?$eBL)h3iGJ6LsL>V~o!-e+KGGonhp^=e-gx!(Ef%%LIS~jEjVb0^n zl^}$DYOKEpjo9%=KSl&NE$MvLa<6g+?<9P~W@(265K8aD#qAWav2-+_ z@kyH)D`&V2v3z8Z@E*mhkOnhhXjci|9}K|UxGPS~^<}81s{8&X6{E;|0vS>fAYRB!jAS%yYi`@5rAxRNw}8#3J*+Pb zx~IAaRY4UCjz*8!eV~HAZ8g1nrM6Qat@Hg{@c|JNj+zJ84@DB%ac9K+-zl#NOGYnJ zz*$V~5xNDh#IFOwMqUrWrbk4HVum=4U604o-%x+3FhMps2$I8xwilsx6sBXw#2tif z$Zb-7l!)ruy1IR+;t`YE`v^>C>!UqAp4-h=l#71)daknq?BfULj?{0id9q0#R&=w5O zy_1xXcoG+PC^b@_4s#F<7{KdsTm(HRqplv-nix#1V^fS{b;~_IKE8HOxtG_DjHaem zh_7lJ)B9moxU`$w&)b_80&ZU!iZ_@cHdOnItb)3ewhd zZq7PGg@^7I_YQZCg)6eMo{2#ZEgW5rRho3O$#$UK`hrEyb%7;>2bsr3JVFV*e&yA#|^RXiyq#U|c9q z@ade-Fwog|u^ngV0T$BNasoGN2$}5v&Ul(QFN57nx2B7WlGmCsf6qP zZwAOTDD7ocRaHHkUPad)K0Jm+%~%>UFpoGK>V*lG*Ts|!eD6?Tomb)x5(vPPlHnm7 zenk;Y0FrnHVy71@+`O%x4MvYI4GpyT;bjohsOI0m3k!EI!JC4z5UUULnE-hYp8X`@ zw!j|`g1#cQL;U^a;E=`aMJ#RYJ*?ohuo!WTRQ=&zcQGp%w>%kG6v%+%83lOmU%Gtx zJgAJ24b3_jMbHx&`33y3`$LCuQeIIptO`WG1(pYb?eovcF4JuzL%aQo&7s()|E4EM zBTQ1xrvX!}9n;F-j4wq4e>N~+gtm3?wT{G_Glc#PVbZUzi;CeY7PgAl7jCSr&DML06@x$o!NYm?cZxUW8p25cJQ?Pu z_TlxM3P*xVYA9e*7S$fa&$c?$Nk)%yhR<9Y1DfHeFiv41D#<3z{MZB67_1 zUo#A=h~?ReRo2iceEsen(+pVbM-!8g$Pu;9bkt`m4C{QBk=PEpFbtx^1RGM$;+TjLh%_g8?&G%EiZ@owJT<{#si*0f zig+;KF};D@kCYRT2{A(m7%_k4WcyHkN+BnFG;QL}*6RjY0(an-&Q4Z#m$|^-vrbVk zw1uCxAiByI3dWMHh=?yuqbfWG}1CB#LC4<4^v(@142VI5Uc&D6# zf{OfugyoXhdF+_?Czz02l_j!L;*ih{d?JE=qjMX;Qw_|LDYFK&L+po}I531IC0>P1 zDFbG9=zBhI4$yiF@$&8@Y{%g6u`clf=efDDx(8N7S#|Y&h}`QC`q9;6z(as2IST`V z>}YosQU}xit==-v)2?gwfqMMGHH3@}AaanG_mXMt9bLFYz7W`GI3ddNMFH8~ZDin3 zJ_EyHcLty@fY5)Dj;EoPN4H_cz7#{oad1%C50U^zVo%g(%!G7H?hcaIQj>om{FUKm6#BPxj)$WtJL~KB;LwULsC@Z^hnUCK_$_dc zGviPJv0$Xp9G*1}pbRkMFEfVltpaGcUTAO8FvC|3(U#zDX~YR#(RS>JwxX=8-27DU zd3?imte~m24fggDD+ST0v>!CmBh~ZUAvY7V8mJLsJ%)yb#SdDpe>*t|Z-Z!E(7z~F zb3G`-po^mu5!?lqruXM!`Ni)y00i+#0?P|%Wg+i(oFq?HPc75XcZsK2MHCTyV1p%} zJjO=w1_SNyMK06PUOJCNCd7O^kHdGoRA^f6AX2eSm^#ZsEGdq+odol52ww2C)jz+= z`}wd;wtl=tp!%ank7fn&F!Ny1ElX;7fDQ|xwYeok$Aab=^DmAH&N-&z2HW5y<_W+; zeIE=XA5;>af5=M=f-eOsJ_qz;wExN&Ip5Pv{$74E_`rgHKi)pWv)3A)I(3RLRuOHw zp^{_Z-@jVl#{hi%YvU@_&*D;7IZPYCG-?liUol8z#npAE4AHME41zsu2*aEGx-IWxh$Nw_GJciA?D zaDQD-<>o5|`yWEA=wh^DJk0I_LH#5qoOGJEVm5@?KsyzuAF zjPE8AyBAyn3X13u#!78mJ6JC+KAv#q zU|o|&JXD5i*Df{Y`X4`jISH z1&$a{MkQ|&?eTvG)W!suGl#m-xY~{ds#AdElGHf?DA%c+Wojwo@ zn+HKXX%^TD>}HeLQONs{h@pC^RX@g!y;VGv!nE#VFMX@|@6;fj~vuIFDSRe>N zuN(;WF)rX8x|cRkDbHb+8$e8;WNG^&WKwV*eg|z93z*tk;wFun;Cc1!ssG;Y!ot4_ z=?oGL;lV$Kl9{5Dw-zG3m*(e(w^Zj&lmYi;c8VXI z_%4va|5n$o^CSf|6Ai2z*S_SmKPV6YHVtmdBk_F#rAD9kFBOoZ0ek!5b>x4zNtQz& zVxRNP*`usl)Es_U&YKXv7geaX?b$S{tt7UJ=phUGf`dH7KdH43HO=Ro2gUux<)pc$ z`Q1NY!YG)m3IXEM* zg`-MQa=w{WYP0dOkQ@Yi;f-erkSuBSQ~C89oIy)BpiZ(*Gy&-GIc@LhV{w^lu=u)5 zlwQJhDEgTJ_}DWMJKu5TO%|^jU^4g2VYTmh41-;A_zzVE;`^~`KZOsWxD@X2@AYx} zsUA&qzb~`Ii9y&aZ@9?LiU6t`PN64W2b@0^U&tB99uhhfaXSWI+{u~W_P_Jkje2tU za+uMWWUT@CA;?kb23v>TCVYuQXVhzWch1Ah>y@;dD|#nS%Rw^L9T-UiZkQKkS1$T{h0eF=IdTUKY60m4)#eBct>}c>_WAlSPZdr`QkkkoX>$=%}d{jz&uefB;o#mR_XJDYy+P|K$$rrmGg9AQ=kGElS?S^&tZVmJT0kzg)9L zRhDYsQ7_!=gxHc;Z2Fz z?Tg*LPPI`PS)w%w?7 zau|Iwg*D`I5p)$871+VsyM((e{K;e6&M}yidqf6VYJf+qTagI;1$^BhHXY#B zF>KiBG+D$jVck!Uw@n~TBK+ZLmOrZbkpr|HEBGisG$n>Vb|CveJwLIG>V0MS94H$< zrKlr7R~erGMQqgaPvnoL?H%tfurtpU*(5MSIb56l)dvH<&mSS3$wn+ARX4|1r#{{X z`1Zyj^MGyCO7nfPR=>G+Esxdr6D^71I+7?Bk7$AUpb8XX|24N26&8zfTF-?%JhdST z^xu_Y)OLR_FIa#-;|}%`1!cBQTxetJnRJNBCgzbs4sBA;+b+k^RBQ?SJry-O?luj0 z;tR3%nvO*UgIuI|?-M!$JkoUO);;B5oAgHv1DH>6gC^Bh3|8KUGfCFUyuG%NTjCFW zQnti(oiayA=kv#M_K?dXRni+4BB0A*$yOUs^nQH`9;egG1Ht|AFZK8uHt-0(@PFKK z79{Z{fc`UI%)`>2aB`;VDTtoF;A6|T?vc1YkOzj0a0|w|ZEiF`2)2h~FV`u0eu2oH z4V+I%e|bn4>BFIgE~iQ2P^{4sZnpc2c4?-GPP7@n)Qv&grKPp_CXh?7{Y_NmH`bwv z!_UGvswyqiqJw=liiT)f`jLO&mDeZw}09!fSmm!!C zp;kOn_7HGj78cu8CqqX^ciE}KI0&Wm5bTib@Qv2YpN{7y@dYB4D)`e2m8VV%2?^o< z>8DLj`|7U&VqrvMhI#aRt7Q;&T8`gu%R1ffccSmP_{5Q4W*hf_ErMsMg zzJmE5R428VCwCVjKnb+eVcUMc0aVTDxu56z!>#Ig=Y=>J&SkI7=qWz+V@BGCBj`{V zZCh{QQ(o3A3qqIir2Qc(irzpo7oBY=8xICZ>>UiZQp{tKF3$f0`25vipgJ(#bsWu! z5z7=_>}x&S|DM`IQu~I)VZ_eZ)b7PUA8(y^UM%ST(RPJF2`>xlNP?&?2jCQOP1NrO zvHy8(=36Y3d?j$(0M?4$le-=Q16D)WmTVHs<6~<$+@4x zE=%dChJH-P%bvNBY=_W__-&(_-N-SR>&}g~2>n-!T$TdTrC97>kH_(RW)gj%vo`ax zx34=)XSQ#s9J&ABl1Zc2Auoa#U+o z!)@jmD-N%0>dH+==27nB z-0bGTR1I>JRK5Qy1m43x$B-p#OZiFym*FF(_M;nhO$2??e~VU#>wRo=RvO;_NTDY+ zx2vtU^8vf#P&6!7W_iVfXwiMGh5-Vz_3nR7*OsPX|9PtuKz8@t;uJMs#f8^(sj9mXZqP8nm_}i3$H4{S0(n=6?|g%V5!IsrOlbpRZ6|?G^EF zLL>$q1Z9TCOYG)<=;+Qxieub=6z(ei3DCRzM7>1+TQ`z|F}j&RgDZ4xKM*TM&XGPh ziT)1#PlkQN>{k*4M!Ep(gGm69ADI4i@)q2If@j#Kd^$-m*>BwUIh08#*`=-HK=Ie@+;&T?eoGya4 z@?C$w3Od!7O7Js>xA<1vR;Op$VdtL5+xudC1>1TR$Px$pQDI%5dF@;9PkveZq+)*Sd6L|n89af|qzb$jKuI-=0_z)8s zpgRkg+<1v*S+YKE{_TDm7Sv)oo`+rnFwp=awRl?(N6=B?=i?%xISzvZJ_;n&n?w}` zJQ#l%rN2I+!5k3{f8jJhdll_PmcWKZZ!b7w&q+X9B6^hO2;HLy%MOdGP?Hj@%vAwE zhfF(I8l(4HjHc%9Yx|A*xL5bc`c)7#z6ha8NMvkicLBkQVx|dqlCP8$I?qPsqG3!w zlV0P*N;wl;yFO4O#k8|bXuDUt7XMFsSN=|Q-oHOuo)$BeU4>?78Ao_f*=ZUw(P$yE zPb5i)P?ljFPjfY6m#dJnl$nMQSqfRsG=n4SG%A&(4hMyF>{-9}%lG*szSs5b7jeb; ze9rsxe&4VAzF*7n({uAITUmCV6vgbIhjGW7BYo&uu7Af#@U+h?;^E%uyzPN36$-%EX&$T<%s_Bk5Zwzp^$5wPh zZ!d+q%LBfx`oon|jV|-zlP~=b+%ldmKwTnAEjQr#sJ5pt*|XTA6`gIns_7ntPaS;R zLw`Sw|8z=N+nKELOE(E=CN!NBbrWeF}LQI zg>{Tn8;Fw|vTOP;vtR}KHfivVvwx3>Aoyt3?vg_prrH>Lj~xtJrB{#}K{%8Rp<<%| ze=1RxI-#q@u#ynFxHU82z;}gk=T4kWKaC-J`>9Cn?|WF?#>2<0NT3{V2X+t}0Hq_X@?}sJY?$h-O0kp-qa`MIgBy z14SiOM?`^|wKFv9U?ERI5D?1b{0s|Y7XZ_iKW7#rD~3bZ*uVezzg=r0`e6m$U;{TA z`>W2Ov|$4fD-Kq(Oz?X^U>wf5K3w{g!pW>2tlkKuV^V+ReBi6#Z5y<`Qxj8InX|LA zItcpw^1gJHXGw3lkD2UL)OqpSx%204Nf%O31e?%ZpQduj2*+{i?E#K`|5oR1sb}_7 zVy#H*xsO#5PMyRe)1oi$!2HuqrLTVQ+MA^6g2_y?;{}{pP(dCte6D|li`cnTS8DpL zKDb;68gGJZ89@H$jo#l*|HUz>!SAd_T#j&6zw)myzJp4QM$&WjM8NICs$)+fzro z6=O8M5;|SC>a+Yqibf#HCOi7=D-5iGm~%!UpO%;Z5o^x;Xh!sD{r>Ae`DuzWQZ7IX zx^rI?rX^491Wk-WON<#QRXvAb2UySv7fjX|eE1`#OS}IXK?;sU9DD>5@(6~?u$yAh z>!J6ayD(2~M2&6xmVkGUm0Q3K;SL`wud+STCwX1217r$3S2rE<-*plq*R1=zs9Jr4 zqtp}p`395|vBqK-j{PDpO^S%mogd)(>1|}B+L19<0M183JS4t5hoc-6nJjU8CB2T$ zaOLP~_C|xCGpHXi_Rt#2gOabaI$$V;mX44I>KnPU0(D|IzGxx$=y{x()1tgv_cD@# zfiHc{B8_G;DCY9+lKqAQu9ug>8nzq5g<4afTDmP&Qz0VuF?zLwIRow42BQYFCm@NKTeP*Kz&0>=s4Fujhh{ z^H;*OP!1?PXeKz|Hu)lqu+IiH%Q%FoG52z!Z zP7ry64G8g;3mGiby>@Fmcz}eAYwjt ztSu?x=H}mLc~^};JPv8+i+eUecxD23HIu@&$-WPydMo zZ5a6$sV(Ddf=`S(s3`~=&s~HOAj|UBBT28t89Ue&nXsn5iEPh;f?+N(gXEDjmbQabBB{1>S4lY zowvVT^4n$QdE13+L;{~E*|UHeF|!&N!7euxPoVbh5t7g(-CRd{9$rW%K`eLf@gd!7 zw|6YtoisZ)%!wx=3KEA%#V+lX_DDNtQ`eXC8TLRofLo#!GmaqQ#d?h`>zMTu?<_k)bLyGwDFkZ?=s(rbyYBR!Xsgj|5x)$!+3%KV_B~p4pjOVF@8gXJ zRQ(u6RzRN-P>kn8p*`xf54PGYT#lxP`#XvO{+NW_vMVDO#Br9pFu718R1QTB zLga-!1WVqq(-b@4=$W76q#DDJ=$K6%yOc4zdE4k#)-wi>T=v=*yZ={^P?(kBIk~VN=u$jv9-H6W zabX_0jwZ;e(d=Y_QI|GEM?rl-kFBGx=>>hCun?5s$Rq#R+3PRmTeSeNWlxraRt`WXRA3tuYTH~ zHW;z6w7d#jHt|&L&1{y)9k^UU*pz-@GXk)RGMKUEKl_|Eu}3Kd?FZe~PNdkO8TC?HG(cGg0zPfvb?3Za>yMS5*dG#;CGdE!2nu>$Wu)!e)%(8i&_-_iL(8>)fvBI zAncKZGq_+T_=&q-9bhRF8=8n>TD1>NEscIzL1ob79SuJAEq?pcTBEPd#&(sGckl|t zEU%?R3HvWi^Oih8rOnT4Hz_P0XD*KYRY{(Fpd%Otw<$~QK)ONs-~VI~ zd4pe&`1WY|2zB69w3e!$X-R}aR7?*YdB`@hwd1DdiHm%=3y?In3n{>^3F=Mp;Qw~X zG77dr(!0AT`K1nlI)F-g;YU`5kBes)aE^PKx#&-k2Q+3UTH3^6-?^lCD@cn8E4t>? z$ju4rNiZ`%Xa6@ILO13@sg(>}^~#ULY9)KdIVwNA@CY^hk$< zP{}XLY?6uWvrk+ZUf>g;0Wp#{yZR0Qf^sl)5}Ma=s$V4G_h{N(?_QVMsa}`Q%;bDc zQhn>z>!z(>sy#vdBLFgWq?{wK_35IazoZCddhrOdU?8 z0cQEI%4Jdd<}+_`9r9%P!t+=zlbwxn9vMJJEKc6#;8iUIQLriG;84aOICuwgvF3`} zJfa>douvz6VwmdBiJaJoNQ)6zyShhDw_^6R92(eJMOCmx-K)LMnjYM;Q!&i4WFuUn;SR3A}2$cI~O1E4AQ&1M&iKsN7Xn9b}ecv(|57$ z6P|Do{H4%L{SYMcrhQmG$5wd-id+s6y?5Xq-h%iadTwS_@k_^ZwT? z%)>hHCO6=QkMRa0^;4r63v!=t z*ik>_=+cNwVo%E0<&XVmg+c_XYCYI-`?JMG)`?Mm6ScKAHMZKv%iwVay!)veaN>&E z5xQ^rSJ|05?=5x*!+*(MnFlDe0UkyvT_PP-OffdqO@ zm7h5yL0T8CXkGQ?{pZ3wjt(+RKE75>=A;d zyYu-HMdhIad~y)+V$`!0HMQGcu0h(p`{FliluL$yIT1*a?Q$DV`R>S827|;TvF^{` z1W!Y5#laWQoIsikrgC(=(ezi4IZ`kHSf#pD`GGvs_EN8Pm>?(%?huKL9}iszu2>5a zCly2Y931_dcOK!dHD>OxkyUsENTgu@;NE{#sGpu~Fsu14({&b4crWJdXcpb)gUT*S zxCh>#QoRJRQ~!EUFjV$_)4a`ZlW_xlIu$-d#=%1VFH z+l;*b{B%3FPJ<^`+%~+NvEE-$J$)(_=>5NbAZ9$o4u@tnq}Iwq3`gNH@z5({G54al zMNb9&T(SssXUm(5!QrQn({cPz1}G)(i$-EJ3>o^}HdnRqe_!6$+Y@&>E7i}O;wJgs z-hsKmsMF|{I9UOW-xz50FQ&)~h96P8*^3+E{5Xw3f@QJcR_>tRk9{;kCeM;mG%u|_^X0ouY6>`W19^Fos66SwNEBz1;7S9JIitNNI!2KOzdSRugefnj z_=1b9R@mg{j25(#%>!=Jy;vn z>0y?&LWD_d|7NYB^~qzG5K2@i?S{MfoZZQoKrhQAqhHN&FhFUTu5ED3jhzoMZBvYNJXhGBIild$Nt>|zrqS1FSYXWNksP<|+ zLVb(_*Kff*jl7pB6F!_7heDYt1&|I*cWR1hUBVo1#Srjro8bwB4E;xAECsL(Q1hxrX2^K@a7RwIQ)UF03ow<{^}t=e4e2j@QAtQL46owpl{EJSUIbKoG`ld<+{?Z%kpi!I81v3S^0bgyDVpi=6lh`LhR6il~h=nLKT&rC@PY92JkA{ z<>5|CoqdrkcPbBZgX!Y_!(8OHbXnt>=dFv?F~~tvA_$|-^#Nu!?~84=;>m=s_QKgl zf+_|h6TL~mVm@1?70(Mwjw-->!TqI8zQ+EeYHz_Vf75MrB}o)GY@iGxCGKESxnlQ` zL!4&x9*84>oa`w%;I9z56;1M#{ZdLZ#qo#M_T=9Zx{-kmOH&AMorpw3XeIG{Ad79j zmdy^jGuC1*6>Y0iGhGV`2r1rZqgR4*wiz5CgSc$yUI!m*S}>BebQNAZrvxgATqIW% zHEUp0Vh~IPI;hKACy}Pk$BCkxxn*CIG(C^QWX(g|28P0{Eri)_29wd>@URWN*0&M* zB1^HIm*M-(CiwE{+fVE8X%l=p44;tT6C!>J2mcqtV$Z_TisM?VWF?2`Lz0<&rj{o8 Id%i#aKkTvyE&u=k literal 0 HcmV?d00001 diff --git a/packages/skia/src/specs/WebGPUViewNativeComponent.ts b/packages/skia/src/specs/WebGPUViewNativeComponent.ts new file mode 100644 index 0000000000..7a601a307b --- /dev/null +++ b/packages/skia/src/specs/WebGPUViewNativeComponent.ts @@ -0,0 +1,11 @@ +import codegenNativeComponent from "react-native/Libraries/Utilities/codegenNativeComponent"; +import type { Int32 } from "react-native/Libraries/Types/CodegenTypes"; +import type { ViewProps } from "react-native"; + +export interface NativeProps extends ViewProps { + contextId: Int32; + transparent: boolean; +} + +// eslint-disable-next-line import/no-default-export +export default codegenNativeComponent("WebGPUView"); diff --git a/packages/skia/src/views/WebGPUCanvas.tsx b/packages/skia/src/views/WebGPUCanvas.tsx new file mode 100644 index 0000000000..9b4e4c73ea --- /dev/null +++ b/packages/skia/src/views/WebGPUCanvas.tsx @@ -0,0 +1,110 @@ +import React, { useImperativeHandle, useRef, useState } from "react"; +import type { ViewProps } from "react-native"; +import { View, Platform } from "react-native"; + +import WebGPUNativeView from "../specs/WebGPUViewNativeComponent"; + +let CONTEXT_COUNTER = 1; +function generateContextId() { + return CONTEXT_COUNTER++; +} + +declare global { + // eslint-disable-next-line no-var + var RNWebGPU: { + gpu: GPU; + fabric: boolean; + getNativeSurface: (contextId: number) => NativeCanvas; + MakeWebGPUCanvasContext: ( + contextId: number, + width: number, + height: number + ) => RNCanvasContext; + }; +} + +type SurfacePointer = bigint; + +export interface NativeCanvas { + surface: SurfacePointer; + width: number; + height: number; + clientWidth: number; + clientHeight: number; +} + +export type RNCanvasContext = GPUCanvasContext & { + present: () => void; +}; + +export interface WebGPUCanvasRef { + getContextId: () => number; + getContext(contextName: "webgpu"): RNCanvasContext | null; + getNativeSurface: () => NativeCanvas; +} + +interface WebGPUCanvasProps extends ViewProps { + transparent?: boolean; + ref?: React.Ref; +} + +export const WebGPUCanvas = ({ + transparent, + ref, + ...props +}: WebGPUCanvasProps) => { + const viewRef = useRef(null); + const [contextId] = useState(() => generateContextId()); + + useImperativeHandle(ref, () => ({ + getContextId: () => contextId, + getNativeSurface: () => { + if (typeof RNWebGPU === "undefined") { + throw new Error( + "[WebGPU] RNWebGPU is not available. Make sure SK_GRAPHITE is enabled." + ); + } + return RNWebGPU.getNativeSurface(contextId); + }, + getContext(contextName: "webgpu"): RNCanvasContext | null { + if (contextName !== "webgpu") { + throw new Error(`[WebGPU] Unsupported context: ${contextName}`); + } + if (!viewRef.current) { + throw new Error("[WebGPU] Cannot get context before mount"); + } + if (typeof RNWebGPU === "undefined") { + throw new Error( + "[WebGPU] RNWebGPU is not available. Make sure SK_GRAPHITE is enabled." + ); + } + // getBoundingClientRect became stable in RN 0.83 + // eslint-disable-next-line @typescript-eslint/no-explicit-any + const view = viewRef.current as any; + const size = + "getBoundingClientRect" in view + ? view.getBoundingClientRect() + : view.unstable_getBoundingClientRect(); + return RNWebGPU.MakeWebGPUCanvasContext( + contextId, + size.width, + size.height + ); + }, + })); + + // WebGPU Canvas is not supported on web + if (Platform.OS === "web") { + return ; + } + + return ( + + + + ); +}; diff --git a/packages/skia/src/views/index.ts b/packages/skia/src/views/index.ts index 1760ffae2e..56181da28c 100644 --- a/packages/skia/src/views/index.ts +++ b/packages/skia/src/views/index.ts @@ -1,2 +1,3 @@ export * from "./SkiaPictureView"; export * from "./types"; +export * from "./WebGPUCanvas"; From 84cbbee60d8cb8b088302aea4727891670c2d677 Mon Sep 17 00:00:00 2001 From: William Candillon Date: Mon, 9 Feb 2026 10:22:14 +0100 Subject: [PATCH 02/10] :wrench: --- apps/example/ios/Podfile.lock | 2162 +++++++++++++---- apps/example/src/App.tsx | 2 +- apps/example/src/Examples/WebGPU/List.tsx | 5 + apps/example/src/Examples/WebGPU/Routes.ts | 1 + apps/example/src/Examples/WebGPU/Shaders.ts | 36 + .../src/Examples/WebGPU/TexturedCube.tsx | 301 +++ .../src/Examples/WebGPU/assets/Di-3d.png | Bin 0 -> 243533 bytes apps/example/src/Examples/WebGPU/cube.ts | 51 + apps/example/src/Examples/WebGPU/index.tsx | 8 + apps/example/src/Examples/WebGPU/matrix.ts | 54 + packages/skia/package.json | 12 +- 11 files changed, 2096 insertions(+), 536 deletions(-) create mode 100644 apps/example/src/Examples/WebGPU/TexturedCube.tsx create mode 100644 apps/example/src/Examples/WebGPU/assets/Di-3d.png create mode 100644 apps/example/src/Examples/WebGPU/cube.ts diff --git a/apps/example/ios/Podfile.lock b/apps/example/ios/Podfile.lock index 9a92f49c06..1eee6abbfc 100644 --- a/apps/example/ios/Podfile.lock +++ b/apps/example/ios/Podfile.lock @@ -1,73 +1,89 @@ PODS: - boost (1.84.0) - DoubleConversion (1.1.6) - - fast_float (6.1.4) - - FBLazyVector (0.78.0) + - fast_float (8.0.0) + - FBLazyVector (0.83.1) - fmt (11.0.2) - glog (0.3.5) - - hermes-engine (0.78.0): - - hermes-engine/Pre-built (= 0.78.0) - - hermes-engine/Pre-built (0.78.0) + - hermes-engine (0.14.0): + - hermes-engine/Pre-built (= 0.14.0) + - hermes-engine/Pre-built (0.14.0) - RCT-Folly (2024.11.18.00): - boost - DoubleConversion - - fast_float (= 6.1.4) + - fast_float (= 8.0.0) - fmt (= 11.0.2) - glog - RCT-Folly/Default (= 2024.11.18.00) - RCT-Folly/Default (2024.11.18.00): - boost - DoubleConversion - - fast_float (= 6.1.4) + - fast_float (= 8.0.0) - fmt (= 11.0.2) - glog - RCT-Folly/Fabric (2024.11.18.00): - boost - DoubleConversion - - fast_float (= 6.1.4) + - fast_float (= 8.0.0) - fmt (= 11.0.2) - glog - - RCTDeprecation (0.78.0) - - RCTRequired (0.78.0) - - RCTTypeSafety (0.78.0): - - FBLazyVector (= 0.78.0) - - RCTRequired (= 0.78.0) - - React-Core (= 0.78.0) - - React (0.78.0): - - React-Core (= 0.78.0) - - React-Core/DevSupport (= 0.78.0) - - React-Core/RCTWebSocket (= 0.78.0) - - React-RCTActionSheet (= 0.78.0) - - React-RCTAnimation (= 0.78.0) - - React-RCTBlob (= 0.78.0) - - React-RCTImage (= 0.78.0) - - React-RCTLinking (= 0.78.0) - - React-RCTNetwork (= 0.78.0) - - React-RCTSettings (= 0.78.0) - - React-RCTText (= 0.78.0) - - React-RCTVibration (= 0.78.0) - - React-callinvoker (0.78.0) - - React-Core (0.78.0): - - glog - - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCTDeprecation (0.83.1) + - RCTRequired (0.83.1) + - RCTSwiftUI (0.83.1) + - RCTSwiftUIWrapper (0.83.1): + - RCTSwiftUI + - RCTTypeSafety (0.83.1): + - FBLazyVector (= 0.83.1) + - RCTRequired (= 0.83.1) + - React-Core (= 0.83.1) + - React (0.83.1): + - React-Core (= 0.83.1) + - React-Core/DevSupport (= 0.83.1) + - React-Core/RCTWebSocket (= 0.83.1) + - React-RCTActionSheet (= 0.83.1) + - React-RCTAnimation (= 0.83.1) + - React-RCTBlob (= 0.83.1) + - React-RCTImage (= 0.83.1) + - React-RCTLinking (= 0.83.1) + - React-RCTNetwork (= 0.83.1) + - React-RCTSettings (= 0.83.1) + - React-RCTText (= 0.83.1) + - React-RCTVibration (= 0.83.1) + - React-callinvoker (0.83.1) + - React-Core (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - hermes-engine + - RCT-Folly + - RCT-Folly/Fabric - RCTDeprecation - - React-Core/Default (= 0.78.0) + - React-Core/Default (= 0.83.1) - React-cxxreact - React-featureflags - React-hermes - React-jsi - React-jsiexecutor - React-jsinspector + - React-jsinspectorcdp + - React-jsitooling - React-perflogger + - React-runtimeexecutor - React-runtimescheduler - React-utils - - SocketRocket (= 0.7.1) + - SocketRocket - Yoga - - React-Core/CoreModulesHeaders (0.78.0): + - React-Core/CoreModulesHeaders (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTDeprecation - React-Core/Default - React-cxxreact @@ -76,15 +92,23 @@ PODS: - React-jsi - React-jsiexecutor - React-jsinspector + - React-jsinspectorcdp + - React-jsitooling - React-perflogger + - React-runtimeexecutor - React-runtimescheduler - React-utils - - SocketRocket (= 0.7.1) + - SocketRocket - Yoga - - React-Core/Default (0.78.0): + - React-Core/Default (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTDeprecation - React-cxxreact - React-featureflags @@ -92,33 +116,49 @@ PODS: - React-jsi - React-jsiexecutor - React-jsinspector + - React-jsinspectorcdp + - React-jsitooling - React-perflogger + - React-runtimeexecutor - React-runtimescheduler - React-utils - - SocketRocket (= 0.7.1) + - SocketRocket - Yoga - - React-Core/DevSupport (0.78.0): + - React-Core/DevSupport (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTDeprecation - - React-Core/Default (= 0.78.0) - - React-Core/RCTWebSocket (= 0.78.0) + - React-Core/Default (= 0.83.1) + - React-Core/RCTWebSocket (= 0.83.1) - React-cxxreact - React-featureflags - React-hermes - React-jsi - React-jsiexecutor - React-jsinspector + - React-jsinspectorcdp + - React-jsitooling - React-perflogger + - React-runtimeexecutor - React-runtimescheduler - React-utils - - SocketRocket (= 0.7.1) + - SocketRocket - Yoga - - React-Core/RCTActionSheetHeaders (0.78.0): + - React-Core/RCTActionSheetHeaders (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTDeprecation - React-Core/Default - React-cxxreact @@ -127,15 +167,23 @@ PODS: - React-jsi - React-jsiexecutor - React-jsinspector + - React-jsinspectorcdp + - React-jsitooling - React-perflogger + - React-runtimeexecutor - React-runtimescheduler - React-utils - - SocketRocket (= 0.7.1) + - SocketRocket - Yoga - - React-Core/RCTAnimationHeaders (0.78.0): + - React-Core/RCTAnimationHeaders (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTDeprecation - React-Core/Default - React-cxxreact @@ -144,15 +192,23 @@ PODS: - React-jsi - React-jsiexecutor - React-jsinspector + - React-jsinspectorcdp + - React-jsitooling - React-perflogger + - React-runtimeexecutor - React-runtimescheduler - React-utils - - SocketRocket (= 0.7.1) + - SocketRocket - Yoga - - React-Core/RCTBlobHeaders (0.78.0): + - React-Core/RCTBlobHeaders (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTDeprecation - React-Core/Default - React-cxxreact @@ -161,15 +217,23 @@ PODS: - React-jsi - React-jsiexecutor - React-jsinspector + - React-jsinspectorcdp + - React-jsitooling - React-perflogger + - React-runtimeexecutor - React-runtimescheduler - React-utils - - SocketRocket (= 0.7.1) + - SocketRocket - Yoga - - React-Core/RCTImageHeaders (0.78.0): + - React-Core/RCTImageHeaders (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTDeprecation - React-Core/Default - React-cxxreact @@ -178,15 +242,23 @@ PODS: - React-jsi - React-jsiexecutor - React-jsinspector + - React-jsinspectorcdp + - React-jsitooling - React-perflogger + - React-runtimeexecutor - React-runtimescheduler - React-utils - - SocketRocket (= 0.7.1) + - SocketRocket - Yoga - - React-Core/RCTLinkingHeaders (0.78.0): + - React-Core/RCTLinkingHeaders (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTDeprecation - React-Core/Default - React-cxxreact @@ -195,15 +267,23 @@ PODS: - React-jsi - React-jsiexecutor - React-jsinspector + - React-jsinspectorcdp + - React-jsitooling - React-perflogger + - React-runtimeexecutor - React-runtimescheduler - React-utils - - SocketRocket (= 0.7.1) + - SocketRocket - Yoga - - React-Core/RCTNetworkHeaders (0.78.0): + - React-Core/RCTNetworkHeaders (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTDeprecation - React-Core/Default - React-cxxreact @@ -212,15 +292,23 @@ PODS: - React-jsi - React-jsiexecutor - React-jsinspector + - React-jsinspectorcdp + - React-jsitooling - React-perflogger + - React-runtimeexecutor - React-runtimescheduler - React-utils - - SocketRocket (= 0.7.1) + - SocketRocket - Yoga - - React-Core/RCTSettingsHeaders (0.78.0): + - React-Core/RCTSettingsHeaders (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTDeprecation - React-Core/Default - React-cxxreact @@ -229,15 +317,23 @@ PODS: - React-jsi - React-jsiexecutor - React-jsinspector + - React-jsinspectorcdp + - React-jsitooling - React-perflogger + - React-runtimeexecutor - React-runtimescheduler - React-utils - - SocketRocket (= 0.7.1) + - SocketRocket - Yoga - - React-Core/RCTTextHeaders (0.78.0): + - React-Core/RCTTextHeaders (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTDeprecation - React-Core/Default - React-cxxreact @@ -246,15 +342,23 @@ PODS: - React-jsi - React-jsiexecutor - React-jsinspector + - React-jsinspectorcdp + - React-jsitooling - React-perflogger + - React-runtimeexecutor - React-runtimescheduler - React-utils - - SocketRocket (= 0.7.1) + - SocketRocket - Yoga - - React-Core/RCTVibrationHeaders (0.78.0): + - React-Core/RCTVibrationHeaders (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTDeprecation - React-Core/Default - React-cxxreact @@ -263,125 +367,178 @@ PODS: - React-jsi - React-jsiexecutor - React-jsinspector + - React-jsinspectorcdp + - React-jsitooling - React-perflogger + - React-runtimeexecutor - React-runtimescheduler - React-utils - - SocketRocket (= 0.7.1) + - SocketRocket - Yoga - - React-Core/RCTWebSocket (0.78.0): + - React-Core/RCTWebSocket (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTDeprecation - - React-Core/Default (= 0.78.0) + - React-Core/Default (= 0.83.1) - React-cxxreact - React-featureflags - React-hermes - React-jsi - React-jsiexecutor - React-jsinspector + - React-jsinspectorcdp + - React-jsitooling - React-perflogger + - React-runtimeexecutor - React-runtimescheduler - React-utils - - SocketRocket (= 0.7.1) + - SocketRocket - Yoga - - React-CoreModules (0.78.0): + - React-CoreModules (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) - - RCT-Folly (= 2024.11.18.00) - - RCTTypeSafety (= 0.78.0) - - React-Core/CoreModulesHeaders (= 0.78.0) - - React-jsi (= 0.78.0) + - fast_float + - fmt + - glog + - RCT-Folly + - RCT-Folly/Fabric + - RCTTypeSafety (= 0.83.1) + - React-Core/CoreModulesHeaders (= 0.83.1) + - React-debug + - React-jsi (= 0.83.1) - React-jsinspector + - React-jsinspectorcdp + - React-jsinspectortracing - React-NativeModulesApple - React-RCTBlob - React-RCTFBReactNativeSpec - - React-RCTImage (= 0.78.0) + - React-RCTImage (= 0.83.1) + - React-runtimeexecutor + - React-utils - ReactCommon - - SocketRocket (= 0.7.1) - - React-cxxreact (0.78.0): + - SocketRocket + - React-cxxreact (0.83.1): - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) - - React-callinvoker (= 0.78.0) - - React-debug (= 0.78.0) - - React-jsi (= 0.78.0) + - RCT-Folly + - RCT-Folly/Fabric + - React-callinvoker (= 0.83.1) + - React-debug (= 0.83.1) + - React-jsi (= 0.83.1) - React-jsinspector - - React-logger (= 0.78.0) - - React-perflogger (= 0.78.0) - - React-runtimeexecutor (= 0.78.0) - - React-timing (= 0.78.0) - - React-debug (0.78.0) - - React-defaultsnativemodule (0.78.0): + - React-jsinspectorcdp + - React-jsinspectortracing + - React-logger (= 0.83.1) + - React-perflogger (= 0.83.1) + - React-runtimeexecutor + - React-timing (= 0.83.1) + - React-utils + - SocketRocket + - React-debug (0.83.1) + - React-defaultsnativemodule (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog - hermes-engine - RCT-Folly + - RCT-Folly/Fabric - React-domnativemodule + - React-featureflags - React-featureflagsnativemodule - React-idlecallbacksnativemodule + - React-intersectionobservernativemodule - React-jsi - React-jsiexecutor - React-microtasksnativemodule - React-RCTFBReactNativeSpec - - React-domnativemodule (0.78.0): + - React-webperformancenativemodule + - SocketRocket + - Yoga + - React-domnativemodule (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog - hermes-engine - RCT-Folly + - RCT-Folly/Fabric - React-Fabric + - React-Fabric/bridging - React-FabricComponents - React-graphics - React-jsi - React-jsiexecutor - React-RCTFBReactNativeSpec + - React-runtimeexecutor - ReactCommon/turbomodule/core + - SocketRocket - Yoga - - React-Fabric (0.78.0): + - React-Fabric (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core - React-cxxreact - React-debug - - React-Fabric/animations (= 0.78.0) - - React-Fabric/attributedstring (= 0.78.0) - - React-Fabric/componentregistry (= 0.78.0) - - React-Fabric/componentregistrynative (= 0.78.0) - - React-Fabric/components (= 0.78.0) - - React-Fabric/consistency (= 0.78.0) - - React-Fabric/core (= 0.78.0) - - React-Fabric/dom (= 0.78.0) - - React-Fabric/imagemanager (= 0.78.0) - - React-Fabric/leakchecker (= 0.78.0) - - React-Fabric/mounting (= 0.78.0) - - React-Fabric/observers (= 0.78.0) - - React-Fabric/scheduler (= 0.78.0) - - React-Fabric/telemetry (= 0.78.0) - - React-Fabric/templateprocessor (= 0.78.0) - - React-Fabric/uimanager (= 0.78.0) + - React-Fabric/animated (= 0.83.1) + - React-Fabric/animationbackend (= 0.83.1) + - React-Fabric/animations (= 0.83.1) + - React-Fabric/attributedstring (= 0.83.1) + - React-Fabric/bridging (= 0.83.1) + - React-Fabric/componentregistry (= 0.83.1) + - React-Fabric/componentregistrynative (= 0.83.1) + - React-Fabric/components (= 0.83.1) + - React-Fabric/consistency (= 0.83.1) + - React-Fabric/core (= 0.83.1) + - React-Fabric/dom (= 0.83.1) + - React-Fabric/imagemanager (= 0.83.1) + - React-Fabric/leakchecker (= 0.83.1) + - React-Fabric/mounting (= 0.83.1) + - React-Fabric/observers (= 0.83.1) + - React-Fabric/scheduler (= 0.83.1) + - React-Fabric/telemetry (= 0.83.1) + - React-Fabric/templateprocessor (= 0.83.1) + - React-Fabric/uimanager (= 0.83.1) - React-featureflags - React-graphics - React-jsi - React-jsiexecutor - React-logger - React-rendererdebug + - React-runtimeexecutor - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core - - React-Fabric/animations (0.78.0): + - SocketRocket + - React-Fabric/animated (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -393,16 +550,20 @@ PODS: - React-jsiexecutor - React-logger - React-rendererdebug + - React-runtimeexecutor - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core - - React-Fabric/attributedstring (0.78.0): + - SocketRocket + - React-Fabric/animationbackend (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -414,16 +575,20 @@ PODS: - React-jsiexecutor - React-logger - React-rendererdebug + - React-runtimeexecutor - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core - - React-Fabric/componentregistry (0.78.0): + - SocketRocket + - React-Fabric/animations (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -435,16 +600,20 @@ PODS: - React-jsiexecutor - React-logger - React-rendererdebug + - React-runtimeexecutor - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core - - React-Fabric/componentregistrynative (0.78.0): + - SocketRocket + - React-Fabric/attributedstring (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -456,40 +625,45 @@ PODS: - React-jsiexecutor - React-logger - React-rendererdebug + - React-runtimeexecutor - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core - - React-Fabric/components (0.78.0): + - SocketRocket + - React-Fabric/bridging (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core - React-cxxreact - React-debug - - React-Fabric/components/legacyviewmanagerinterop (= 0.78.0) - - React-Fabric/components/root (= 0.78.0) - - React-Fabric/components/view (= 0.78.0) - React-featureflags - React-graphics - React-jsi - React-jsiexecutor - React-logger - React-rendererdebug + - React-runtimeexecutor - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core - - React-Fabric/components/legacyviewmanagerinterop (0.78.0): + - SocketRocket + - React-Fabric/componentregistry (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -501,16 +675,20 @@ PODS: - React-jsiexecutor - React-logger - React-rendererdebug + - React-runtimeexecutor - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core - - React-Fabric/components/root (0.78.0): + - SocketRocket + - React-Fabric/componentregistrynative (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -522,38 +700,49 @@ PODS: - React-jsiexecutor - React-logger - React-rendererdebug + - React-runtimeexecutor - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core - - React-Fabric/components/view (0.78.0): + - SocketRocket + - React-Fabric/components (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core - React-cxxreact - React-debug + - React-Fabric/components/legacyviewmanagerinterop (= 0.83.1) + - React-Fabric/components/root (= 0.83.1) + - React-Fabric/components/scrollview (= 0.83.1) + - React-Fabric/components/view (= 0.83.1) - React-featureflags - React-graphics - React-jsi - React-jsiexecutor - React-logger - React-rendererdebug + - React-runtimeexecutor - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core - - Yoga - - React-Fabric/consistency (0.78.0): + - SocketRocket + - React-Fabric/components/legacyviewmanagerinterop (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -565,16 +754,20 @@ PODS: - React-jsiexecutor - React-logger - React-rendererdebug + - React-runtimeexecutor - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core - - React-Fabric/core (0.78.0): + - SocketRocket + - React-Fabric/components/root (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -586,16 +779,20 @@ PODS: - React-jsiexecutor - React-logger - React-rendererdebug + - React-runtimeexecutor - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core - - React-Fabric/dom (0.78.0): + - SocketRocket + - React-Fabric/components/scrollview (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -607,16 +804,20 @@ PODS: - React-jsiexecutor - React-logger - React-rendererdebug + - React-runtimeexecutor - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core - - React-Fabric/imagemanager (0.78.0): + - SocketRocket + - React-Fabric/components/view (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -627,17 +828,23 @@ PODS: - React-jsi - React-jsiexecutor - React-logger + - React-renderercss - React-rendererdebug + - React-runtimeexecutor - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core - - React-Fabric/leakchecker (0.78.0): + - SocketRocket + - Yoga + - React-Fabric/consistency (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -649,16 +856,20 @@ PODS: - React-jsiexecutor - React-logger - React-rendererdebug + - React-runtimeexecutor - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core - - React-Fabric/mounting (0.78.0): + - SocketRocket + - React-Fabric/core (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -670,38 +881,45 @@ PODS: - React-jsiexecutor - React-logger - React-rendererdebug + - React-runtimeexecutor - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core - - React-Fabric/observers (0.78.0): + - SocketRocket + - React-Fabric/dom (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core - React-cxxreact - React-debug - - React-Fabric/observers/events (= 0.78.0) - React-featureflags - React-graphics - React-jsi - React-jsiexecutor - React-logger - React-rendererdebug + - React-runtimeexecutor - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core - - React-Fabric/observers/events (0.78.0): + - SocketRocket + - React-Fabric/imagemanager (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -713,39 +931,45 @@ PODS: - React-jsiexecutor - React-logger - React-rendererdebug + - React-runtimeexecutor - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core - - React-Fabric/scheduler (0.78.0): + - SocketRocket + - React-Fabric/leakchecker (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core - React-cxxreact - React-debug - - React-Fabric/observers/events - React-featureflags - React-graphics - React-jsi - React-jsiexecutor - React-logger - - React-performancetimeline - React-rendererdebug + - React-runtimeexecutor - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core - - React-Fabric/telemetry (0.78.0): + - SocketRocket + - React-Fabric/mounting (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -757,60 +981,72 @@ PODS: - React-jsiexecutor - React-logger - React-rendererdebug + - React-runtimeexecutor - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core - - React-Fabric/templateprocessor (0.78.0): + - SocketRocket + - React-Fabric/observers (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core - React-cxxreact - React-debug + - React-Fabric/observers/events (= 0.83.1) + - React-Fabric/observers/intersection (= 0.83.1) - React-featureflags - React-graphics - React-jsi - React-jsiexecutor - React-logger - React-rendererdebug + - React-runtimeexecutor - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core - - React-Fabric/uimanager (0.78.0): + - SocketRocket + - React-Fabric/observers/events (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core - React-cxxreact - React-debug - - React-Fabric/uimanager/consistency (= 0.78.0) - React-featureflags - React-graphics - React-jsi - React-jsiexecutor - React-logger - - React-rendererconsistency - React-rendererdebug + - React-runtimeexecutor - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core - - React-Fabric/uimanager/consistency (0.78.0): + - SocketRocket + - React-Fabric/observers/intersection (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -821,75 +1057,220 @@ PODS: - React-jsi - React-jsiexecutor - React-logger - - React-rendererconsistency - React-rendererdebug + - React-runtimeexecutor - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core - - React-FabricComponents (0.78.0): + - SocketRocket + - React-Fabric/scheduler (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric + - RCTRequired + - RCTTypeSafety + - React-Core + - React-cxxreact + - React-debug + - React-Fabric/observers/events + - React-featureflags + - React-graphics + - React-jsi + - React-jsiexecutor + - React-logger + - React-performancecdpmetrics + - React-performancetimeline + - React-rendererdebug + - React-runtimeexecutor + - React-runtimescheduler + - React-utils + - ReactCommon/turbomodule/core + - SocketRocket + - React-Fabric/telemetry (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - hermes-engine + - RCT-Folly + - RCT-Folly/Fabric + - RCTRequired + - RCTTypeSafety + - React-Core + - React-cxxreact + - React-debug + - React-featureflags + - React-graphics + - React-jsi + - React-jsiexecutor + - React-logger + - React-rendererdebug + - React-runtimeexecutor + - React-runtimescheduler + - React-utils + - ReactCommon/turbomodule/core + - SocketRocket + - React-Fabric/templateprocessor (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - hermes-engine + - RCT-Folly + - RCT-Folly/Fabric + - RCTRequired + - RCTTypeSafety + - React-Core + - React-cxxreact + - React-debug + - React-featureflags + - React-graphics + - React-jsi + - React-jsiexecutor + - React-logger + - React-rendererdebug + - React-runtimeexecutor + - React-runtimescheduler + - React-utils + - ReactCommon/turbomodule/core + - SocketRocket + - React-Fabric/uimanager (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - hermes-engine + - RCT-Folly + - RCT-Folly/Fabric + - RCTRequired + - RCTTypeSafety + - React-Core + - React-cxxreact + - React-debug + - React-Fabric/uimanager/consistency (= 0.83.1) + - React-featureflags + - React-graphics + - React-jsi + - React-jsiexecutor + - React-logger + - React-rendererconsistency + - React-rendererdebug + - React-runtimeexecutor + - React-runtimescheduler + - React-utils + - ReactCommon/turbomodule/core + - SocketRocket + - React-Fabric/uimanager/consistency (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - hermes-engine + - RCT-Folly + - RCT-Folly/Fabric + - RCTRequired + - RCTTypeSafety + - React-Core + - React-cxxreact + - React-debug + - React-featureflags + - React-graphics + - React-jsi + - React-jsiexecutor + - React-logger + - React-rendererconsistency + - React-rendererdebug + - React-runtimeexecutor + - React-runtimescheduler + - React-utils + - ReactCommon/turbomodule/core + - SocketRocket + - React-FabricComponents (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - hermes-engine + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core - React-cxxreact - React-debug - React-Fabric - - React-FabricComponents/components (= 0.78.0) - - React-FabricComponents/textlayoutmanager (= 0.78.0) + - React-FabricComponents/components (= 0.83.1) + - React-FabricComponents/textlayoutmanager (= 0.83.1) - React-featureflags - React-graphics - React-jsi - React-jsiexecutor - React-logger + - React-RCTFBReactNativeSpec - React-rendererdebug - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core + - SocketRocket - Yoga - - React-FabricComponents/components (0.78.0): + - React-FabricComponents/components (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core - React-cxxreact - React-debug - React-Fabric - - React-FabricComponents/components/inputaccessory (= 0.78.0) - - React-FabricComponents/components/iostextinput (= 0.78.0) - - React-FabricComponents/components/modal (= 0.78.0) - - React-FabricComponents/components/rncore (= 0.78.0) - - React-FabricComponents/components/safeareaview (= 0.78.0) - - React-FabricComponents/components/scrollview (= 0.78.0) - - React-FabricComponents/components/text (= 0.78.0) - - React-FabricComponents/components/textinput (= 0.78.0) - - React-FabricComponents/components/unimplementedview (= 0.78.0) + - React-FabricComponents/components/inputaccessory (= 0.83.1) + - React-FabricComponents/components/iostextinput (= 0.83.1) + - React-FabricComponents/components/modal (= 0.83.1) + - React-FabricComponents/components/rncore (= 0.83.1) + - React-FabricComponents/components/safeareaview (= 0.83.1) + - React-FabricComponents/components/scrollview (= 0.83.1) + - React-FabricComponents/components/switch (= 0.83.1) + - React-FabricComponents/components/text (= 0.83.1) + - React-FabricComponents/components/textinput (= 0.83.1) + - React-FabricComponents/components/unimplementedview (= 0.83.1) + - React-FabricComponents/components/virtualview (= 0.83.1) + - React-FabricComponents/components/virtualviewexperimental (= 0.83.1) - React-featureflags - React-graphics - React-jsi - React-jsiexecutor - React-logger + - React-RCTFBReactNativeSpec - React-rendererdebug - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core + - SocketRocket - Yoga - - React-FabricComponents/components/inputaccessory (0.78.0): + - React-FabricComponents/components/inputaccessory (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -901,18 +1282,22 @@ PODS: - React-jsi - React-jsiexecutor - React-logger + - React-RCTFBReactNativeSpec - React-rendererdebug - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core + - SocketRocket - Yoga - - React-FabricComponents/components/iostextinput (0.78.0): + - React-FabricComponents/components/iostextinput (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -924,18 +1309,22 @@ PODS: - React-jsi - React-jsiexecutor - React-logger + - React-RCTFBReactNativeSpec - React-rendererdebug - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core + - SocketRocket - Yoga - - React-FabricComponents/components/modal (0.78.0): + - React-FabricComponents/components/modal (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -947,18 +1336,22 @@ PODS: - React-jsi - React-jsiexecutor - React-logger + - React-RCTFBReactNativeSpec - React-rendererdebug - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core + - SocketRocket - Yoga - - React-FabricComponents/components/rncore (0.78.0): + - React-FabricComponents/components/rncore (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -970,18 +1363,22 @@ PODS: - React-jsi - React-jsiexecutor - React-logger + - React-RCTFBReactNativeSpec - React-rendererdebug - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core + - SocketRocket - Yoga - - React-FabricComponents/components/safeareaview (0.78.0): + - React-FabricComponents/components/safeareaview (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -993,18 +1390,22 @@ PODS: - React-jsi - React-jsiexecutor - React-logger + - React-RCTFBReactNativeSpec - React-rendererdebug - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core + - SocketRocket - Yoga - - React-FabricComponents/components/scrollview (0.78.0): + - React-FabricComponents/components/scrollview (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -1016,18 +1417,22 @@ PODS: - React-jsi - React-jsiexecutor - React-logger + - React-RCTFBReactNativeSpec - React-rendererdebug - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core + - SocketRocket - Yoga - - React-FabricComponents/components/text (0.78.0): + - React-FabricComponents/components/switch (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -1039,18 +1444,22 @@ PODS: - React-jsi - React-jsiexecutor - React-logger + - React-RCTFBReactNativeSpec - React-rendererdebug - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core + - SocketRocket - Yoga - - React-FabricComponents/components/textinput (0.78.0): + - React-FabricComponents/components/text (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -1062,18 +1471,22 @@ PODS: - React-jsi - React-jsiexecutor - React-logger + - React-RCTFBReactNativeSpec - React-rendererdebug - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core + - SocketRocket - Yoga - - React-FabricComponents/components/unimplementedview (0.78.0): + - React-FabricComponents/components/textinput (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -1085,18 +1498,22 @@ PODS: - React-jsi - React-jsiexecutor - React-logger + - React-RCTFBReactNativeSpec - React-rendererdebug - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core + - SocketRocket - Yoga - - React-FabricComponents/textlayoutmanager (0.78.0): + - React-FabricComponents/components/unimplementedview (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -1108,75 +1525,196 @@ PODS: - React-jsi - React-jsiexecutor - React-logger + - React-RCTFBReactNativeSpec - React-rendererdebug - React-runtimescheduler - React-utils - ReactCommon/turbomodule/core + - SocketRocket - Yoga - - React-FabricImage (0.78.0): + - React-FabricComponents/components/virtualview (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt + - glog + - hermes-engine + - RCT-Folly + - RCT-Folly/Fabric + - RCTRequired + - RCTTypeSafety + - React-Core + - React-cxxreact + - React-debug + - React-Fabric + - React-featureflags + - React-graphics + - React-jsi + - React-jsiexecutor + - React-logger + - React-RCTFBReactNativeSpec + - React-rendererdebug + - React-runtimescheduler + - React-utils + - ReactCommon/turbomodule/core + - SocketRocket + - Yoga + - React-FabricComponents/components/virtualviewexperimental (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - hermes-engine + - RCT-Folly + - RCT-Folly/Fabric + - RCTRequired + - RCTTypeSafety + - React-Core + - React-cxxreact + - React-debug + - React-Fabric + - React-featureflags + - React-graphics + - React-jsi + - React-jsiexecutor + - React-logger + - React-RCTFBReactNativeSpec + - React-rendererdebug + - React-runtimescheduler + - React-utils + - ReactCommon/turbomodule/core + - SocketRocket + - Yoga + - React-FabricComponents/textlayoutmanager (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) - - RCTRequired (= 0.78.0) - - RCTTypeSafety (= 0.78.0) + - RCT-Folly + - RCT-Folly/Fabric + - RCTRequired + - RCTTypeSafety + - React-Core + - React-cxxreact + - React-debug + - React-Fabric + - React-featureflags + - React-graphics + - React-jsi + - React-jsiexecutor + - React-logger + - React-RCTFBReactNativeSpec + - React-rendererdebug + - React-runtimescheduler + - React-utils + - ReactCommon/turbomodule/core + - SocketRocket + - Yoga + - React-FabricImage (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - hermes-engine + - RCT-Folly + - RCT-Folly/Fabric + - RCTRequired (= 0.83.1) + - RCTTypeSafety (= 0.83.1) - React-Fabric - React-featureflags - React-graphics - React-ImageManager - React-jsi - - React-jsiexecutor (= 0.78.0) + - React-jsiexecutor (= 0.83.1) - React-logger - React-rendererdebug - React-utils - ReactCommon + - SocketRocket - Yoga - - React-featureflags (0.78.0): - - RCT-Folly (= 2024.11.18.00) - - React-featureflagsnativemodule (0.78.0): + - React-featureflags (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - RCT-Folly + - RCT-Folly/Fabric + - SocketRocket + - React-featureflagsnativemodule (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog - hermes-engine - RCT-Folly + - RCT-Folly/Fabric - React-featureflags - React-jsi - React-jsiexecutor - React-RCTFBReactNativeSpec - ReactCommon/turbomodule/core - - React-graphics (0.78.0): + - SocketRocket + - React-graphics (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - React-jsi - React-jsiexecutor - React-utils - - React-hermes (0.78.0): + - SocketRocket + - React-hermes (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) - - React-cxxreact (= 0.78.0) + - RCT-Folly + - RCT-Folly/Fabric + - React-cxxreact (= 0.83.1) - React-jsi - - React-jsiexecutor (= 0.78.0) + - React-jsiexecutor (= 0.83.1) - React-jsinspector - - React-perflogger (= 0.78.0) + - React-jsinspectorcdp + - React-jsinspectortracing + - React-oscompat + - React-perflogger (= 0.83.1) - React-runtimeexecutor - - React-idlecallbacksnativemodule (0.78.0): + - SocketRocket + - React-idlecallbacksnativemodule (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - RCT-Folly + - RCT-Folly/Fabric - React-jsi - React-jsiexecutor - React-RCTFBReactNativeSpec + - React-runtimeexecutor - React-runtimescheduler - ReactCommon/turbomodule/core - - React-ImageManager (0.78.0): + - SocketRocket + - React-ImageManager (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt - glog + - RCT-Folly - RCT-Folly/Fabric - React-Core/Default - React-debug @@ -1184,65 +1722,185 @@ PODS: - React-graphics - React-rendererdebug - React-utils - - React-jserrorhandler (0.78.0): + - SocketRocket + - React-intersectionobservernativemodule (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric + - React-cxxreact + - React-Fabric + - React-Fabric/bridging + - React-graphics + - React-jsi + - React-jsiexecutor + - React-RCTFBReactNativeSpec + - React-runtimeexecutor + - React-runtimescheduler + - ReactCommon/turbomodule/core + - SocketRocket + - Yoga + - React-jserrorhandler (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - hermes-engine + - RCT-Folly + - RCT-Folly/Fabric - React-cxxreact - React-debug - React-featureflags - React-jsi - ReactCommon/turbomodule/bridging - - React-jsi (0.78.0): + - SocketRocket + - React-jsi (0.83.1): - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) - - React-jsiexecutor (0.78.0): + - RCT-Folly + - RCT-Folly/Fabric + - SocketRocket + - React-jsiexecutor (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) - - React-cxxreact (= 0.78.0) - - React-jsi (= 0.78.0) + - RCT-Folly + - RCT-Folly/Fabric + - React-cxxreact + - React-debug + - React-jsi - React-jsinspector - - React-perflogger (= 0.78.0) - - React-jsinspector (0.78.0): + - React-jsinspectorcdp + - React-jsinspectortracing + - React-perflogger + - React-runtimeexecutor + - React-utils + - SocketRocket + - React-jsinspector (0.83.1): + - boost - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - RCT-Folly + - RCT-Folly/Fabric - React-featureflags - React-jsi + - React-jsinspectorcdp + - React-jsinspectornetwork - React-jsinspectortracing - - React-perflogger (= 0.78.0) - - React-runtimeexecutor (= 0.78.0) - - React-jsinspectortracing (0.78.0): + - React-oscompat + - React-perflogger (= 0.83.1) + - React-runtimeexecutor + - React-utils + - SocketRocket + - React-jsinspectorcdp (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - RCT-Folly + - RCT-Folly/Fabric + - SocketRocket + - React-jsinspectornetwork (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - RCT-Folly + - RCT-Folly/Fabric + - React-jsinspectorcdp + - SocketRocket + - React-jsinspectortracing (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - hermes-engine - RCT-Folly - - React-jsitracing (0.78.0): + - RCT-Folly/Fabric - React-jsi - - React-logger (0.78.0): + - React-jsinspectornetwork + - React-oscompat + - React-timing + - SocketRocket + - React-jsitooling (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt - glog - - React-Mapbuffer (0.78.0): + - RCT-Folly + - RCT-Folly/Fabric + - React-cxxreact (= 0.83.1) + - React-debug + - React-jsi (= 0.83.1) + - React-jsinspector + - React-jsinspectorcdp + - React-jsinspectortracing + - React-runtimeexecutor + - React-utils + - SocketRocket + - React-jsitracing (0.83.1): + - React-jsi + - React-logger (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt - glog + - RCT-Folly + - RCT-Folly/Fabric + - SocketRocket + - React-Mapbuffer (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - RCT-Folly + - RCT-Folly/Fabric - React-debug - - React-microtasksnativemodule (0.78.0): + - SocketRocket + - React-microtasksnativemodule (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog - hermes-engine - RCT-Folly + - RCT-Folly/Fabric - React-jsi - React-jsiexecutor - React-RCTFBReactNativeSpec - ReactCommon/turbomodule/core - - react-native-safe-area-context (5.3.0): + - SocketRocket + - react-native-safe-area-context (5.6.2): + - boost - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -1251,21 +1909,28 @@ PODS: - React-featureflags - React-graphics - React-ImageManager - - react-native-safe-area-context/common (= 5.3.0) - - react-native-safe-area-context/fabric (= 5.3.0) + - React-jsi + - react-native-safe-area-context/common (= 5.6.2) + - react-native-safe-area-context/fabric (= 5.6.2) - React-NativeModulesApple - React-RCTFabric + - React-renderercss - React-rendererdebug - React-utils - ReactCodegen - ReactCommon/turbomodule/bridging - ReactCommon/turbomodule/core + - SocketRocket - Yoga - - react-native-safe-area-context/common (5.3.0): + - react-native-safe-area-context/common (5.6.2): + - boost - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -1274,19 +1939,26 @@ PODS: - React-featureflags - React-graphics - React-ImageManager + - React-jsi - React-NativeModulesApple - React-RCTFabric + - React-renderercss - React-rendererdebug - React-utils - ReactCodegen - ReactCommon/turbomodule/bridging - ReactCommon/turbomodule/core + - SocketRocket - Yoga - - react-native-safe-area-context/fabric (5.3.0): + - react-native-safe-area-context/fabric (5.6.2): + - boost - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -1295,20 +1967,27 @@ PODS: - React-featureflags - React-graphics - React-ImageManager + - React-jsi - react-native-safe-area-context/common - React-NativeModulesApple - React-RCTFabric + - React-renderercss - React-rendererdebug - React-utils - ReactCodegen - ReactCommon/turbomodule/bridging - ReactCommon/turbomodule/core + - SocketRocket - Yoga - react-native-skia (0.0.0): + - boost - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React @@ -1319,46 +1998,116 @@ PODS: - React-featureflags - React-graphics - React-ImageManager + - React-jsi - React-NativeModulesApple - React-RCTFabric + - React-renderercss - React-rendererdebug - React-utils - ReactCodegen - ReactCommon/turbomodule/bridging - ReactCommon/turbomodule/core + - SocketRocket - Yoga - - React-NativeModulesApple (0.78.0): + - React-NativeModulesApple (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt - glog - hermes-engine + - RCT-Folly + - RCT-Folly/Fabric - React-callinvoker - React-Core - React-cxxreact + - React-debug + - React-featureflags - React-jsi - React-jsinspector + - React-jsinspectorcdp - React-runtimeexecutor - ReactCommon/turbomodule/bridging - ReactCommon/turbomodule/core - - React-perflogger (0.78.0): + - SocketRocket + - React-networking (0.83.1): + - boost - DoubleConversion - - RCT-Folly (= 2024.11.18.00) - - React-performancetimeline (0.78.0): - - RCT-Folly (= 2024.11.18.00) - - React-cxxreact + - fast_float + - fmt + - glog + - RCT-Folly + - RCT-Folly/Fabric - React-featureflags + - React-jsinspectornetwork - React-jsinspectortracing + - React-performancetimeline - React-timing - - React-RCTActionSheet (0.78.0): - - React-Core/RCTActionSheetHeaders (= 0.78.0) - - React-RCTAnimation (0.78.0): - - RCT-Folly (= 2024.11.18.00) + - SocketRocket + - React-oscompat (0.83.1) + - React-perflogger (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - RCT-Folly + - RCT-Folly/Fabric + - SocketRocket + - React-performancecdpmetrics (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - hermes-engine + - RCT-Folly + - RCT-Folly/Fabric + - React-jsi + - React-performancetimeline + - React-runtimeexecutor + - React-timing + - SocketRocket + - React-performancetimeline (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - RCT-Folly + - RCT-Folly/Fabric + - React-featureflags + - React-jsinspectortracing + - React-perflogger + - React-timing + - SocketRocket + - React-RCTActionSheet (0.83.1): + - React-Core/RCTActionSheetHeaders (= 0.83.1) + - React-RCTAnimation (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - RCT-Folly + - RCT-Folly/Fabric - RCTTypeSafety - React-Core/RCTAnimationHeaders + - React-featureflags - React-jsi - React-NativeModulesApple - React-RCTFBReactNativeSpec - ReactCommon - - React-RCTAppDelegate (0.78.0): - - RCT-Folly (= 2024.11.18.00) + - SocketRocket + - React-RCTAppDelegate (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - hermes-engine + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -1369,36 +2118,50 @@ PODS: - React-featureflags - React-graphics - React-hermes + - React-jsitooling - React-NativeModulesApple - React-RCTFabric - React-RCTFBReactNativeSpec - React-RCTImage - React-RCTNetwork + - React-RCTRuntime - React-rendererdebug - React-RuntimeApple - React-RuntimeCore - - React-RuntimeHermes + - React-runtimeexecutor - React-runtimescheduler - React-utils - ReactCommon - - React-RCTBlob (0.78.0): + - SocketRocket + - React-RCTBlob (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt + - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - React-Core/RCTBlobHeaders - React-Core/RCTWebSocket - React-jsi - React-jsinspector + - React-jsinspectorcdp - React-NativeModulesApple - React-RCTFBReactNativeSpec - React-RCTNetwork - ReactCommon - - React-RCTFabric (0.78.0): + - SocketRocket + - React-RCTFabric (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric + - RCTSwiftUIWrapper - React-Core - React-debug - React-Fabric @@ -1409,27 +2172,71 @@ PODS: - React-ImageManager - React-jsi - React-jsinspector + - React-jsinspectorcdp - React-jsinspectortracing + - React-networking + - React-performancecdpmetrics - React-performancetimeline + - React-RCTAnimation + - React-RCTFBReactNativeSpec - React-RCTImage - React-RCTText - React-rendererconsistency + - React-renderercss - React-rendererdebug + - React-runtimeexecutor - React-runtimescheduler - React-utils + - SocketRocket - Yoga - - React-RCTFBReactNativeSpec (0.78.0): + - React-RCTFBReactNativeSpec (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog - hermes-engine - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core - React-jsi - - React-jsiexecutor - React-NativeModulesApple + - React-RCTFBReactNativeSpec/components (= 0.83.1) + - ReactCommon + - SocketRocket + - React-RCTFBReactNativeSpec/components (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - hermes-engine + - RCT-Folly + - RCT-Folly/Fabric + - RCTRequired + - RCTTypeSafety + - React-Core + - React-debug + - React-Fabric + - React-featureflags + - React-graphics + - React-jsi + - React-NativeModulesApple + - React-rendererdebug + - React-utils - ReactCommon - - React-RCTImage (0.78.0): - - RCT-Folly (= 2024.11.18.00) + - SocketRocket + - Yoga + - React-RCTImage (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - RCT-Folly + - RCT-Folly/Fabric - RCTTypeSafety - React-Core/RCTImageHeaders - React-jsi @@ -1437,50 +2244,111 @@ PODS: - React-RCTFBReactNativeSpec - React-RCTNetwork - ReactCommon - - React-RCTLinking (0.78.0): - - React-Core/RCTLinkingHeaders (= 0.78.0) - - React-jsi (= 0.78.0) + - SocketRocket + - React-RCTLinking (0.83.1): + - React-Core/RCTLinkingHeaders (= 0.83.1) + - React-jsi (= 0.83.1) - React-NativeModulesApple - React-RCTFBReactNativeSpec - ReactCommon - - ReactCommon/turbomodule/core (= 0.78.0) - - React-RCTNetwork (0.78.0): - - RCT-Folly (= 2024.11.18.00) + - ReactCommon/turbomodule/core (= 0.83.1) + - React-RCTNetwork (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - RCT-Folly + - RCT-Folly/Fabric - RCTTypeSafety - React-Core/RCTNetworkHeaders + - React-debug + - React-featureflags - React-jsi + - React-jsinspectorcdp + - React-jsinspectornetwork - React-NativeModulesApple + - React-networking - React-RCTFBReactNativeSpec - ReactCommon - - React-RCTSettings (0.78.0): - - RCT-Folly (= 2024.11.18.00) + - SocketRocket + - React-RCTRuntime (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - hermes-engine + - RCT-Folly + - RCT-Folly/Fabric + - React-Core + - React-debug + - React-jsi + - React-jsinspector + - React-jsinspectorcdp + - React-jsinspectortracing + - React-jsitooling + - React-RuntimeApple + - React-RuntimeCore + - React-runtimeexecutor + - React-RuntimeHermes + - React-utils + - SocketRocket + - React-RCTSettings (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - RCT-Folly + - RCT-Folly/Fabric - RCTTypeSafety - React-Core/RCTSettingsHeaders - React-jsi - React-NativeModulesApple - React-RCTFBReactNativeSpec - ReactCommon - - React-RCTText (0.78.0): - - React-Core/RCTTextHeaders (= 0.78.0) + - SocketRocket + - React-RCTText (0.83.1): + - React-Core/RCTTextHeaders (= 0.83.1) - Yoga - - React-RCTVibration (0.78.0): - - RCT-Folly (= 2024.11.18.00) + - React-RCTVibration (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - RCT-Folly + - RCT-Folly/Fabric - React-Core/RCTVibrationHeaders - React-jsi - React-NativeModulesApple - React-RCTFBReactNativeSpec - ReactCommon - - React-rendererconsistency (0.78.0) - - React-rendererdebug (0.78.0): + - SocketRocket + - React-rendererconsistency (0.83.1) + - React-renderercss (0.83.1): + - React-debug + - React-utils + - React-rendererdebug (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) - - RCT-Folly (= 2024.11.18.00) + - fast_float + - fmt + - glog + - RCT-Folly + - RCT-Folly/Fabric - React-debug - - React-rncore (0.78.0) - - React-RuntimeApple (0.78.0): + - SocketRocket + - React-RuntimeApple (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - React-callinvoker - React-Core/Default - React-CoreModules @@ -1490,6 +2358,7 @@ PODS: - React-jsi - React-jsiexecutor - React-jsinspector + - React-jsitooling - React-Mapbuffer - React-NativeModulesApple - React-RCTFabric @@ -1499,10 +2368,16 @@ PODS: - React-RuntimeHermes - React-runtimescheduler - React-utils - - React-RuntimeCore (0.78.0): + - SocketRocket + - React-RuntimeCore (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - React-cxxreact - React-Fabric - React-featureflags @@ -1510,51 +2385,110 @@ PODS: - React-jsi - React-jsiexecutor - React-jsinspector + - React-jsitooling - React-performancetimeline - React-runtimeexecutor - React-runtimescheduler - React-utils - - React-runtimeexecutor (0.78.0): - - React-jsi (= 0.78.0) - - React-RuntimeHermes (0.78.0): + - SocketRocket + - React-runtimeexecutor (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - RCT-Folly + - RCT-Folly/Fabric + - React-debug + - React-featureflags + - React-jsi (= 0.83.1) + - React-utils + - SocketRocket + - React-RuntimeHermes (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog - hermes-engine - - RCT-Folly/Fabric (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - React-featureflags - React-hermes - React-jsi - React-jsinspector + - React-jsinspectorcdp + - React-jsinspectortracing + - React-jsitooling - React-jsitracing - React-RuntimeCore + - React-runtimeexecutor - React-utils - - React-runtimescheduler (0.78.0): + - SocketRocket + - React-runtimescheduler (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - React-callinvoker - React-cxxreact - React-debug - React-featureflags - React-jsi + - React-jsinspectortracing - React-performancetimeline - React-rendererconsistency - React-rendererdebug - React-runtimeexecutor - React-timing - React-utils - - React-timing (0.78.0) - - React-utils (0.78.0): + - SocketRocket + - React-timing (0.83.1): + - React-debug + - React-utils (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - React-debug - - React-jsi (= 0.78.0) - - ReactAppDependencyProvider (0.78.0): + - React-jsi (= 0.83.1) + - SocketRocket + - React-webperformancenativemodule (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - hermes-engine + - RCT-Folly + - RCT-Folly/Fabric + - React-cxxreact + - React-jsi + - React-jsiexecutor + - React-performancetimeline + - React-RCTFBReactNativeSpec + - React-runtimeexecutor + - ReactCommon/turbomodule/core + - SocketRocket + - ReactAppDependencyProvider (0.83.1): - ReactCodegen - - ReactCodegen (0.78.0): + - ReactCodegen (0.83.1): + - boost - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -1571,54 +2505,76 @@ PODS: - React-utils - ReactCommon/turbomodule/bridging - ReactCommon/turbomodule/core - - ReactCommon (0.78.0): - - ReactCommon/turbomodule (= 0.78.0) - - ReactCommon/turbomodule (0.78.0): + - SocketRocket + - ReactCommon (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt + - glog + - RCT-Folly + - RCT-Folly/Fabric + - ReactCommon/turbomodule (= 0.83.1) + - SocketRocket + - ReactCommon/turbomodule (0.83.1): + - boost + - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) - - React-callinvoker (= 0.78.0) - - React-cxxreact (= 0.78.0) - - React-jsi (= 0.78.0) - - React-logger (= 0.78.0) - - React-perflogger (= 0.78.0) - - ReactCommon/turbomodule/bridging (= 0.78.0) - - ReactCommon/turbomodule/core (= 0.78.0) - - ReactCommon/turbomodule/bridging (0.78.0): + - RCT-Folly + - RCT-Folly/Fabric + - React-callinvoker (= 0.83.1) + - React-cxxreact (= 0.83.1) + - React-jsi (= 0.83.1) + - React-logger (= 0.83.1) + - React-perflogger (= 0.83.1) + - ReactCommon/turbomodule/bridging (= 0.83.1) + - ReactCommon/turbomodule/core (= 0.83.1) + - SocketRocket + - ReactCommon/turbomodule/bridging (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) - - React-callinvoker (= 0.78.0) - - React-cxxreact (= 0.78.0) - - React-jsi (= 0.78.0) - - React-logger (= 0.78.0) - - React-perflogger (= 0.78.0) - - ReactCommon/turbomodule/core (0.78.0): + - RCT-Folly + - RCT-Folly/Fabric + - React-callinvoker (= 0.83.1) + - React-cxxreact (= 0.83.1) + - React-jsi (= 0.83.1) + - React-logger (= 0.83.1) + - React-perflogger (= 0.83.1) + - SocketRocket + - ReactCommon/turbomodule/core (0.83.1): + - boost - DoubleConversion - - fast_float (= 6.1.4) - - fmt (= 11.0.2) + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) - - React-callinvoker (= 0.78.0) - - React-cxxreact (= 0.78.0) - - React-debug (= 0.78.0) - - React-featureflags (= 0.78.0) - - React-jsi (= 0.78.0) - - React-logger (= 0.78.0) - - React-perflogger (= 0.78.0) - - React-utils (= 0.78.0) - - ReactNativeHost (0.5.12): + - RCT-Folly + - RCT-Folly/Fabric + - React-callinvoker (= 0.83.1) + - React-cxxreact (= 0.83.1) + - React-debug (= 0.83.1) + - React-featureflags (= 0.83.1) + - React-jsi (= 0.83.1) + - React-logger (= 0.83.1) + - React-perflogger (= 0.83.1) + - React-utils (= 0.83.1) + - SocketRocket + - ReactNativeHost (0.5.16): + - boost - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -1628,24 +2584,31 @@ PODS: - React-featureflags - React-graphics - React-ImageManager + - React-jsi - React-NativeModulesApple - React-RCTAppDelegate - React-RCTFabric + - React-renderercss - React-rendererdebug - React-utils - ReactCodegen - ReactCommon/turbomodule/bridging - ReactCommon/turbomodule/core + - SocketRocket - Yoga - ReactTestApp-DevSupport (4.4.7): - React-Core - React-jsi - ReactTestApp-Resources (1.0.0-dev) - - RNGestureHandler (2.25.0): + - RNGestureHandler (2.30.0): + - boost - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -1654,19 +2617,26 @@ PODS: - React-featureflags - React-graphics - React-ImageManager + - React-jsi - React-NativeModulesApple - React-RCTFabric + - React-renderercss - React-rendererdebug - React-utils - ReactCodegen - ReactCommon/turbomodule/bridging - ReactCommon/turbomodule/core + - SocketRocket - Yoga - - RNReanimated (3.19.1): + - RNReanimated (4.2.1): + - boost - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -1679,19 +2649,25 @@ PODS: - React-jsi - React-NativeModulesApple - React-RCTFabric + - React-renderercss - React-rendererdebug - React-utils - ReactCodegen - ReactCommon/turbomodule/bridging - ReactCommon/turbomodule/core - - RNReanimated/reanimated (= 3.19.1) - - RNReanimated/worklets (= 3.19.1) + - RNReanimated/reanimated (= 4.2.1) + - RNWorklets + - SocketRocket - Yoga - - RNReanimated/reanimated (3.19.1): + - RNReanimated/reanimated (4.2.1): + - boost - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -1704,18 +2680,25 @@ PODS: - React-jsi - React-NativeModulesApple - React-RCTFabric + - React-renderercss - React-rendererdebug - React-utils - ReactCodegen - ReactCommon/turbomodule/bridging - ReactCommon/turbomodule/core - - RNReanimated/reanimated/apple (= 3.19.1) + - RNReanimated/reanimated/apple (= 4.2.1) + - RNWorklets + - SocketRocket - Yoga - - RNReanimated/reanimated/apple (3.19.1): + - RNReanimated/reanimated/apple (4.2.1): + - boost - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -1728,17 +2711,24 @@ PODS: - React-jsi - React-NativeModulesApple - React-RCTFabric + - React-renderercss - React-rendererdebug - React-utils - ReactCodegen - ReactCommon/turbomodule/bridging - ReactCommon/turbomodule/core + - RNWorklets + - SocketRocket - Yoga - - RNReanimated/worklets (3.19.1): + - RNScreens (4.20.0): + - boost - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -1746,23 +2736,29 @@ PODS: - React-Fabric - React-featureflags - React-graphics - - React-hermes - React-ImageManager - React-jsi - React-NativeModulesApple - React-RCTFabric + - React-RCTImage + - React-renderercss - React-rendererdebug - React-utils - ReactCodegen - ReactCommon/turbomodule/bridging - ReactCommon/turbomodule/core - - RNReanimated/worklets/apple (= 3.19.1) + - RNScreens/common (= 4.20.0) + - SocketRocket - Yoga - - RNReanimated/worklets/apple (3.19.1): + - RNScreens/common (4.20.0): + - boost - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -1770,22 +2766,28 @@ PODS: - React-Fabric - React-featureflags - React-graphics - - React-hermes - React-ImageManager - React-jsi - React-NativeModulesApple - React-RCTFabric + - React-RCTImage + - React-renderercss - React-rendererdebug - React-utils - ReactCodegen - ReactCommon/turbomodule/bridging - ReactCommon/turbomodule/core + - SocketRocket - Yoga - - RNScreens (4.10.0): + - RNSVG (15.14.0): + - boost - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -1794,21 +2796,27 @@ PODS: - React-featureflags - React-graphics - React-ImageManager + - React-jsi - React-NativeModulesApple - React-RCTFabric - - React-RCTImage + - React-renderercss - React-rendererdebug - React-utils - ReactCodegen - ReactCommon/turbomodule/bridging - ReactCommon/turbomodule/core - - RNScreens/common (= 4.10.0) + - RNSVG/common (= 15.14.0) + - SocketRocket - Yoga - - RNScreens/common (4.10.0): + - RNSVG/common (15.14.0): + - boost - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -1817,20 +2825,26 @@ PODS: - React-featureflags - React-graphics - React-ImageManager + - React-jsi - React-NativeModulesApple - React-RCTFabric - - React-RCTImage + - React-renderercss - React-rendererdebug - React-utils - ReactCodegen - ReactCommon/turbomodule/bridging - ReactCommon/turbomodule/core + - SocketRocket - Yoga - - RNSVG (15.14.0): + - RNWorklets (0.7.1): + - boost - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -1838,21 +2852,59 @@ PODS: - React-Fabric - React-featureflags - React-graphics + - React-hermes - React-ImageManager + - React-jsi - React-NativeModulesApple - React-RCTFabric + - React-renderercss - React-rendererdebug - React-utils - ReactCodegen - ReactCommon/turbomodule/bridging - ReactCommon/turbomodule/core - - RNSVG/common (= 15.14.0) + - RNWorklets/worklets (= 0.7.1) + - SocketRocket - Yoga - - RNSVG/common (15.14.0): + - RNWorklets/worklets (0.7.1): + - boost + - DoubleConversion + - fast_float + - fmt + - glog + - hermes-engine + - RCT-Folly + - RCT-Folly/Fabric + - RCTRequired + - RCTTypeSafety + - React-Core + - React-debug + - React-Fabric + - React-featureflags + - React-graphics + - React-hermes + - React-ImageManager + - React-jsi + - React-NativeModulesApple + - React-RCTFabric + - React-renderercss + - React-rendererdebug + - React-utils + - ReactCodegen + - ReactCommon/turbomodule/bridging + - ReactCommon/turbomodule/core + - RNWorklets/worklets/apple (= 0.7.1) + - SocketRocket + - Yoga + - RNWorklets/worklets/apple (0.7.1): + - boost - DoubleConversion + - fast_float + - fmt - glog - hermes-engine - - RCT-Folly (= 2024.11.18.00) + - RCT-Folly + - RCT-Folly/Fabric - RCTRequired - RCTTypeSafety - React-Core @@ -1860,14 +2912,18 @@ PODS: - React-Fabric - React-featureflags - React-graphics + - React-hermes - React-ImageManager + - React-jsi - React-NativeModulesApple - React-RCTFabric + - React-renderercss - React-rendererdebug - React-utils - ReactCodegen - ReactCommon/turbomodule/bridging - ReactCommon/turbomodule/core + - SocketRocket - Yoga - SocketRocket (0.7.1) - Yoga (0.0.0) @@ -1881,9 +2937,10 @@ DEPENDENCIES: - glog (from `../../../node_modules/react-native/third-party-podspecs/glog.podspec`) - hermes-engine (from `../../../node_modules/react-native/sdks/hermes-engine/hermes-engine.podspec`) - RCT-Folly (from `../../../node_modules/react-native/third-party-podspecs/RCT-Folly.podspec`) - - RCT-Folly/Fabric (from `../../../node_modules/react-native/third-party-podspecs/RCT-Folly.podspec`) - RCTDeprecation (from `../../../node_modules/react-native/ReactApple/Libraries/RCTFoundation/RCTDeprecation`) - RCTRequired (from `../../../node_modules/react-native/Libraries/Required`) + - RCTSwiftUI (from `../../../node_modules/react-native/ReactApple/RCTSwiftUI`) + - RCTSwiftUIWrapper (from `../../../node_modules/react-native/ReactApple/RCTSwiftUIWrapper`) - RCTTypeSafety (from `../../../node_modules/react-native/Libraries/TypeSafety`) - React (from `../../../node_modules/react-native/`) - React-callinvoker (from `../../../node_modules/react-native/ReactCommon/callinvoker`) @@ -1903,11 +2960,15 @@ DEPENDENCIES: - React-hermes (from `../../../node_modules/react-native/ReactCommon/hermes`) - React-idlecallbacksnativemodule (from `../../../node_modules/react-native/ReactCommon/react/nativemodule/idlecallbacks`) - React-ImageManager (from `../../../node_modules/react-native/ReactCommon/react/renderer/imagemanager/platform/ios`) + - React-intersectionobservernativemodule (from `../../../node_modules/react-native/ReactCommon/react/nativemodule/intersectionobserver`) - React-jserrorhandler (from `../../../node_modules/react-native/ReactCommon/jserrorhandler`) - React-jsi (from `../../../node_modules/react-native/ReactCommon/jsi`) - React-jsiexecutor (from `../../../node_modules/react-native/ReactCommon/jsiexecutor`) - React-jsinspector (from `../../../node_modules/react-native/ReactCommon/jsinspector-modern`) + - React-jsinspectorcdp (from `../../../node_modules/react-native/ReactCommon/jsinspector-modern/cdp`) + - React-jsinspectornetwork (from `../../../node_modules/react-native/ReactCommon/jsinspector-modern/network`) - React-jsinspectortracing (from `../../../node_modules/react-native/ReactCommon/jsinspector-modern/tracing`) + - React-jsitooling (from `../../../node_modules/react-native/ReactCommon/jsitooling`) - React-jsitracing (from `../../../node_modules/react-native/ReactCommon/hermes/executor/`) - React-logger (from `../../../node_modules/react-native/ReactCommon/logger`) - React-Mapbuffer (from `../../../node_modules/react-native/ReactCommon`) @@ -1915,7 +2976,10 @@ DEPENDENCIES: - react-native-safe-area-context (from `../../../node_modules/react-native-safe-area-context`) - "react-native-skia (from `../../../node_modules/@shopify/react-native-skia`)" - React-NativeModulesApple (from `../../../node_modules/react-native/ReactCommon/react/nativemodule/core/platform/ios`) + - React-networking (from `../../../node_modules/react-native/ReactCommon/react/networking`) + - React-oscompat (from `../../../node_modules/react-native/ReactCommon/oscompat`) - React-perflogger (from `../../../node_modules/react-native/ReactCommon/reactperflogger`) + - React-performancecdpmetrics (from `../../../node_modules/react-native/ReactCommon/react/performance/cdpmetrics`) - React-performancetimeline (from `../../../node_modules/react-native/ReactCommon/react/performance/timeline`) - React-RCTActionSheet (from `../../../node_modules/react-native/Libraries/ActionSheetIOS`) - React-RCTAnimation (from `../../../node_modules/react-native/Libraries/NativeAnimation`) @@ -1926,12 +2990,13 @@ DEPENDENCIES: - React-RCTImage (from `../../../node_modules/react-native/Libraries/Image`) - React-RCTLinking (from `../../../node_modules/react-native/Libraries/LinkingIOS`) - React-RCTNetwork (from `../../../node_modules/react-native/Libraries/Network`) + - React-RCTRuntime (from `../../../node_modules/react-native/React/Runtime`) - React-RCTSettings (from `../../../node_modules/react-native/Libraries/Settings`) - React-RCTText (from `../../../node_modules/react-native/Libraries/Text`) - React-RCTVibration (from `../../../node_modules/react-native/Libraries/Vibration`) - React-rendererconsistency (from `../../../node_modules/react-native/ReactCommon/react/renderer/consistency`) + - React-renderercss (from `../../../node_modules/react-native/ReactCommon/react/renderer/css`) - React-rendererdebug (from `../../../node_modules/react-native/ReactCommon/react/renderer/debug`) - - React-rncore (from `../../../node_modules/react-native/ReactCommon`) - React-RuntimeApple (from `../../../node_modules/react-native/ReactCommon/react/runtime/platform/ios`) - React-RuntimeCore (from `../../../node_modules/react-native/ReactCommon/react/runtime`) - React-runtimeexecutor (from `../../../node_modules/react-native/ReactCommon/runtimeexecutor`) @@ -1939,16 +3004,19 @@ DEPENDENCIES: - React-runtimescheduler (from `../../../node_modules/react-native/ReactCommon/react/renderer/runtimescheduler`) - React-timing (from `../../../node_modules/react-native/ReactCommon/react/timing`) - React-utils (from `../../../node_modules/react-native/ReactCommon/react/utils`) - - ReactAppDependencyProvider (from `build/generated/ios`) - - ReactCodegen (from `build/generated/ios`) + - React-webperformancenativemodule (from `../../../node_modules/react-native/ReactCommon/react/nativemodule/webperformance`) + - ReactAppDependencyProvider (from `build/generated/ios/ReactAppDependencyProvider`) + - ReactCodegen (from `build/generated/ios/ReactCodegen`) - ReactCommon/turbomodule/core (from `../../../node_modules/react-native/ReactCommon`) - - "ReactNativeHost (from `../node_modules/@rnx-kit/react-native-host`)" + - "ReactNativeHost (from `../../../node_modules/@rnx-kit/react-native-host`)" - ReactTestApp-DevSupport (from `../node_modules/react-native-test-app`) - ReactTestApp-Resources (from `..`) - RNGestureHandler (from `../../../node_modules/react-native-gesture-handler`) - RNReanimated (from `../../../node_modules/react-native-reanimated`) - RNScreens (from `../../../node_modules/react-native-screens`) - RNSVG (from `../../../node_modules/react-native-svg`) + - RNWorklets (from `../../../node_modules/react-native-worklets`) + - SocketRocket (~> 0.7.1) - Yoga (from `../../../node_modules/react-native/ReactCommon/yoga`) SPEC REPOS: @@ -1970,13 +3038,17 @@ EXTERNAL SOURCES: :podspec: "../../../node_modules/react-native/third-party-podspecs/glog.podspec" hermes-engine: :podspec: "../../../node_modules/react-native/sdks/hermes-engine/hermes-engine.podspec" - :tag: hermes-2025-01-13-RNv0.78.0-a942ef374897d85da38e9c8904574f8376555388 + :tag: hermes-v0.14.0 RCT-Folly: :podspec: "../../../node_modules/react-native/third-party-podspecs/RCT-Folly.podspec" RCTDeprecation: :path: "../../../node_modules/react-native/ReactApple/Libraries/RCTFoundation/RCTDeprecation" RCTRequired: :path: "../../../node_modules/react-native/Libraries/Required" + RCTSwiftUI: + :path: "../../../node_modules/react-native/ReactApple/RCTSwiftUI" + RCTSwiftUIWrapper: + :path: "../../../node_modules/react-native/ReactApple/RCTSwiftUIWrapper" RCTTypeSafety: :path: "../../../node_modules/react-native/Libraries/TypeSafety" React: @@ -2013,6 +3085,8 @@ EXTERNAL SOURCES: :path: "../../../node_modules/react-native/ReactCommon/react/nativemodule/idlecallbacks" React-ImageManager: :path: "../../../node_modules/react-native/ReactCommon/react/renderer/imagemanager/platform/ios" + React-intersectionobservernativemodule: + :path: "../../../node_modules/react-native/ReactCommon/react/nativemodule/intersectionobserver" React-jserrorhandler: :path: "../../../node_modules/react-native/ReactCommon/jserrorhandler" React-jsi: @@ -2021,8 +3095,14 @@ EXTERNAL SOURCES: :path: "../../../node_modules/react-native/ReactCommon/jsiexecutor" React-jsinspector: :path: "../../../node_modules/react-native/ReactCommon/jsinspector-modern" + React-jsinspectorcdp: + :path: "../../../node_modules/react-native/ReactCommon/jsinspector-modern/cdp" + React-jsinspectornetwork: + :path: "../../../node_modules/react-native/ReactCommon/jsinspector-modern/network" React-jsinspectortracing: :path: "../../../node_modules/react-native/ReactCommon/jsinspector-modern/tracing" + React-jsitooling: + :path: "../../../node_modules/react-native/ReactCommon/jsitooling" React-jsitracing: :path: "../../../node_modules/react-native/ReactCommon/hermes/executor/" React-logger: @@ -2037,8 +3117,14 @@ EXTERNAL SOURCES: :path: "../../../node_modules/@shopify/react-native-skia" React-NativeModulesApple: :path: "../../../node_modules/react-native/ReactCommon/react/nativemodule/core/platform/ios" + React-networking: + :path: "../../../node_modules/react-native/ReactCommon/react/networking" + React-oscompat: + :path: "../../../node_modules/react-native/ReactCommon/oscompat" React-perflogger: :path: "../../../node_modules/react-native/ReactCommon/reactperflogger" + React-performancecdpmetrics: + :path: "../../../node_modules/react-native/ReactCommon/react/performance/cdpmetrics" React-performancetimeline: :path: "../../../node_modules/react-native/ReactCommon/react/performance/timeline" React-RCTActionSheet: @@ -2059,6 +3145,8 @@ EXTERNAL SOURCES: :path: "../../../node_modules/react-native/Libraries/LinkingIOS" React-RCTNetwork: :path: "../../../node_modules/react-native/Libraries/Network" + React-RCTRuntime: + :path: "../../../node_modules/react-native/React/Runtime" React-RCTSettings: :path: "../../../node_modules/react-native/Libraries/Settings" React-RCTText: @@ -2067,10 +3155,10 @@ EXTERNAL SOURCES: :path: "../../../node_modules/react-native/Libraries/Vibration" React-rendererconsistency: :path: "../../../node_modules/react-native/ReactCommon/react/renderer/consistency" + React-renderercss: + :path: "../../../node_modules/react-native/ReactCommon/react/renderer/css" React-rendererdebug: :path: "../../../node_modules/react-native/ReactCommon/react/renderer/debug" - React-rncore: - :path: "../../../node_modules/react-native/ReactCommon" React-RuntimeApple: :path: "../../../node_modules/react-native/ReactCommon/react/runtime/platform/ios" React-RuntimeCore: @@ -2085,14 +3173,16 @@ EXTERNAL SOURCES: :path: "../../../node_modules/react-native/ReactCommon/react/timing" React-utils: :path: "../../../node_modules/react-native/ReactCommon/react/utils" + React-webperformancenativemodule: + :path: "../../../node_modules/react-native/ReactCommon/react/nativemodule/webperformance" ReactAppDependencyProvider: - :path: build/generated/ios + :path: build/generated/ios/ReactAppDependencyProvider ReactCodegen: - :path: build/generated/ios + :path: build/generated/ios/ReactCodegen ReactCommon: :path: "../../../node_modules/react-native/ReactCommon" ReactNativeHost: - :path: "../node_modules/@rnx-kit/react-native-host" + :path: "../../../node_modules/@rnx-kit/react-native-host" ReactTestApp-DevSupport: :path: "../node_modules/react-native-test-app" ReactTestApp-Resources: @@ -2105,86 +3195,100 @@ EXTERNAL SOURCES: :path: "../../../node_modules/react-native-screens" RNSVG: :path: "../../../node_modules/react-native-svg" + RNWorklets: + :path: "../../../node_modules/react-native-worklets" Yoga: :path: "../../../node_modules/react-native/ReactCommon/yoga" SPEC CHECKSUMS: boost: 7e761d76ca2ce687f7cc98e698152abd03a18f90 DoubleConversion: cb417026b2400c8f53ae97020b2be961b59470cb - fast_float: 06eeec4fe712a76acc9376682e4808b05ce978b6 - FBLazyVector: 6fe148afcef2e3213e484758e3459609d40d57f5 + fast_float: b32c788ed9c6a8c584d114d0047beda9664e7cc6 + FBLazyVector: 309703e71d3f2f1ed7dc7889d58309c9d77a95a4 fmt: a40bb5bd0294ea969aaaba240a927bd33d878cdd - glog: eb93e2f488219332457c3c4eafd2738ddc7e80b8 - hermes-engine: b417d2b2aee3b89b58e63e23a51e02be91dc876d - RCT-Folly: e78785aa9ba2ed998ea4151e314036f6c49e6d82 - RCTDeprecation: b2eecf2d60216df56bc5e6be5f063826d3c1ee35 - RCTRequired: 78522de7dc73b81f3ed7890d145fa341f5bb32ea - RCTTypeSafety: c135dd2bf50402d87fd12884cbad5d5e64850edd - React: b229c49ed5898dab46d60f61ed5a0bfa2ee2fadb - React-callinvoker: 2ac508e92c8bd9cf834cc7d7787d94352e4af58f - React-Core: 325b4f6d9162ae8b9a6ff42fe78e260eb124180d - React-CoreModules: 558041e5258f70cd1092f82778d07b8b2ff01897 - React-cxxreact: 8fff17cbe76e6a8f9991b59552e1235429f9c74b - React-debug: 0a5fcdbacc6becba0521e910c1bcfdb20f32a3f6 - React-defaultsnativemodule: 618dc50a0fad41b489997c3eb7aba3a74479fd14 - React-domnativemodule: 7ba599afb6c2a7ec3eb6450153e2efe0b8747e9a - React-Fabric: 252112089d2c63308f4cbfade4010b6606db67d1 - React-FabricComponents: 3c0f75321680d14d124438ab279c64ec2a3d13c4 - React-FabricImage: 728b8061cdec2857ca885fd605ee03ad43ffca98 - React-featureflags: 19682e02ef5861d96b992af16a19109c3dfc1200 - React-featureflagsnativemodule: 23528c7e7d50782b7ef0804168ba40bbaf1e86ab - React-graphics: fefe48f71bfe6f48fd037f59e8277b12e91b6be1 - React-hermes: a9a0c8377627b5506ef9a7b6f60a805c306e3f51 - React-idlecallbacksnativemodule: 7e2b6a3b70e042f89cd91dbd73c479bb39a72a7e - React-ImageManager: e3300996ac2e2914bf821f71e2f2c92ae6e62ae2 - React-jserrorhandler: fa75876c662e5d7e79d6efc763fc9f4c88e26986 - React-jsi: f3f51595cc4c089037b536368f016d4742bf9cf7 - React-jsiexecutor: cca6c232db461e2fd213a11e9364cfa6fdaa20eb - React-jsinspector: 2bd4c9fddf189d6ec2abf4948461060502582bef - React-jsinspectortracing: a417d8a0ad481edaa415734b4dac81e3e5ee7dc6 - React-jsitracing: 1ff7172c5b0522cbf6c98d82bdbb160e49b5804e - React-logger: 018826bfd51b9f18e87f67db1590bc510ad20664 - React-Mapbuffer: 3c11cee7737609275c7b66bd0b1de475f094cedf - React-microtasksnativemodule: 843f352b32aacbe13a9c750190d34df44c3e6c2c - react-native-safe-area-context: 0f14bce545abcdfbff79ce2e3c78c109f0be283e - react-native-skia: dfaee9b8ed9f24b34902c0319eb3fa23dbfe242a - React-NativeModulesApple: 88433b6946778bea9c153e27b671de15411bf225 - React-perflogger: 9e8d3c0dc0194eb932162812a168aa5dc662f418 - React-performancetimeline: 5a2d6efef52bdcefac079c7baa30934978acd023 - React-RCTActionSheet: 592674cf61142497e0e820688f5a696e41bf16dd - React-RCTAnimation: e6d669872f9b3b4ab9527aab283b7c49283236b7 - React-RCTAppDelegate: de2343fe08be4c945d57e0ecce44afcc7dd8fc03 - React-RCTBlob: 3e2dce94c56218becc4b32b627fc2293149f798d - React-RCTFabric: cac2c033381d79a5956e08550b0220cb2d78ea93 - React-RCTFBReactNativeSpec: d10ca5e0ccbfeac8c047361fedf8e4ac653887b6 - React-RCTImage: dc04b176c022d12a8f55ae7a7279b1e091066ae0 - React-RCTLinking: 88f5e37fe4f26fbc80791aa2a5f01baf9b9a3fd5 - React-RCTNetwork: f213693565efbd698b8e9c18d700a514b49c0c8e - React-RCTSettings: a2d32a90c45a3575568cad850abc45924999b8a5 - React-RCTText: 54cdcd1cbf6f6a91dc6317f5d2c2b7fc3f6bf7a0 - React-RCTVibration: 11dae0e7f577b5807bb7d31e2e881eb46f854fd4 - React-rendererconsistency: 64e897e00d2568fd8dfe31e2496f80e85c0aaad1 - React-rendererdebug: 41ce452460c44bba715d9e41d5493a96de277764 - React-rncore: 58748c2aa445f56b99e5118dad0aedb51c40ce9f - React-RuntimeApple: 7785ed0d8ae54da65a88736bb63ca97608a6d933 - React-RuntimeCore: 6029ea70bc77f98cfd43ebe69217f14e93ba1f12 - React-runtimeexecutor: a188df372373baf5066e6e229177836488799f80 - React-RuntimeHermes: a264609c28b796edfffc8ae4cb8fad1773ab948b - React-runtimescheduler: 23ec3a1e0fb1ec752d1a9c1fb15258c30bfc7222 - React-timing: bb220a53a795ed57976a4855c521f3de2f298fe5 - React-utils: 3b054aaebe658fc710a8d239d0e4b9fd3e0b78f9 - ReactAppDependencyProvider: a1fb08dfdc7ebc387b2e54cfc9decd283ed821d8 - ReactCodegen: e232f8db3a40721044ec81b9388f95a7afaad36a - ReactCommon: 0c097b53f03d6bf166edbcd0915da32f3015dd90 - ReactNativeHost: 1b6ccdcfc87bb31e772a5b3c3ca3b09c90954328 + glog: 5683914934d5b6e4240e497e0f4a3b42d1854183 + hermes-engine: 11b010917f5f15150b2c015abddef1573d2bb05d + RCT-Folly: 846fda9475e61ec7bcbf8a3fe81edfcaeb090669 + RCTDeprecation: a41bbdd9af30bf2e5715796b313e44ec43eefff1 + RCTRequired: 7be34aabb0b77c3cefe644528df0fa0afad4e4d0 + RCTSwiftUI: a6c7271c39098bf00dbdad8f8ed997a59bbfbe44 + RCTSwiftUIWrapper: ff9098ccf7727e58218f2f8ea110349863f43438 + RCTTypeSafety: 27927d0ca04e419ed9467578b3e6297e37210b5c + React: 4bc1f928568ad4bcfd147260f907b4ea5873a03b + React-callinvoker: 87f8728235a0dc62e9dc19b3851c829d9347d015 + React-Core: 76bed73b02821e5630e7f2cb2e82432ee964695d + React-CoreModules: 752dbfdaeb096658aa0adc4a03ba6214815a08df + React-cxxreact: b6798528aa601c6db66e6adc7e2da2b059c8be74 + React-debug: 8978deb306f6f38c28b5091e52b0ac9f942b157e + React-defaultsnativemodule: 682b77ef4acfb298017be15f4f93c1d998deb174 + React-domnativemodule: 4c4b44f7eb68dbc3a2218db088bef318a7302017 + React-Fabric: b6f82a4d8498ce4475586f71ca8397a771fe292d + React-FabricComponents: c8695f4b11918a127c4560d66f7d3fdb01a17986 + React-FabricImage: d64f48830f63830e8ffaaf69fa487116856fbbf1 + React-featureflags: 2a46b229903e906d33dbaf9207ce57c59306c369 + React-featureflagsnativemodule: cba6c0814051a0934f8bcee4a436ee2a6bcc9754 + React-graphics: 3d0435051e1ab8904d065f8ffbe981a9fc202841 + React-hermes: 32fc9c231c1aa5c2fcfe851b0d19ee9269f88f4c + React-idlecallbacksnativemodule: f8ee42581795c4844d97147596bcc2d824c0f188 + React-ImageManager: e8f7377ef0585fd2df05559a17e01a03e187d5cf + React-intersectionobservernativemodule: b1bea12ca29accdd2eda60c87605a6030b894eb9 + React-jserrorhandler: 1a86df895b4eaf4e771abe8cf34cbb26d821f771 + React-jsi: adf8527fec197ad9d0480cc5b8945eb56de627f0 + React-jsiexecutor: 315fa2f879b43e3a9ca08f5f4b733472f7e4e8a4 + React-jsinspector: b4fd1933666bcb2549b566b40656c1e45e9d7632 + React-jsinspectorcdp: 80141710f2668e5b8f00417298d9b76b4abf90fa + React-jsinspectornetwork: 1d3ea717dbbec316cd8c21a0af53928a7bf74901 + React-jsinspectortracing: 4ce745374d4b2bfbd164cce9f8de8383d3d818a0 + React-jsitooling: fc4ac4c3b1f3f9f7fedf0c777c6ff3f244f568bd + React-jsitracing: bff08a6faeef4a9bd286487da191f5e5329e21a9 + React-logger: b8483fa08e0d62e430c76d864309d90576ca2f68 + React-Mapbuffer: 7b72a669e94662359dad4f42b5af005eb24b4e83 + React-microtasksnativemodule: cdc02da075f2857803ed63f24f5f72fc40e094c0 + react-native-safe-area-context: c00143b4823773bba23f2f19f85663ae89ceb460 + react-native-skia: c4007b72a1ce079c5e0862d065f3bc7b48a9105c + React-NativeModulesApple: a2c3d2cbec893956a5b3e4060322db2984fff75b + React-networking: 3f98bd96893a294376e7e03730947a08d474c380 + React-oscompat: 80166b66da22e7af7fad94474e9997bd52d4c8c6 + React-perflogger: d6797918d2b1031e91a9d8f5e7fdd2c8728fb390 + React-performancecdpmetrics: 5570be61e2f97c4741c5d432c91570e8e5a39892 + React-performancetimeline: 5763499ae1991fc18dcf416e340ce7bc829bb298 + React-RCTActionSheet: 3bd5f5db9f983cf38d51bb9a7a198e2ebea94821 + React-RCTAnimation: 46a9978f27dc434dbeed16afa7b82619b690a9af + React-RCTAppDelegate: 62ecd60a2b2a8cae26ce6a066bfa59cfde97af01 + React-RCTBlob: 8285c859513023ee3cc8c806d9b59d4da078c4ba + React-RCTFabric: 05ed09347e938de985052f791a6a0698816d5761 + React-RCTFBReactNativeSpec: 83ba579fca9a51e774ac32578ef5dd3262edd7e2 + React-RCTImage: a5364d0f098692cfbf5bef1e8a63e7712ecb14b7 + React-RCTLinking: 34b63b0aa0e92d30f5d7aa2c255a8f95fa75ee8f + React-RCTNetwork: 1ef88b7a5310b8f915d3556b5b247def113191ed + React-RCTRuntime: ed29cf68a46782fec891e5afe1d8d758ca6ccd9b + React-RCTSettings: 2c45623d6c0f30851a123f621eb9d32298bcbb0c + React-RCTText: 0ee70f5dc18004b4d81b2c214267c6cbec058587 + React-RCTVibration: 88557e21e7cc3fe76b5b174cba28ff45c6def997 + React-rendererconsistency: d280314a3e7f0097152f89e815b4de821c2be8b9 + React-renderercss: f8cbf83d95c2c2bbf893d37fe50c73f046584411 + React-rendererdebug: 37216ddfcd38e49d1e92bf9052ea4bc9d7b932e5 + React-RuntimeApple: 1c0e7cb8e1c2c5775585afcaaa666ec151629a8d + React-RuntimeCore: 925fe2ca24cf8e6ed87586dbb92827306b93b83f + React-runtimeexecutor: 962dae024f6df760d029512a7d99e3f73d570935 + React-RuntimeHermes: 19a7c59ec1bc9908516f0bbc29b49425f6ec64ba + React-runtimescheduler: 62f21127cd97f4d8f164eee5150d3ce53dd36f66 + React-timing: 8757bf6fb96227c264f2d1609f4ba5c68217b8ce + React-utils: 8ab26781c2f5c2f7fafb2022c8ab39d39f231b80 + React-webperformancenativemodule: 7953b7fe519f76fa595111fe18ff3d5de131bfe9 + ReactAppDependencyProvider: 0eb286cc274abb059ee601b862ebddac2e681d01 + ReactCodegen: b8e56b780fffe6edd6405be0af4a1e3049a937f7 + ReactCommon: ac934cb340aee91282ecd6f273a26d24d4c55cae + ReactNativeHost: eef98ec49b55d88ad4cabf5a4378a12b42b551ee ReactTestApp-DevSupport: ea18f446cff64b6c9a3e28788600c82ecf51bde6 ReactTestApp-Resources: 1bd9ff10e4c24f2ad87101a32023721ae923bccf - RNGestureHandler: dcb1b1db024f3744b03af56d132f4f72c4c27195 - RNReanimated: d5f33d14a4d1da33a02d89124de233a64b3aaeaa - RNScreens: 790123c4a28783d80a342ce42e8c7381bed62db1 - RNSVG: 05a9310dfd69f18a69f6aa7ba5ddaa44bf24fd1c + RNGestureHandler: cd4be101cfa17ea6bbd438710caa02e286a84381 + RNReanimated: 132940c4c15ca2757f4f7d1fd7c9c3c01dbc4689 + RNScreens: 714e10b6b554f7dc7ad9f78dcf36dc8e3fc73415 + RNSVG: 11354d28dd6cb71a59570b68c91ba6772a2d781d + RNWorklets: f2ed333c600377955ac5ab798a14210805de846d SocketRocket: d4aabe649be1e368d1318fdf28a022d714d65748 - Yoga: afd04ff05ebe0121a00c468a8a3c8080221cb14c + Yoga: 5456bb010373068fc92221140921b09d126b116e PODFILE CHECKSUM: 87506345285a0371afb28b9c3e6daaa999c214f3 diff --git a/apps/example/src/App.tsx b/apps/example/src/App.tsx index a03b723bb8..c737980c82 100644 --- a/apps/example/src/App.tsx +++ b/apps/example/src/App.tsx @@ -112,7 +112,7 @@ const App = () => { screenOptions={{ headerLeft: HeaderLeft, }} - initialRouteName={CI ? "Tests" : "Home"} + initialRouteName={CI ? "Tests" : "WebGPU"} > uniforms : Uniforms; + +struct VertexOutput { + @builtin(position) Position : vec4f, + @location(0) fragUV : vec2f, + @location(1) fragPosition: vec4f, +} + +@vertex +fn main( + @location(0) position : vec4f, + @location(1) uv : vec2f +) -> VertexOutput { + var output : VertexOutput; + output.Position = uniforms.modelViewProjectionMatrix * position; + output.fragUV = uv; + output.fragPosition = 0.5 * (position + vec4(1.0, 1.0, 1.0, 1.0)); + return output; +} +`; + +export const sampleTextureMixColorWGSL = /* wgsl */ `@group(0) @binding(1) var mySampler: sampler; +@group(0) @binding(2) var myTexture: texture_2d; + +@fragment +fn main( + @location(0) fragUV: vec2f, + @location(1) fragPosition: vec4f +) -> @location(0) vec4f { + return textureSample(myTexture, mySampler, fragUV) * fragPosition; +} +`; + export const wireframeWGSL = /*wgsl*/ `struct Uniforms { worldViewProjectionMatrix: mat4x4f, worldMatrix: mat4x4f, diff --git a/apps/example/src/Examples/WebGPU/TexturedCube.tsx b/apps/example/src/Examples/WebGPU/TexturedCube.tsx new file mode 100644 index 0000000000..5dc60c2cde --- /dev/null +++ b/apps/example/src/Examples/WebGPU/TexturedCube.tsx @@ -0,0 +1,301 @@ +import React, { useEffect, useRef } from "react"; +import { StyleSheet, View, Text } from "react-native"; +import type { WebGPUCanvasRef } from "@shopify/react-native-skia"; +import { WebGPUCanvas, Skia } from "@shopify/react-native-skia"; + +import { + cubePositionOffset, + cubeUVOffset, + cubeVertexArray, + cubeVertexCount, + cubeVertexSize, +} from "./cube"; +import { basicVertWGSL, sampleTextureMixColorWGSL } from "./Shaders"; +import { + mat4Identity, + mat4Multiply, + mat4Perspective, + mat4Rotate, + mat4Translate, + type Mat4, + type Vec3, +} from "./matrix"; + +export function TexturedCube() { + const canvasRef = useRef(null); + const animationRef = useRef(0); + const cleanupRef = useRef<(() => void) | null>(null); + + useEffect(() => { + const timeoutId = setTimeout(async () => { + if (!canvasRef.current) { + return; + } + + if (typeof RNWebGPU === "undefined") { + console.warn( + "RNWebGPU is not available. Make sure SK_GRAPHITE is enabled." + ); + return; + } + + const ctx = canvasRef.current.getContext("webgpu"); + if (!ctx) { + console.warn("Failed to get WebGPU context"); + return; + } + + const device = Skia.getDevice(); + const canvas = ctx.canvas as HTMLCanvasElement; + const presentationFormat = navigator.gpu.getPreferredCanvasFormat(); + + ctx.configure({ + device, + format: presentationFormat, + alphaMode: "premultiplied", + }); + + // Create a vertex buffer from the cube data. + const verticesBuffer = device.createBuffer({ + size: cubeVertexArray.byteLength, + usage: GPUBufferUsage.VERTEX, + mappedAtCreation: true, + }); + new Float32Array(verticesBuffer.getMappedRange()).set(cubeVertexArray); + verticesBuffer.unmap(); + + const pipeline = device.createRenderPipeline({ + layout: "auto", + vertex: { + module: device.createShaderModule({ + code: basicVertWGSL, + }), + buffers: [ + { + arrayStride: cubeVertexSize, + attributes: [ + { + // position + shaderLocation: 0, + offset: cubePositionOffset, + format: "float32x4", + }, + { + // uv + shaderLocation: 1, + offset: cubeUVOffset, + format: "float32x2", + }, + ], + }, + ], + }, + fragment: { + module: device.createShaderModule({ + code: sampleTextureMixColorWGSL, + }), + targets: [ + { + format: presentationFormat, + }, + ], + }, + primitive: { + topology: "triangle-list", + cullMode: "back", + }, + depthStencil: { + depthWriteEnabled: true, + depthCompare: "less", + format: "depth24plus", + }, + }); + + const depthTexture = device.createTexture({ + size: [canvas.width, canvas.height], + format: "depth24plus", + usage: GPUTextureUsage.RENDER_ATTACHMENT, + }); + + const uniformBufferSize = 4 * 16; // 4x4 matrix + const uniformBuffer = device.createBuffer({ + size: uniformBufferSize, + usage: GPUBufferUsage.UNIFORM | GPUBufferUsage.COPY_DST, + }); + + // Create a Skia offscreen drawing and convert to a GPUTexture. + const textureSize = 512; + const surface = Skia.Surface.MakeOffscreen(textureSize, textureSize)!; + const skCanvas = surface.getCanvas(); + skCanvas.drawColor(Skia.Color("pink")); + const paint = Skia.Paint(); + paint.setColor(Skia.Color("cyan")); + skCanvas.drawCircle(256, 256, 200, paint); + surface.flush(); + const skImage = surface.makeImageSnapshot(); + const cubeTexture = Skia.Image.MakeTextureFromImage(skImage); + + // Create a sampler with linear filtering for smooth interpolation. + const sampler = device.createSampler({ + magFilter: "linear", + minFilter: "linear", + }); + + const uniformBindGroup = device.createBindGroup({ + layout: pipeline.getBindGroupLayout(0), + entries: [ + { + binding: 0, + resource: { + buffer: uniformBuffer, + }, + }, + { + binding: 1, + resource: sampler, + }, + { + binding: 2, + resource: cubeTexture.createView(), + }, + ], + }); + + const renderPassDescriptor: GPURenderPassDescriptor = { + colorAttachments: [ + { + // eslint-disable-next-line @typescript-eslint/no-explicit-any + view: undefined as any, + clearValue: [0.5, 0.5, 0.5, 1.0], + loadOp: "clear", + storeOp: "store", + }, + ], + depthStencilAttachment: { + view: depthTexture.createView(), + depthClearValue: 1.0, + depthLoadOp: "clear", + depthStoreOp: "store", + }, + }; + + const aspect = canvas.width / canvas.height; + const projectionMatrix = mat4Perspective( + (2 * Math.PI) / 5, + aspect, + 1, + 100.0 + ); + const modelViewProjectionMatrix = mat4Identity(); + + function getTransformationMatrix(): Mat4 { + const viewMatrix = mat4Identity(); + mat4Translate(viewMatrix, [0, 0, -4] as Vec3, viewMatrix); + const now = Date.now() / 1000; + mat4Rotate( + viewMatrix, + [Math.sin(now), Math.cos(now), 0] as Vec3, + 1, + viewMatrix + ); + mat4Multiply(projectionMatrix, viewMatrix, modelViewProjectionMatrix); + return modelViewProjectionMatrix; + } + + let running = true; + + const render = () => { + if (!running) { + return; + } + + const transformationMatrix = getTransformationMatrix(); + device.queue.writeBuffer( + uniformBuffer, + 0, + transformationMatrix.buffer, + transformationMatrix.byteOffset, + transformationMatrix.byteLength + ); + + // eslint-disable-next-line @typescript-eslint/no-explicit-any + (renderPassDescriptor.colorAttachments as any)[0].view = ctx + .getCurrentTexture() + .createView(); + + const commandEncoder = device.createCommandEncoder(); + const passEncoder = + commandEncoder.beginRenderPass(renderPassDescriptor); + passEncoder.setPipeline(pipeline); + passEncoder.setBindGroup(0, uniformBindGroup); + passEncoder.setVertexBuffer(0, verticesBuffer); + passEncoder.draw(cubeVertexCount); + passEncoder.end(); + device.queue.submit([commandEncoder.finish()]); + ctx.present(); + + animationRef.current = requestAnimationFrame(render); + }; + + animationRef.current = requestAnimationFrame(render); + + cleanupRef.current = () => { + running = false; + cancelAnimationFrame(animationRef.current); + }; + }, 100); + + return () => { + clearTimeout(timeoutId); + cleanupRef.current?.(); + }; + }, []); + + if (typeof RNWebGPU === "undefined") { + return ( + + + + WebGPU Canvas requires SK_GRAPHITE to be enabled. + + + Build react-native-skia with Graphite support to use this feature. + + + + ); + } + + return ( + + + + ); +} + +const styles = StyleSheet.create({ + container: { + flex: 1, + backgroundColor: "#1a1a1a", + }, + canvas: { + flex: 1, + }, + messageContainer: { + flex: 1, + justifyContent: "center", + alignItems: "center", + padding: 20, + }, + message: { + color: "#fff", + fontSize: 18, + textAlign: "center", + marginBottom: 10, + }, + submessage: { + color: "#888", + fontSize: 14, + textAlign: "center", + }, +}); diff --git a/apps/example/src/Examples/WebGPU/assets/Di-3d.png b/apps/example/src/Examples/WebGPU/assets/Di-3d.png new file mode 100644 index 0000000000000000000000000000000000000000..ebbff45ead2a90ccb1cead28fbf25c157df23af9 GIT binary patch literal 243533 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 z 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%0D`Jt#M1EoSdDb}(CMblt! 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

50J_F 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 @@ -34,6 +35,13 @@ export const WebGPU = () => { header: () => null, }} /> + ); }; diff --git a/apps/example/src/Examples/WebGPU/matrix.ts b/apps/example/src/Examples/WebGPU/matrix.ts index f7fc215227..6b202f66ce 100644 --- a/apps/example/src/Examples/WebGPU/matrix.ts +++ b/apps/example/src/Examples/WebGPU/matrix.ts @@ -216,6 +216,60 @@ export function mat4RotateY(m: Mat4, angle: number, dst?: Mat4): Mat4 { return dst; } +export function mat4Rotate(m: Mat4, axis: Vec3, angle: number, dst?: Mat4): Mat4 { + dst = dst || new Float32Array(16); + let x = axis[0], + y = axis[1], + z = axis[2]; + const len = Math.sqrt(x * x + y * y + z * z); + if (len === 0) { + return m; + } + x /= len; + y /= len; + z /= len; + + const s = Math.sin(angle); + const c = Math.cos(angle); + const t = 1 - c; + + const r00 = t * x * x + c; + const r01 = t * x * y + s * z; + const r02 = t * x * z - s * y; + const r10 = t * x * y - s * z; + const r11 = t * y * y + c; + const r12 = t * y * z + s * x; + const r20 = t * x * z + s * y; + const r21 = t * y * z - s * x; + const r22 = t * z * z + c; + + const m00 = m[0], m01 = m[1], m02 = m[2], m03 = m[3]; + const m10 = m[4], m11 = m[5], m12 = m[6], m13 = m[7]; + const m20 = m[8], m21 = m[9], m22 = m[10], m23 = m[11]; + + dst[0] = m00 * r00 + m10 * r01 + m20 * r02; + dst[1] = m01 * r00 + m11 * r01 + m21 * r02; + dst[2] = m02 * r00 + m12 * r01 + m22 * r02; + dst[3] = m03 * r00 + m13 * r01 + m23 * r02; + dst[4] = m00 * r10 + m10 * r11 + m20 * r12; + dst[5] = m01 * r10 + m11 * r11 + m21 * r12; + dst[6] = m02 * r10 + m12 * r11 + m22 * r12; + dst[7] = m03 * r10 + m13 * r11 + m23 * r12; + dst[8] = m00 * r20 + m10 * r21 + m20 * r22; + dst[9] = m01 * r20 + m11 * r21 + m21 * r22; + dst[10] = m02 * r20 + m12 * r21 + m22 * r22; + dst[11] = m03 * r20 + m13 * r21 + m23 * r22; + + if (dst !== m) { + dst[12] = m[12]; + dst[13] = m[13]; + dst[14] = m[14]; + dst[15] = m[15]; + } + + return dst; +} + export function mat3FromMat4(m: Mat4, dst?: Float32Array): Float32Array { dst = dst || new Float32Array(12); dst[0] = m[0]; diff --git a/packages/skia/package.json b/packages/skia/package.json index 84c5a47585..6bcc6250f4 100644 --- a/packages/skia/package.json +++ b/packages/skia/package.json @@ -24,12 +24,12 @@ "skia-graphite": { "version": "m142b", "checksums": { - "android-armeabi-v7a": "3e40f44c804194fa0983c46903f834e8f834c6dd96534c7fa1b4ebb4f409527d", - "android-arm64-v8a": "d6c3035449fcf7ef13369b0d6c4ef41f3177d15074eeb195201e0ba4cfb2f527", - "android-x86": "6dc229847420b8a43c15098cdcb4fe45b2df20a38ad69f37e0aa91c832499c2a", - "android-x86_64": "ecae351d98af3b175d40d894520c2e3263034276bb0b0e9d2f9c19ba7dc046fa", - "apple-ios-xcframeworks": "6f60f03faaeebfb798615d09715040790ff95e75bf95028893ced6f514ab5196", - "apple-macos-xcframeworks": "07467cd1778053537528ed91c7a35d116e1a4644819f0aad8e06e7d884591dea" + "android-armeabi-v7a": "b3db57a758482d479d07a5a31dd46492b5ca58de1cdcb9fbba1f71879561057a", + "android-arm64-v8a": "099cb2491723f05bcf44fc2af7b4d33d80b3768dc4be8609d7bd2102efce8e4f", + "android-x86": "bcbeb88d1e484b64f6f87722405a9d0319ba1795b85ef3ddd3a673412dfd505f", + "android-x86_64": "285448b69b18d619f6d468461c928931ab85b73dc90c4675ffb60a336c2c78d9", + "apple-ios-xcframeworks": "5efb7b78b3e748d05f1a79ff4be4561af1a49ef178a46ace319eaa75ece0f27f", + "apple-macos-xcframeworks": "1ded51aa285b1925e2ead8a118a01a2775e0c3f940e01263262358e58fdb9b77" } }, "description": "High-performance React Native Graphics using Skia", From ca608d48cec8ec9b52acfd1da40c498e41fa350f Mon Sep 17 00:00:00 2001 From: William Candillon Date: Mon, 9 Feb 2026 10:28:27 +0100 Subject: [PATCH 03/10] :wrench: --- .../src/Examples/WebGPU/TexturedCube.tsx | 97 +++++++++++++------ 1 file changed, 67 insertions(+), 30 deletions(-) diff --git a/apps/example/src/Examples/WebGPU/TexturedCube.tsx b/apps/example/src/Examples/WebGPU/TexturedCube.tsx index 5dc60c2cde..0769732266 100644 --- a/apps/example/src/Examples/WebGPU/TexturedCube.tsx +++ b/apps/example/src/Examples/WebGPU/TexturedCube.tsx @@ -7,7 +7,6 @@ import { cubePositionOffset, cubeUVOffset, cubeVertexArray, - cubeVertexCount, cubeVertexSize, } from "./cube"; import { basicVertWGSL, sampleTextureMixColorWGSL } from "./Shaders"; @@ -123,17 +122,31 @@ export function TexturedCube() { usage: GPUBufferUsage.UNIFORM | GPUBufferUsage.COPY_DST, }); - // Create a Skia offscreen drawing and convert to a GPUTexture. + // Create two Skia offscreen surfaces for the cube textures. const textureSize = 512; - const surface = Skia.Surface.MakeOffscreen(textureSize, textureSize)!; - const skCanvas = surface.getCanvas(); - skCanvas.drawColor(Skia.Color("pink")); + const surface1 = Skia.Surface.MakeOffscreen(textureSize, textureSize)!; + const surface2 = Skia.Surface.MakeOffscreen(textureSize, textureSize)!; const paint = Skia.Paint(); - paint.setColor(Skia.Color("cyan")); - skCanvas.drawCircle(256, 256, 200, paint); - surface.flush(); - const skImage = surface.makeImageSnapshot(); - const cubeTexture = Skia.Image.MakeTextureFromImage(skImage); + + // Draw on surface 1 — customize this per frame below. + function drawTexture1(t: number) { + const c = surface1.getCanvas(); + c.drawColor(Skia.Color("cyan")); + paint.setColor(Skia.Color("white")); + const r = 100 + Math.sin(t * 2) * 80; + c.drawCircle(256, 256, r, paint); + surface1.flush(); + } + + // Draw on surface 2 — customize this per frame below. + function drawTexture2(t: number) { + const c = surface2.getCanvas(); + c.drawColor(Skia.Color("pink")); + paint.setColor(Skia.Color("black")); + const x = 256 + Math.cos(t * 3) * 100; + c.drawCircle(x, 256, 80, paint); + surface2.flush(); + } // Create a sampler with linear filtering for smooth interpolation. const sampler = device.createSampler({ @@ -141,25 +154,27 @@ export function TexturedCube() { minFilter: "linear", }); - const uniformBindGroup = device.createBindGroup({ - layout: pipeline.getBindGroupLayout(0), - entries: [ - { - binding: 0, - resource: { - buffer: uniformBuffer, + const bindGroupLayout = pipeline.getBindGroupLayout(0); + + function createBindGroup(texture: GPUTexture) { + return device.createBindGroup({ + layout: bindGroupLayout, + entries: [ + { + binding: 0, + resource: { buffer: uniformBuffer }, }, - }, - { - binding: 1, - resource: sampler, - }, - { - binding: 2, - resource: cubeTexture.createView(), - }, - ], - }); + { + binding: 1, + resource: sampler, + }, + { + binding: 2, + resource: texture.createView(), + }, + ], + }); + } const renderPassDescriptor: GPURenderPassDescriptor = { colorAttachments: [ @@ -209,6 +224,21 @@ export function TexturedCube() { return; } + const t = Date.now() / 1000; + + // Update Skia drawings each frame + drawTexture1(t); + const tex1 = Skia.Image.MakeTextureFromImage( + surface1.makeImageSnapshot() + ); + const bindGroup1 = createBindGroup(tex1); + + drawTexture2(t); + const tex2 = Skia.Image.MakeTextureFromImage( + surface2.makeImageSnapshot() + ); + const bindGroup2 = createBindGroup(tex2); + const transformationMatrix = getTransformationMatrix(); device.queue.writeBuffer( uniformBuffer, @@ -227,9 +257,16 @@ export function TexturedCube() { const passEncoder = commandEncoder.beginRenderPass(renderPassDescriptor); passEncoder.setPipeline(pipeline); - passEncoder.setBindGroup(0, uniformBindGroup); passEncoder.setVertexBuffer(0, verticesBuffer); - passEncoder.draw(cubeVertexCount); + + // First 3 faces (18 vertices) with texture 1 + passEncoder.setBindGroup(0, bindGroup1); + passEncoder.draw(18, 1, 0, 0); + + // Last 3 faces (18 vertices) with texture 2 + passEncoder.setBindGroup(0, bindGroup2); + passEncoder.draw(18, 1, 18, 0); + passEncoder.end(); device.queue.submit([commandEncoder.finish()]); ctx.present(); From 02510aa5a60389d67da0c64d807cea9d993f2362 Mon Sep 17 00:00:00 2001 From: William Candillon Date: Mon, 9 Feb 2026 10:54:51 +0100 Subject: [PATCH 04/10] :wrench: --- .../src/Examples/WebGPU/TexturedCube.tsx | 145 +++++++----------- 1 file changed, 53 insertions(+), 92 deletions(-) diff --git a/apps/example/src/Examples/WebGPU/TexturedCube.tsx b/apps/example/src/Examples/WebGPU/TexturedCube.tsx index 0769732266..2125e3be73 100644 --- a/apps/example/src/Examples/WebGPU/TexturedCube.tsx +++ b/apps/example/src/Examples/WebGPU/TexturedCube.tsx @@ -1,6 +1,6 @@ import React, { useEffect, useRef } from "react"; import { StyleSheet, View, Text } from "react-native"; -import type { WebGPUCanvasRef } from "@shopify/react-native-skia"; +import type { SkCanvas, WebGPUCanvasRef } from "@shopify/react-native-skia"; import { WebGPUCanvas, Skia } from "@shopify/react-native-skia"; import { @@ -20,6 +20,23 @@ import { type Vec3, } from "./matrix"; +const TEXTURE_SIZE = 512; +const paint = Skia.Paint(); + +function drawTexture1(canvas: SkCanvas, t: number) { + canvas.drawColor(Skia.Color("cyan")); + paint.setColor(Skia.Color("white")); + const r = 100 + Math.sin(t * 2) * 80; + canvas.drawCircle(256, 256, r, paint); +} + +function drawTexture2(canvas: SkCanvas, t: number) { + canvas.drawColor(Skia.Color("pink")); + paint.setColor(Skia.Color("black")); + const x = 256 + Math.cos(t * 3) * 100; + canvas.drawCircle(x, 256, 80, paint); +} + export function TexturedCube() { const canvasRef = useRef(null); const animationRef = useRef(0); @@ -30,17 +47,11 @@ export function TexturedCube() { if (!canvasRef.current) { return; } - if (typeof RNWebGPU === "undefined") { - console.warn( - "RNWebGPU is not available. Make sure SK_GRAPHITE is enabled." - ); return; } - const ctx = canvasRef.current.getContext("webgpu"); if (!ctx) { - console.warn("Failed to get WebGPU context"); return; } @@ -54,7 +65,6 @@ export function TexturedCube() { alphaMode: "premultiplied", }); - // Create a vertex buffer from the cube data. const verticesBuffer = device.createBuffer({ size: cubeVertexArray.byteLength, usage: GPUBufferUsage.VERTEX, @@ -66,21 +76,17 @@ export function TexturedCube() { const pipeline = device.createRenderPipeline({ layout: "auto", vertex: { - module: device.createShaderModule({ - code: basicVertWGSL, - }), + module: device.createShaderModule({ code: basicVertWGSL }), buffers: [ { arrayStride: cubeVertexSize, attributes: [ { - // position shaderLocation: 0, offset: cubePositionOffset, format: "float32x4", }, { - // uv shaderLocation: 1, offset: cubeUVOffset, format: "float32x2", @@ -93,16 +99,9 @@ export function TexturedCube() { module: device.createShaderModule({ code: sampleTextureMixColorWGSL, }), - targets: [ - { - format: presentationFormat, - }, - ], - }, - primitive: { - topology: "triangle-list", - cullMode: "back", + targets: [{ format: presentationFormat }], }, + primitive: { topology: "triangle-list", cullMode: "back" }, depthStencil: { depthWriteEnabled: true, depthCompare: "less", @@ -116,39 +115,14 @@ export function TexturedCube() { usage: GPUTextureUsage.RENDER_ATTACHMENT, }); - const uniformBufferSize = 4 * 16; // 4x4 matrix const uniformBuffer = device.createBuffer({ - size: uniformBufferSize, + size: 4 * 16, usage: GPUBufferUsage.UNIFORM | GPUBufferUsage.COPY_DST, }); - // Create two Skia offscreen surfaces for the cube textures. - const textureSize = 512; - const surface1 = Skia.Surface.MakeOffscreen(textureSize, textureSize)!; - const surface2 = Skia.Surface.MakeOffscreen(textureSize, textureSize)!; - const paint = Skia.Paint(); - - // Draw on surface 1 — customize this per frame below. - function drawTexture1(t: number) { - const c = surface1.getCanvas(); - c.drawColor(Skia.Color("cyan")); - paint.setColor(Skia.Color("white")); - const r = 100 + Math.sin(t * 2) * 80; - c.drawCircle(256, 256, r, paint); - surface1.flush(); - } - - // Draw on surface 2 — customize this per frame below. - function drawTexture2(t: number) { - const c = surface2.getCanvas(); - c.drawColor(Skia.Color("pink")); - paint.setColor(Skia.Color("black")); - const x = 256 + Math.cos(t * 3) * 100; - c.drawCircle(x, 256, 80, paint); - surface2.flush(); - } + const surface1 = Skia.Surface.MakeOffscreen(TEXTURE_SIZE, TEXTURE_SIZE)!; + const surface2 = Skia.Surface.MakeOffscreen(TEXTURE_SIZE, TEXTURE_SIZE)!; - // Create a sampler with linear filtering for smooth interpolation. const sampler = device.createSampler({ magFilter: "linear", minFilter: "linear", @@ -160,18 +134,9 @@ export function TexturedCube() { return device.createBindGroup({ layout: bindGroupLayout, entries: [ - { - binding: 0, - resource: { buffer: uniformBuffer }, - }, - { - binding: 1, - resource: sampler, - }, - { - binding: 2, - resource: texture.createView(), - }, + { binding: 0, resource: { buffer: uniformBuffer } }, + { binding: 1, resource: sampler }, + { binding: 2, resource: texture.createView() }, ], }); } @@ -201,20 +166,15 @@ export function TexturedCube() { 1, 100.0 ); - const modelViewProjectionMatrix = mat4Identity(); + const mvp = mat4Identity(); function getTransformationMatrix(): Mat4 { - const viewMatrix = mat4Identity(); - mat4Translate(viewMatrix, [0, 0, -4] as Vec3, viewMatrix); + const view = mat4Identity(); + mat4Translate(view, [0, 0, -4] as Vec3, view); const now = Date.now() / 1000; - mat4Rotate( - viewMatrix, - [Math.sin(now), Math.cos(now), 0] as Vec3, - 1, - viewMatrix - ); - mat4Multiply(projectionMatrix, viewMatrix, modelViewProjectionMatrix); - return modelViewProjectionMatrix; + mat4Rotate(view, [Math.sin(now), Math.cos(now), 0] as Vec3, 1, view); + mat4Multiply(projectionMatrix, view, mvp); + return mvp; } let running = true; @@ -223,29 +183,31 @@ export function TexturedCube() { if (!running) { return; } - const t = Date.now() / 1000; - // Update Skia drawings each frame - drawTexture1(t); + // Update Skia textures + drawTexture1(surface1.getCanvas(), t); + surface1.flush(); const tex1 = Skia.Image.MakeTextureFromImage( surface1.makeImageSnapshot() ); const bindGroup1 = createBindGroup(tex1); - drawTexture2(t); + drawTexture2(surface2.getCanvas(), t); + surface2.flush(); const tex2 = Skia.Image.MakeTextureFromImage( surface2.makeImageSnapshot() ); const bindGroup2 = createBindGroup(tex2); - const transformationMatrix = getTransformationMatrix(); + // Update MVP matrix + const mat = getTransformationMatrix(); device.queue.writeBuffer( uniformBuffer, 0, - transformationMatrix.buffer, - transformationMatrix.byteOffset, - transformationMatrix.byteLength + mat.buffer, + mat.byteOffset, + mat.byteLength ); // eslint-disable-next-line @typescript-eslint/no-explicit-any @@ -254,20 +216,19 @@ export function TexturedCube() { .createView(); const commandEncoder = device.createCommandEncoder(); - const passEncoder = - commandEncoder.beginRenderPass(renderPassDescriptor); - passEncoder.setPipeline(pipeline); - passEncoder.setVertexBuffer(0, verticesBuffer); + const pass = commandEncoder.beginRenderPass(renderPassDescriptor); + pass.setPipeline(pipeline); + pass.setVertexBuffer(0, verticesBuffer); - // First 3 faces (18 vertices) with texture 1 - passEncoder.setBindGroup(0, bindGroup1); - passEncoder.draw(18, 1, 0, 0); + // First 3 faces with texture 1 + pass.setBindGroup(0, bindGroup1); + pass.draw(18, 1, 0, 0); - // Last 3 faces (18 vertices) with texture 2 - passEncoder.setBindGroup(0, bindGroup2); - passEncoder.draw(18, 1, 18, 0); + // Last 3 faces with texture 2 + pass.setBindGroup(0, bindGroup2); + pass.draw(18, 1, 18, 0); - passEncoder.end(); + pass.end(); device.queue.submit([commandEncoder.finish()]); ctx.present(); From 399ab413ad9bc827cbdf711b4607bdd589886a17 Mon Sep 17 00:00:00 2001 From: William Candillon Date: Mon, 9 Feb 2026 10:58:56 +0100 Subject: [PATCH 05/10] :wrench: --- apps/example/src/Examples/WebGPU/Shaders.ts | 2 +- apps/example/src/Examples/WebGPU/TexturedCube.tsx | 7 +++++++ 2 files changed, 8 insertions(+), 1 deletion(-) diff --git a/apps/example/src/Examples/WebGPU/Shaders.ts b/apps/example/src/Examples/WebGPU/Shaders.ts index bb75bf9e7b..f469047e9d 100644 --- a/apps/example/src/Examples/WebGPU/Shaders.ts +++ b/apps/example/src/Examples/WebGPU/Shaders.ts @@ -61,7 +61,7 @@ fn main( @location(0) fragUV: vec2f, @location(1) fragPosition: vec4f ) -> @location(0) vec4f { - return textureSample(myTexture, mySampler, fragUV) * fragPosition; + return textureSample(myTexture, mySampler, fragUV);// * fragPosition; } `; diff --git a/apps/example/src/Examples/WebGPU/TexturedCube.tsx b/apps/example/src/Examples/WebGPU/TexturedCube.tsx index 2125e3be73..e2c39557cb 100644 --- a/apps/example/src/Examples/WebGPU/TexturedCube.tsx +++ b/apps/example/src/Examples/WebGPU/TexturedCube.tsx @@ -37,6 +37,13 @@ function drawTexture2(canvas: SkCanvas, t: number) { canvas.drawCircle(x, 256, 80, paint); } +function drawTexture3(canvas: SkCanvas, t: number) { + canvas.drawColor(Skia.Color("yellow")); + paint.setColor(Skia.Color("red")); + const y = 256 + Math.sin(t * 4) * 100; + canvas.drawCircle(256, y, 60, paint); +} + export function TexturedCube() { const canvasRef = useRef(null); const animationRef = useRef(0); From c3ee6c9c8d75e48365f1d1cb5298863c4073cb51 Mon Sep 17 00:00:00 2001 From: William Candillon Date: Mon, 9 Feb 2026 11:19:33 +0100 Subject: [PATCH 06/10] :wrench: --- .../src/Examples/WebGPU/TexturedCube.tsx | 75 ++++++++++++++++--- 1 file changed, 66 insertions(+), 9 deletions(-) diff --git a/apps/example/src/Examples/WebGPU/TexturedCube.tsx b/apps/example/src/Examples/WebGPU/TexturedCube.tsx index e2c39557cb..791ac8702a 100644 --- a/apps/example/src/Examples/WebGPU/TexturedCube.tsx +++ b/apps/example/src/Examples/WebGPU/TexturedCube.tsx @@ -1,7 +1,12 @@ import React, { useEffect, useRef } from "react"; import { StyleSheet, View, Text } from "react-native"; import type { SkCanvas, WebGPUCanvasRef } from "@shopify/react-native-skia"; -import { WebGPUCanvas, Skia } from "@shopify/react-native-skia"; +import { + WebGPUCanvas, + Skia, + BlurStyle, + BlendMode, +} from "@shopify/react-native-skia"; import { cubePositionOffset, @@ -23,6 +28,12 @@ import { const TEXTURE_SIZE = 512; const paint = Skia.Paint(); +// Breathe drawing resources +const breathePaint = Skia.Paint(); +breathePaint.setMaskFilter(Skia.MaskFilter.MakeBlur(BlurStyle.Solid, 40, true)); +breathePaint.setBlendMode(BlendMode.Screen); +const breatheColors = ["#529ca0", "#61bea2"]; + function drawTexture1(canvas: SkCanvas, t: number) { canvas.drawColor(Skia.Color("cyan")); paint.setColor(Skia.Color("white")); @@ -37,11 +48,47 @@ function drawTexture2(canvas: SkCanvas, t: number) { canvas.drawCircle(x, 256, 80, paint); } +function easeInOut(t: number): number { + // Attempt to match Easing.inOut(Easing.ease) — a cubic bezier ease-in-out + // Approximation using smoothstep: 3t² - 2t³ + return t * t * (3 - 2 * t); +} + function drawTexture3(canvas: SkCanvas, t: number) { - canvas.drawColor(Skia.Color("yellow")); - paint.setColor(Skia.Color("red")); - const y = 256 + Math.sin(t * 4) * 100; - canvas.drawCircle(256, y, 60, paint); + const cx = TEXTURE_SIZE / 2; + const cy = TEXTURE_SIZE / 2; + const R = TEXTURE_SIZE / 4; + const total = 6; + + // Triangle wave: 0→1→0 over 6 seconds (matching useLoop({duration: 3000})) + const period = 6; + const phase = (t % period) / period; // 0..1 + const triangle = phase < 0.5 ? phase * 2 : 2 - phase * 2; // 0→1→0 + const progress = easeInOut(triangle); + + // Background + canvas.drawColor(Skia.Color("rgb(36,43,56)")); + + canvas.save(); + + // Group rotation: mix(progress, -PI, 0) around center + const angle = (-Math.PI * (1 - progress) * 180) / Math.PI; + canvas.translate(cx, cy); + canvas.rotate(angle, 0, 0); + canvas.translate(-cx, -cy); + + // Draw 6 circles + for (let i = 0; i < total; i++) { + const theta = (i * 2 * Math.PI) / total; + const r = progress * R; + const x = cx + r * Math.cos(theta); + const y = cy + r * Math.sin(theta); + const scale = 0.3 + 0.7 * progress; + breathePaint.setColor(Skia.Color(breatheColors[i % 2])); + canvas.drawCircle(x, y, R * scale, breathePaint); + } + + canvas.restore(); } export function TexturedCube() { @@ -129,6 +176,7 @@ export function TexturedCube() { const surface1 = Skia.Surface.MakeOffscreen(TEXTURE_SIZE, TEXTURE_SIZE)!; const surface2 = Skia.Surface.MakeOffscreen(TEXTURE_SIZE, TEXTURE_SIZE)!; + const surface3 = Skia.Surface.MakeOffscreen(TEXTURE_SIZE, TEXTURE_SIZE)!; const sampler = device.createSampler({ magFilter: "linear", @@ -207,6 +255,13 @@ export function TexturedCube() { ); const bindGroup2 = createBindGroup(tex2); + drawTexture3(surface3.getCanvas(), t); + surface3.flush(); + const tex3 = Skia.Image.MakeTextureFromImage( + surface3.makeImageSnapshot() + ); + const bindGroup3 = createBindGroup(tex3); + // Update MVP matrix const mat = getTransformationMatrix(); device.queue.writeBuffer( @@ -227,13 +282,15 @@ export function TexturedCube() { pass.setPipeline(pipeline); pass.setVertexBuffer(0, verticesBuffer); - // First 3 faces with texture 1 + // 2 faces (12 vertices) per texture pass.setBindGroup(0, bindGroup1); - pass.draw(18, 1, 0, 0); + pass.draw(12, 1, 0, 0); - // Last 3 faces with texture 2 pass.setBindGroup(0, bindGroup2); - pass.draw(18, 1, 18, 0); + pass.draw(12, 1, 12, 0); + + pass.setBindGroup(0, bindGroup3); + pass.draw(12, 1, 24, 0); pass.end(); device.queue.submit([commandEncoder.finish()]); From f82653b4636449938606d3fcdb3f7da2b8869e9c Mon Sep 17 00:00:00 2001 From: William Candillon Date: Mon, 9 Feb 2026 11:33:03 +0100 Subject: [PATCH 07/10] :wrench: --- .../src/Examples/WebGPU/TexturedCube.tsx | 165 ++++++++++++++++-- 1 file changed, 153 insertions(+), 12 deletions(-) diff --git a/apps/example/src/Examples/WebGPU/TexturedCube.tsx b/apps/example/src/Examples/WebGPU/TexturedCube.tsx index 791ac8702a..917ef546b6 100644 --- a/apps/example/src/Examples/WebGPU/TexturedCube.tsx +++ b/apps/example/src/Examples/WebGPU/TexturedCube.tsx @@ -1,11 +1,28 @@ import React, { useEffect, useRef } from "react"; import { StyleSheet, View, Text } from "react-native"; -import type { SkCanvas, WebGPUCanvasRef } from "@shopify/react-native-skia"; +import type { + SkCanvas, + SkParagraph, + SkTextStyle, + WebGPUCanvasRef, +} from "@shopify/react-native-skia"; import { WebGPUCanvas, Skia, BlurStyle, BlendMode, + FontWeight, + FontSlant, + PaintStyle, + TextDecoration, + TextDecorationStyle, + useFonts, + fitbox, + rect, + processTransform3d, + StrokeCap, + StrokeJoin, + TileMode, } from "@shopify/react-native-skia"; import { @@ -34,18 +51,67 @@ breathePaint.setMaskFilter(Skia.MaskFilter.MakeBlur(BlurStyle.Solid, 40, true)); breathePaint.setBlendMode(BlendMode.Screen); const breatheColors = ["#529ca0", "#61bea2"]; +// Hello path +const helloSvg = + "M13.6 247.8C13.6 247.8 51.8 206.1 84.2 168.8 140.8 103.4 202.8 27.1 150.1 14.3 131 9.7 116.4 29.3 107.3 44.8 69.7 108.4 58 213.8 57.5 302 67.7 271.3 104.4 190.3 140.2 192.5 181.5 195.1 145.3 257 154.5 283.8 168.8 321.6 208.2 292.3 230 276.9 265.9 251.5 289 230.7 289 199.9 289 161 235.3 173.5 223.3 204.6 213.9 228.9 214.3 265.3 229.3 283.6 247.5 305.7 287.7 309.4 312.2 287.9 337 266.2 354.7 234 368.7 212.5 403.9 158.3 464.4 85.6 449.1 29.5 447 21.9 440.4 16 432.5 15.7 393.6 14.2 381.8 98.6 375.3 128.8 368.8 159.3 345.2 260.8 373.1 292.5 404.4 328 446.3 261.9 464.7 231.1 468.7 224.8 472.6 217.9 476.1 212.5 511.3 158.4 571.8 85.6 556.5 29.5 554.4 21.9 547.8 16.1 539.9 15.8 501 14.2 489.2 98.7 482.8 128.8 476.2 159.3 452.6 260.8 480.5 292.6 511.8 328.1 562.4 265 572.6 232.3 587.3 185.4 620.9 171 660.9 179.7M660.9 179.7C616 166.1 580.9 199.1 572.6 232.6 566.8 256.4 573.5 281.6 599.2 295.2 668.5 331.9 742.8 211.1 660.9 179.7ZM660.9 179.7C643.7 181.3 636.1 204.2 643.3 227.2 654.3 263.4 704.3 267.7 733.1 255.5"; +const helloPath = Skia.Path.MakeFromSVGString(helloSvg)!; +const helloBounds = helloPath.computeTightBounds(); +helloPath.transform( + processTransform3d( + fitbox( + "contain", + helloBounds, + rect(30, 30, TEXTURE_SIZE - 60, TEXTURE_SIZE - 60) + ) + ) +); + +// Paragraph fonts +const paragraphFonts = { + Roboto: [ + require("../../Tests/assets/Roboto-Medium.ttf"), + require("../../Tests/assets/Roboto-Regular.ttf"), + ], +}; + function drawTexture1(canvas: SkCanvas, t: number) { - canvas.drawColor(Skia.Color("cyan")); - paint.setColor(Skia.Color("white")); - const r = 100 + Math.sin(t * 2) * 80; - canvas.drawCircle(256, 256, r, paint); + canvas.drawColor(Skia.Color("white")); + const progress = (Math.sin(t * 0.8) + 1) / 2; + const trimmed = helloPath.copy(); + trimmed.trim(0, progress, false); + trimmed.stroke({ width: 25, join: StrokeJoin.Round, cap: StrokeCap.Round }); + paint.setShader( + Skia.Shader.MakeLinearGradient( + { x: 0, y: 0 }, + { x: 512, y: 0 }, + [ + "#3FCEBC", + "#3CBCEB", + "#5F96E7", + "#816FE3", + "#9F5EE2", + "#DE589F", + "#FF645E", + "#FDA859", + "#FAEC54", + "#9EE671", + "#41E08D", + ].map((c) => Skia.Color(c)), + null, + TileMode.Clamp + ) + ); + canvas.drawPath(trimmed, paint); } -function drawTexture2(canvas: SkCanvas, t: number) { - canvas.drawColor(Skia.Color("pink")); - paint.setColor(Skia.Color("black")); - const x = 256 + Math.cos(t * 3) * 100; - canvas.drawCircle(x, 256, 80, paint); +function drawTexture2(canvas: SkCanvas, t: number, paragraph: SkParagraph) { + canvas.drawColor(Skia.Color("white")); + const progress = (Math.sin(t) + 1) / 2; + const minW = TEXTURE_SIZE * 0.3; + const maxW = TEXTURE_SIZE * 0.8; + const width = minW + progress * (maxW - minW); + paragraph.layout(width); + paragraph.paint(canvas, 30, 30); } function easeInOut(t: number): number { @@ -95,6 +161,7 @@ export function TexturedCube() { const canvasRef = useRef(null); const animationRef = useRef(0); const cleanupRef = useRef<(() => void) | null>(null); + const customFontMgr = useFonts(paragraphFonts); useEffect(() => { const timeoutId = setTimeout(async () => { @@ -104,6 +171,9 @@ export function TexturedCube() { if (typeof RNWebGPU === "undefined") { return; } + if (!customFontMgr) { + return; + } const ctx = canvasRef.current.getContext("webgpu"); if (!ctx) { return; @@ -178,6 +248,77 @@ export function TexturedCube() { const surface2 = Skia.Surface.MakeOffscreen(TEXTURE_SIZE, TEXTURE_SIZE)!; const surface3 = Skia.Surface.MakeOffscreen(TEXTURE_SIZE, TEXTURE_SIZE)!; + // Build paragraph for texture 2 + const fontSize = 40; + const strokePaint = Skia.Paint(); + strokePaint.setStyle(PaintStyle.Stroke); + strokePaint.setStrokeWidth(1); + + const textStyle = { + fontSize, + fontFamilies: ["Roboto"], + color: Skia.Color("#000"), + }; + + const coloredTextStyle = { + fontSize: fontSize * 1.3, + fontFamilies: ["Roboto"], + fontStyle: { weight: FontWeight.Medium }, + color: Skia.Color("#61bea2"), + }; + + const crazyStyle: SkTextStyle = { + color: Skia.Color("#000"), + backgroundColor: Skia.Color("#CECECE"), + fontSize: fontSize * 1.3, + fontFamilies: ["Roboto"], + letterSpacing: -1, + wordSpacing: 20, + fontStyle: { + slant: FontSlant.Italic, + weight: FontWeight.ExtraBlack, + }, + shadows: [ + { + color: Skia.Color("#00000044"), + blurRadius: 4, + offset: { x: 4, y: 4 }, + }, + ], + decorationColor: Skia.Color("#00223A"), + decorationThickness: 2, + decoration: TextDecoration.Underline, + decorationStyle: TextDecorationStyle.Dotted, + }; + + const paragraph = Skia.ParagraphBuilder.Make({}, customFontMgr) + .pushStyle(textStyle) + .addText("Hello ") + .pushStyle({ + ...textStyle, + fontStyle: { weight: FontWeight.Medium }, + }) + .addText("Skia") + .pop() + .addText("\n\nThis text rendered using the ") + .pushStyle(coloredTextStyle) + .addText("SkParagraph ") + .pop() + .addText("module with ") + .pushStyle({ ...coloredTextStyle, color: Skia.Color("#f5a623") }) + .addText("libgrapheme ") + .pop() + .addText("on iOS.") + .pushStyle(textStyle) + .addText( + "\n\nOn Android we use built-in ICU while on web we use CanvasKit's." + ) + .pop() + .pushStyle(crazyStyle, strokePaint) + .addText("\n\nWow - this is cool.") + .pop() + .build(); + const sampler = device.createSampler({ magFilter: "linear", minFilter: "linear", @@ -248,7 +389,7 @@ export function TexturedCube() { ); const bindGroup1 = createBindGroup(tex1); - drawTexture2(surface2.getCanvas(), t); + drawTexture2(surface2.getCanvas(), t, paragraph); surface2.flush(); const tex2 = Skia.Image.MakeTextureFromImage( surface2.makeImageSnapshot() @@ -311,7 +452,7 @@ export function TexturedCube() { clearTimeout(timeoutId); cleanupRef.current?.(); }; - }, []); + }, [customFontMgr]); if (typeof RNWebGPU === "undefined") { return ( From 5cdcd6ee4bea16e4c364026c1cd9690fab44e328 Mon Sep 17 00:00:00 2001 From: William Candillon Date: Thu, 12 Feb 2026 12:05:17 +0100 Subject: [PATCH 08/10] :wrench: --- .../src/Examples/WebGPU/TexturedCube.tsx | 25 ++++++++++++++++--- .../skia/src/external/reanimated/useVideo.ts | 5 +--- 2 files changed, 22 insertions(+), 8 deletions(-) diff --git a/apps/example/src/Examples/WebGPU/TexturedCube.tsx b/apps/example/src/Examples/WebGPU/TexturedCube.tsx index 917ef546b6..dd7b170f5e 100644 --- a/apps/example/src/Examples/WebGPU/TexturedCube.tsx +++ b/apps/example/src/Examples/WebGPU/TexturedCube.tsx @@ -42,6 +42,7 @@ import { type Vec3, } from "./matrix"; +const videoURL = "https://bit.ly/skia-video"; const TEXTURE_SIZE = 512; const paint = Skia.Paint(); @@ -248,6 +249,12 @@ export function TexturedCube() { const surface2 = Skia.Surface.MakeOffscreen(TEXTURE_SIZE, TEXTURE_SIZE)!; const surface3 = Skia.Surface.MakeOffscreen(TEXTURE_SIZE, TEXTURE_SIZE)!; + // Video player — managed directly on the JS thread + const video = await Skia.Video(videoURL); + video.setLooping(true); + video.setVolume(0); + video.play(); + // Build paragraph for texture 2 const fontSize = 40; const strokePaint = Skia.Paint(); @@ -403,6 +410,10 @@ export function TexturedCube() { ); const bindGroup3 = createBindGroup(tex3); + const frame = video.nextImage(); + const tex4 = frame ? Skia.Image.MakeTextureFromImage(frame) : null; + const bindGroup4 = tex4 ? createBindGroup(tex4) : null; + // Update MVP matrix const mat = getTransformationMatrix(); device.queue.writeBuffer( @@ -423,15 +434,20 @@ export function TexturedCube() { pass.setPipeline(pipeline); pass.setVertexBuffer(0, verticesBuffer); - // 2 faces (12 vertices) per texture + // 1 face each for hello/paragraph/breathe, 3 faces for video pass.setBindGroup(0, bindGroup1); - pass.draw(12, 1, 0, 0); + pass.draw(6, 1, 0, 0); pass.setBindGroup(0, bindGroup2); - pass.draw(12, 1, 12, 0); + pass.draw(6, 1, 6, 0); pass.setBindGroup(0, bindGroup3); - pass.draw(12, 1, 24, 0); + pass.draw(6, 1, 12, 0); + + if (bindGroup4) { + pass.setBindGroup(0, bindGroup4); + pass.draw(18, 1, 18, 0); + } pass.end(); device.queue.submit([commandEncoder.finish()]); @@ -445,6 +461,7 @@ export function TexturedCube() { cleanupRef.current = () => { running = false; cancelAnimationFrame(animationRef.current); + video.dispose(); }; }, 100); diff --git a/packages/skia/src/external/reanimated/useVideo.ts b/packages/skia/src/external/reanimated/useVideo.ts index 6a78a687e1..c05b628de7 100644 --- a/packages/skia/src/external/reanimated/useVideo.ts +++ b/packages/skia/src/external/reanimated/useVideo.ts @@ -22,7 +22,7 @@ const copyFrameOnAndroid = (currentFrame: SharedValue) => { if (Platform.OS === "android") { const tex = currentFrame.value; if (tex) { - currentFrame.value = tex.makeNonTextureImage(); + currentFrame.value = tex; //.makeNonTextureImage(); tex.dispose(); } } @@ -32,9 +32,6 @@ const setFrame = (video: Video, currentFrame: SharedValue) => { "worklet"; const img = video.nextImage(); if (img) { - if (currentFrame.value) { - currentFrame.value.dispose(); - } currentFrame.value = img; copyFrameOnAndroid(currentFrame); } From e2c9b92fadfe32bbf66af606e76d6be9eaea6346 Mon Sep 17 00:00:00 2001 From: William Candillon Date: Tue, 17 Feb 2026 06:51:52 +0100 Subject: [PATCH 09/10] :wrench: --- packages/skia/cpp/rnskia/RNSkManager.cpp | 4 +- packages/skia/cpp/rnwgpu/api/GPUAdapter.cpp | 26 ++++++++ packages/skia/cpp/rnwgpu/api/GPUDevice.cpp | 52 +++++++++++++++ packages/skia/cpp/rnwgpu/api/GPUDevice.h | 63 ++++++++++++++++++- .../cpp/rnwgpu/api/GPUUncapturedErrorEvent.h | 61 ++++++++++++++++++ 5 files changed, 204 insertions(+), 2 deletions(-) create mode 100644 packages/skia/cpp/rnwgpu/api/GPUUncapturedErrorEvent.h diff --git a/packages/skia/cpp/rnskia/RNSkManager.cpp b/packages/skia/cpp/rnskia/RNSkManager.cpp index 5fc17cbd6a..0e88812ac8 100644 --- a/packages/skia/cpp/rnskia/RNSkManager.cpp +++ b/packages/skia/cpp/rnskia/RNSkManager.cpp @@ -14,6 +14,7 @@ #ifdef SK_GRAPHITE #include "RNDawnContext.h" #include "rnwgpu/api/GPU.h" +#include "rnwgpu/api/GPUUncapturedErrorEvent.h" #include "rnwgpu/api/RNWebGPU.h" #include "rnwgpu/api/descriptors/GPUBufferUsage.h" #include "rnwgpu/api/descriptors/GPUColorWrite.h" @@ -74,8 +75,9 @@ void RNSkManager::installBindings() { jsi::Object::createFromHostObject(*_jsRuntime, _viewApi)); #ifdef SK_GRAPHITE - // Install WebGPU GPU constructor + // Install WebGPU constructors rnwgpu::GPU::installConstructor(*_jsRuntime); + rnwgpu::GPUUncapturedErrorEvent::installConstructor(*_jsRuntime); // Create and expose navigator.gpu using DawnContext's instance auto &dawnContext = DawnContext::getInstance(); auto gpu = std::make_shared(*_jsRuntime, dawnContext.getWGPUInstance()); diff --git a/packages/skia/cpp/rnwgpu/api/GPUAdapter.cpp b/packages/skia/cpp/rnwgpu/api/GPUAdapter.cpp index d058244be4..af60450319 100644 --- a/packages/skia/cpp/rnwgpu/api/GPUAdapter.cpp +++ b/packages/skia/cpp/rnwgpu/api/GPUAdapter.cpp @@ -10,6 +10,9 @@ #include "Convertors.h" #include "GPUFeatures.h" +#include "GPUInternalError.h" +#include "GPUOutOfMemoryError.h" +#include "GPUValidationError.h" #include "jsi2/JSIConverter.h" namespace rnwgpu { @@ -74,6 +77,29 @@ async::AsyncTaskHandle GPUAdapter::requestDevice( std::string(message.data, message.length) : "no message"; fprintf(stderr, "%s", fullMessage.c_str()); + + // Look up the GPUDevice from the registry and notify it + auto *gpuDevice = GPUDeviceRegistry::getInstance().getDevice(device.Get()); + if (gpuDevice != nullptr) { + std::string messageStr = + message.length > 0 ? std::string(message.data, message.length) : ""; + + GPUErrorVariant error; + switch (type) { + case wgpu::ErrorType::Validation: + error = std::make_shared(messageStr); + break; + case wgpu::ErrorType::OutOfMemory: + error = std::make_shared(messageStr); + break; + case wgpu::ErrorType::Internal: + case wgpu::ErrorType::Unknown: + default: + error = std::make_shared(messageStr); + break; + } + gpuDevice->notifyUncapturedError(std::move(error)); + } }); std::string label = descriptor.has_value() ? descriptor.value()->label.value_or("") : ""; diff --git a/packages/skia/cpp/rnwgpu/api/GPUDevice.cpp b/packages/skia/cpp/rnwgpu/api/GPUDevice.cpp index edc181b38c..19e2b1d977 100644 --- a/packages/skia/cpp/rnwgpu/api/GPUDevice.cpp +++ b/packages/skia/cpp/rnwgpu/api/GPUDevice.cpp @@ -431,4 +431,56 @@ async::AsyncTaskHandle GPUDevice::getLost() { _lostHandle = handle; return handle; } +void GPUDevice::addEventListener(std::string type, jsi::Function callback) { + std::lock_guard lock(_listenersMutex); + auto sharedCallback = std::make_shared(std::move(callback)); + _eventListeners[type].push_back(sharedCallback); +} + +void GPUDevice::removeEventListener(std::string type, jsi::Function callback) { + std::lock_guard lock(_listenersMutex); + auto it = _eventListeners.find(type); + if (it != _eventListeners.end()) { + auto &listeners = it->second; + // Remove the last listener of this type (simple approach since we can't + // easily compare jsi::Function objects) + if (!listeners.empty()) { + listeners.pop_back(); + } + } +} + +void GPUDevice::notifyUncapturedError(GPUErrorVariant error) { + auto runtime = getCreationRuntime(); + if (runtime == nullptr) { + return; + } + + std::vector> listeners; + { + std::lock_guard lock(_listenersMutex); + auto it = _eventListeners.find("uncapturederror"); + if (it != _eventListeners.end()) { + listeners = it->second; + } + } + + if (listeners.empty()) { + return; + } + + // Create the event object + auto event = std::make_shared(std::move(error)); + auto eventValue = GPUUncapturedErrorEvent::create(*runtime, event); + + // Call all listeners + for (const auto &listener : listeners) { + try { + listener->call(*runtime, eventValue); + } catch (const std::exception &e) { + fprintf(stderr, "Error in uncapturederror listener: %s\n", e.what()); + } + } +} + } // namespace rnwgpu diff --git a/packages/skia/cpp/rnwgpu/api/GPUDevice.h b/packages/skia/cpp/rnwgpu/api/GPUDevice.h index 0406d7eefd..79d67ee74f 100644 --- a/packages/skia/cpp/rnwgpu/api/GPUDevice.h +++ b/packages/skia/cpp/rnwgpu/api/GPUDevice.h @@ -1,11 +1,15 @@ #pragma once +#include +#include #include +#include #include #include #include #include #include +#include #include "descriptors/Unions.h" @@ -16,6 +20,8 @@ #include "webgpu/webgpu_cpp.h" +#include "GPUUncapturedErrorEvent.h" + #include "GPUBindGroup.h" #include "descriptors/GPUBindGroupDescriptor.h" #include "GPUBindGroupLayout.h" @@ -51,6 +57,39 @@ namespace rnwgpu { namespace jsi = facebook::jsi; +// Forward declaration +class GPUDevice; + +// Static registry to map wgpu::Device handles to GPUDevice instances +class GPUDeviceRegistry { +public: + static GPUDeviceRegistry &getInstance() { + static GPUDeviceRegistry instance; + return instance; + } + + void registerDevice(WGPUDevice handle, GPUDevice *device) { + std::lock_guard lock(_mutex); + _devices[handle] = device; + } + + void unregisterDevice(WGPUDevice handle) { + std::lock_guard lock(_mutex); + _devices.erase(handle); + } + + GPUDevice *getDevice(WGPUDevice handle) { + std::lock_guard lock(_mutex); + auto it = _devices.find(handle); + return it != _devices.end() ? it->second : nullptr; + } + +private: + GPUDeviceRegistry() = default; + std::mutex _mutex; + std::map _devices; +}; + class GPUDevice : public NativeObject { public: static constexpr const char *CLASS_NAME = "GPUDevice"; @@ -59,7 +98,15 @@ class GPUDevice : public NativeObject { std::shared_ptr async, std::string label) : NativeObject(CLASS_NAME), _instance(instance), _async(async), - _label(label) {} + _label(label) { + // Register this device in the global registry + GPUDeviceRegistry::getInstance().registerDevice(_instance.Get(), this); + } + + ~GPUDevice() { + // Unregister from the global registry + GPUDeviceRegistry::getInstance().unregisterDevice(_instance.Get()); + } public: std::string getBrand() { return CLASS_NAME; } @@ -105,6 +152,11 @@ class GPUDevice : public NativeObject { void notifyDeviceLost(wgpu::DeviceLostReason reason, std::string message); void forceLossForTesting(); + // Event listener methods + void addEventListener(std::string type, jsi::Function callback); + void removeEventListener(std::string type, jsi::Function callback); + void notifyUncapturedError(GPUErrorVariant error); + std::string getLabel() { return _label; } void setLabel(const std::string &label) { _label = label; @@ -155,6 +207,10 @@ class GPUDevice : public NativeObject { &GPUDevice::setLabel); installMethod(runtime, prototype, "forceLossForTesting", &GPUDevice::forceLossForTesting); + installMethod(runtime, prototype, "addEventListener", + &GPUDevice::addEventListener); + installMethod(runtime, prototype, "removeEventListener", + &GPUDevice::removeEventListener); } inline const wgpu::Device get() { return _instance; } @@ -169,6 +225,11 @@ class GPUDevice : public NativeObject { std::shared_ptr _lostInfo; bool _lostSettled = false; std::optional _lostResolve; + + // Event listeners storage + std::mutex _listenersMutex; + std::map>> + _eventListeners; }; } // namespace rnwgpu diff --git a/packages/skia/cpp/rnwgpu/api/GPUUncapturedErrorEvent.h b/packages/skia/cpp/rnwgpu/api/GPUUncapturedErrorEvent.h new file mode 100644 index 0000000000..baa23da5b5 --- /dev/null +++ b/packages/skia/cpp/rnwgpu/api/GPUUncapturedErrorEvent.h @@ -0,0 +1,61 @@ +#pragma once + +#include +#include +#include + +#include "jsi2/NativeObject.h" + +#include "GPUError.h" +#include "GPUInternalError.h" +#include "GPUOutOfMemoryError.h" +#include "GPUValidationError.h" + +namespace rnwgpu { + +namespace jsi = facebook::jsi; + +using GPUErrorVariant = + std::variant, + std::shared_ptr, + std::shared_ptr>; + +class GPUUncapturedErrorEvent : public NativeObject { +public: + static constexpr const char *CLASS_NAME = "GPUUncapturedErrorEvent"; + + explicit GPUUncapturedErrorEvent(GPUErrorVariant error) + : NativeObject(CLASS_NAME), _error(std::move(error)) {} + + GPUErrorVariant getError() { return _error; } + + static void definePrototype(jsi::Runtime &runtime, jsi::Object &prototype) { + installGetter(runtime, prototype, "error", + &GPUUncapturedErrorEvent::getError); + } + +private: + GPUErrorVariant _error; +}; + +} // namespace rnwgpu + +namespace rnwgpu { + +template <> struct JSIConverter { + static jsi::Value toJSI(jsi::Runtime &runtime, GPUErrorVariant arg) { + return std::visit( + [&runtime](auto &&error) -> jsi::Value { + using T = std::decay_t; + return JSIConverter::toJSI(runtime, error); + }, + arg); + } + + static GPUErrorVariant fromJSI(jsi::Runtime &runtime, const jsi::Value &arg, + bool outOfBounds) { + throw std::runtime_error("GPUErrorVariant::fromJSI not implemented"); + } +}; + +} // namespace rnwgpu From 0014dc00d24925f4ce8c1639d0c73bfd323bf8cf Mon Sep 17 00:00:00 2001 From: William Candillon Date: Mon, 23 Feb 2026 08:54:29 +0100 Subject: [PATCH 10/10] Support passing GPUBuffer directly as resource (auto-wrap in GPUBufferBinding) --- packages/skia/cpp/rnwgpu/api/descriptors/GPUBindGroupEntry.h | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/packages/skia/cpp/rnwgpu/api/descriptors/GPUBindGroupEntry.h b/packages/skia/cpp/rnwgpu/api/descriptors/GPUBindGroupEntry.h index 9ea0ccc70c..867a5c0c1c 100644 --- a/packages/skia/cpp/rnwgpu/api/descriptors/GPUBindGroupEntry.h +++ b/packages/skia/cpp/rnwgpu/api/descriptors/GPUBindGroupEntry.h @@ -45,6 +45,10 @@ template <> struct JSIConverter> { } else if (obj.hasNativeState(runtime)) { result->textureView = obj.getNativeState(runtime); + } else if (obj.hasNativeState(runtime)) { + auto binding = std::make_shared(); + binding->buffer = obj.getNativeState(runtime); + result->buffer = binding; } else { result->buffer = JSIConverter< std::shared_ptr>::fromJSI(runtime,