@symbiote-native/angular 0.0.0-canary-20260724081123

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (276) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +157 -0
  3. package/babel-linker.cjs +7 -0
  4. package/babel-register-composed.cjs +127 -0
  5. package/bin/symbiote-angular-dev.cjs +93 -0
  6. package/build/angular/anchor-host-registry.d.ts +2 -0
  7. package/build/angular/anchor-host-registry.js +84 -0
  8. package/build/angular/anchor-host-registry.js.map +1 -0
  9. package/build/angular/bootstrap.d.ts +7 -0
  10. package/build/angular/bootstrap.js +15 -0
  11. package/build/angular/bootstrap.js.map +1 -0
  12. package/build/angular/components/activity-indicator/index.android.d.ts +12 -0
  13. package/build/angular/components/activity-indicator/index.android.js +21 -0
  14. package/build/angular/components/activity-indicator/index.android.js.map +1 -0
  15. package/build/angular/components/activity-indicator/index.d.ts +1 -0
  16. package/build/angular/components/activity-indicator/index.ios.d.ts +8 -0
  17. package/build/angular/components/activity-indicator/index.ios.js +21 -0
  18. package/build/angular/components/activity-indicator/index.ios.js.map +1 -0
  19. package/build/angular/components/activity-indicator/index.js +4 -0
  20. package/build/angular/components/activity-indicator/index.js.map +1 -0
  21. package/build/angular/components/activity-indicator/shared.d.ts +67 -0
  22. package/build/angular/components/activity-indicator/shared.js +260 -0
  23. package/build/angular/components/activity-indicator/shared.js.map +1 -0
  24. package/build/angular/components/button.d.ts +63 -0
  25. package/build/angular/components/button.js +332 -0
  26. package/build/angular/components/button.js.map +1 -0
  27. package/build/angular/components/flat-list/index.d.ts +122 -0
  28. package/build/angular/components/flat-list/index.js +688 -0
  29. package/build/angular/components/flat-list/index.js.map +1 -0
  30. package/build/angular/components/image/index.android.d.ts +10 -0
  31. package/build/angular/components/image/index.android.js +59 -0
  32. package/build/angular/components/image/index.android.js.map +1 -0
  33. package/build/angular/components/image/index.d.ts +1 -0
  34. package/build/angular/components/image/index.ios.d.ts +10 -0
  35. package/build/angular/components/image/index.ios.js +59 -0
  36. package/build/angular/components/image/index.ios.js.map +1 -0
  37. package/build/angular/components/image/index.js +3 -0
  38. package/build/angular/components/image/index.js.map +1 -0
  39. package/build/angular/components/image/shared.d.ts +101 -0
  40. package/build/angular/components/image/shared.js +406 -0
  41. package/build/angular/components/image/shared.js.map +1 -0
  42. package/build/angular/components/image-background.d.ts +81 -0
  43. package/build/angular/components/image-background.js +418 -0
  44. package/build/angular/components/image-background.js.map +1 -0
  45. package/build/angular/components/input-accessory-view/index.d.ts +60 -0
  46. package/build/angular/components/input-accessory-view/index.js +251 -0
  47. package/build/angular/components/input-accessory-view/index.js.map +1 -0
  48. package/build/angular/components/keyboard-avoiding-view/index.d.ts +82 -0
  49. package/build/angular/components/keyboard-avoiding-view/index.js +358 -0
  50. package/build/angular/components/keyboard-avoiding-view/index.js.map +1 -0
  51. package/build/angular/components/modal/index.d.ts +92 -0
  52. package/build/angular/components/modal/index.js +360 -0
  53. package/build/angular/components/modal/index.js.map +1 -0
  54. package/build/angular/components/pressable/index.d.ts +123 -0
  55. package/build/angular/components/pressable/index.js +420 -0
  56. package/build/angular/components/pressable/index.js.map +1 -0
  57. package/build/angular/components/refresh-control/index.d.ts +86 -0
  58. package/build/angular/components/refresh-control/index.js +342 -0
  59. package/build/angular/components/refresh-control/index.js.map +1 -0
  60. package/build/angular/components/safe-area-view/index.d.ts +57 -0
  61. package/build/angular/components/safe-area-view/index.js +248 -0
  62. package/build/angular/components/safe-area-view/index.js.map +1 -0
  63. package/build/angular/components/scroll-view/index.android.d.ts +21 -0
  64. package/build/angular/components/scroll-view/index.android.js +235 -0
  65. package/build/angular/components/scroll-view/index.android.js.map +1 -0
  66. package/build/angular/components/scroll-view/index.d.ts +3 -0
  67. package/build/angular/components/scroll-view/index.ios.d.ts +9 -0
  68. package/build/angular/components/scroll-view/index.ios.js +86 -0
  69. package/build/angular/components/scroll-view/index.ios.js.map +1 -0
  70. package/build/angular/components/scroll-view/index.js +6 -0
  71. package/build/angular/components/scroll-view/index.js.map +1 -0
  72. package/build/angular/components/scroll-view/projection.d.ts +32 -0
  73. package/build/angular/components/scroll-view/projection.js +334 -0
  74. package/build/angular/components/scroll-view/projection.js.map +1 -0
  75. package/build/angular/components/scroll-view/shared.d.ts +230 -0
  76. package/build/angular/components/scroll-view/shared.js +682 -0
  77. package/build/angular/components/scroll-view/shared.js.map +1 -0
  78. package/build/angular/components/scroll-view/sticky-header.d.ts +40 -0
  79. package/build/angular/components/scroll-view/sticky-header.js +225 -0
  80. package/build/angular/components/scroll-view/sticky-header.js.map +1 -0
  81. package/build/angular/components/section-list/index.d.ts +116 -0
  82. package/build/angular/components/section-list/index.js +641 -0
  83. package/build/angular/components/section-list/index.js.map +1 -0
  84. package/build/angular/components/switch/index.android.d.ts +20 -0
  85. package/build/angular/components/switch/index.android.js +70 -0
  86. package/build/angular/components/switch/index.android.js.map +1 -0
  87. package/build/angular/components/switch/index.d.ts +1 -0
  88. package/build/angular/components/switch/index.ios.d.ts +19 -0
  89. package/build/angular/components/switch/index.ios.js +69 -0
  90. package/build/angular/components/switch/index.ios.js.map +1 -0
  91. package/build/angular/components/switch/index.js +4 -0
  92. package/build/angular/components/switch/index.js.map +1 -0
  93. package/build/angular/components/switch/shared.d.ts +40 -0
  94. package/build/angular/components/switch/shared.js +127 -0
  95. package/build/angular/components/switch/shared.js.map +1 -0
  96. package/build/angular/components/text-input.d.ts +153 -0
  97. package/build/angular/components/text-input.js +599 -0
  98. package/build/angular/components/text-input.js.map +1 -0
  99. package/build/angular/components/touchable/index.d.ts +245 -0
  100. package/build/angular/components/touchable/index.js +1186 -0
  101. package/build/angular/components/touchable/index.js.map +1 -0
  102. package/build/angular/components/touchable-native-feedback/index.d.ts +83 -0
  103. package/build/angular/components/touchable-native-feedback/index.js +371 -0
  104. package/build/angular/components/touchable-native-feedback/index.js.map +1 -0
  105. package/build/angular/components/virtualized-list/directives.d.ts +54 -0
  106. package/build/angular/components/virtualized-list/directives.js +153 -0
  107. package/build/angular/components/virtualized-list/directives.js.map +1 -0
  108. package/build/angular/components/virtualized-list/index.d.ts +253 -0
  109. package/build/angular/components/virtualized-list/index.js +1031 -0
  110. package/build/angular/components/virtualized-list/index.js.map +1 -0
  111. package/build/angular/components/virtualized-section-list/directives.d.ts +37 -0
  112. package/build/angular/components/virtualized-section-list/directives.js +76 -0
  113. package/build/angular/components/virtualized-section-list/directives.js.map +1 -0
  114. package/build/angular/components/virtualized-section-list/index.d.ts +178 -0
  115. package/build/angular/components/virtualized-section-list/index.js +720 -0
  116. package/build/angular/components/virtualized-section-list/index.js.map +1 -0
  117. package/build/angular/components.d.ts +39 -0
  118. package/build/angular/components.js +38 -0
  119. package/build/angular/components.js.map +1 -0
  120. package/build/angular/create-portal/index.d.ts +22 -0
  121. package/build/angular/create-portal/index.js +74 -0
  122. package/build/angular/create-portal/index.js.map +1 -0
  123. package/build/angular/create-tunnel/index.d.ts +34 -0
  124. package/build/angular/create-tunnel/index.js +126 -0
  125. package/build/angular/create-tunnel/index.js.map +1 -0
  126. package/build/angular/descriptor-to-angular/index.d.ts +22 -0
  127. package/build/angular/descriptor-to-angular/index.js +142 -0
  128. package/build/angular/descriptor-to-angular/index.js.map +1 -0
  129. package/build/angular/host-instance/index.d.ts +2 -0
  130. package/build/angular/host-instance/index.js +37 -0
  131. package/build/angular/host-instance/index.js.map +1 -0
  132. package/build/angular/index.d.ts +22 -0
  133. package/build/angular/index.js +46 -0
  134. package/build/angular/index.js.map +1 -0
  135. package/build/angular/modules/animated/animated-leaf-binder/index.d.ts +14 -0
  136. package/build/angular/modules/animated/animated-leaf-binder/index.js +91 -0
  137. package/build/angular/modules/animated/animated-leaf-binder/index.js.map +1 -0
  138. package/build/angular/modules/animated/animated-leaf-binder.d.ts +14 -0
  139. package/build/angular/modules/animated/animated-leaf-binder.js +91 -0
  140. package/build/angular/modules/animated/animated-leaf-binder.js.map +1 -0
  141. package/build/angular/modules/animated/create-animated-component.d.ts +59 -0
  142. package/build/angular/modules/animated/create-animated-component.js +364 -0
  143. package/build/angular/modules/animated/create-animated-component.js.map +1 -0
  144. package/build/angular/modules/animated/index.d.ts +51 -0
  145. package/build/angular/modules/animated/index.js +59 -0
  146. package/build/angular/modules/animated/index.js.map +1 -0
  147. package/build/angular/modules/app-registry/index.d.ts +7 -0
  148. package/build/angular/modules/app-registry/index.js +23 -0
  149. package/build/angular/modules/app-registry/index.js.map +1 -0
  150. package/build/angular/modules/status-bar/index.d.ts +20 -0
  151. package/build/angular/modules/status-bar/index.js +59 -0
  152. package/build/angular/modules/status-bar/index.js.map +1 -0
  153. package/build/angular/primitives/index.d.ts +63 -0
  154. package/build/angular/primitives/index.js +189 -0
  155. package/build/angular/primitives/index.js.map +1 -0
  156. package/build/angular/primitives/shared.d.ts +88 -0
  157. package/build/angular/primitives/shared.js +171 -0
  158. package/build/angular/primitives/shared.js.map +1 -0
  159. package/build/angular/render/index.d.ts +11 -0
  160. package/build/angular/render/index.js +171 -0
  161. package/build/angular/render/index.js.map +1 -0
  162. package/build/angular/renderer/index.d.ts +37 -0
  163. package/build/angular/renderer/index.js +301 -0
  164. package/build/angular/renderer/index.js.map +1 -0
  165. package/build/angular/services/color-scheme.service.d.ts +16 -0
  166. package/build/angular/services/color-scheme.service.js +31 -0
  167. package/build/angular/services/color-scheme.service.js.map +1 -0
  168. package/build/angular/services/index.d.ts +2 -0
  169. package/build/angular/services/index.js +3 -0
  170. package/build/angular/services/index.js.map +1 -0
  171. package/build/angular/services/window-dimensions.service.d.ts +16 -0
  172. package/build/angular/services/window-dimensions.service.js +42 -0
  173. package/build/angular/services/window-dimensions.service.js.map +1 -0
  174. package/metro-config.cjs +48 -0
  175. package/metro-css-parser.cjs +13 -0
  176. package/package.json +80 -0
  177. package/src/__tests__/responder-change-detection.test.ts +102 -0
  178. package/src/__tests__/responder-nested-cd.test.ts +113 -0
  179. package/src/anchor-host-registry.ts +88 -0
  180. package/src/angular-gaps.test.ts +142 -0
  181. package/src/angular-imports.test.ts +100 -0
  182. package/src/bootstrap.ts +26 -0
  183. package/src/components/activity-indicator/activity-indicator-class-style.test.ts +44 -0
  184. package/src/components/activity-indicator/activity-indicator.test.ts +131 -0
  185. package/src/components/activity-indicator/index.android.ts +16 -0
  186. package/src/components/activity-indicator/index.ios.ts +17 -0
  187. package/src/components/activity-indicator/index.ts +4 -0
  188. package/src/components/activity-indicator/shared.ts +206 -0
  189. package/src/components/button.ts +193 -0
  190. package/src/components/flat-list/column-wrapper-style-class.test.ts +116 -0
  191. package/src/components/flat-list/flat-list-array-style.test.ts +131 -0
  192. package/src/components/flat-list/flat-list-class-style.test.ts +74 -0
  193. package/src/components/flat-list/flat-list-scroll-containment.test.ts +107 -0
  194. package/src/components/flat-list/flat-list.test.ts +99 -0
  195. package/src/components/flat-list/index.ts +574 -0
  196. package/src/components/image/image-class-style.test.ts +46 -0
  197. package/src/components/image/index.android.ts +48 -0
  198. package/src/components/image/index.ios.ts +48 -0
  199. package/src/components/image/index.ts +3 -0
  200. package/src/components/image/shared.ts +479 -0
  201. package/src/components/image-background-class-style.test.ts +48 -0
  202. package/src/components/image-background-style-class.test.ts +79 -0
  203. package/src/components/image-background.ts +270 -0
  204. package/src/components/input-accessory-view/index.ts +185 -0
  205. package/src/components/input-accessory-view/input-accessory-view.test.ts +43 -0
  206. package/src/components/keyboard-avoiding-view/index.ts +303 -0
  207. package/src/components/keyboard-avoiding-view/keyboard-avoiding-view.test.ts +54 -0
  208. package/src/components/modal/index.ts +299 -0
  209. package/src/components/modal/modal.test.ts +43 -0
  210. package/src/components/pressable/index.ts +373 -0
  211. package/src/components/pressable/pressable.test.ts +85 -0
  212. package/src/components/refresh-control/index.ts +284 -0
  213. package/src/components/refresh-control/refresh-control.test.ts +41 -0
  214. package/src/components/safe-area-view/index.ts +177 -0
  215. package/src/components/safe-area-view/safe-area-view.test.ts +43 -0
  216. package/src/components/scroll-view/android-scroll-view-axis-projection.test.ts +123 -0
  217. package/src/components/scroll-view/content-container-style-class.test.ts +75 -0
  218. package/src/components/scroll-view/index.android.ts +190 -0
  219. package/src/components/scroll-view/index.ios.ts +79 -0
  220. package/src/components/scroll-view/index.ts +7 -0
  221. package/src/components/scroll-view/projection.ts +414 -0
  222. package/src/components/scroll-view/scroll-view-class-style.test.ts +134 -0
  223. package/src/components/scroll-view/scroll-view-projection.test.ts +194 -0
  224. package/src/components/scroll-view/shared.ts +844 -0
  225. package/src/components/scroll-view/sticky-header.ts +255 -0
  226. package/src/components/section-list/index.ts +445 -0
  227. package/src/components/switch/android-switch-class.test.ts +42 -0
  228. package/src/components/switch/index.android.ts +61 -0
  229. package/src/components/switch/index.ios.ts +60 -0
  230. package/src/components/switch/index.ts +4 -0
  231. package/src/components/switch/shared.ts +197 -0
  232. package/src/components/switch/switch.test.ts +92 -0
  233. package/src/components/text-input-class-style.test.ts +54 -0
  234. package/src/components/text-input.ts +531 -0
  235. package/src/components/touchable/index.ts +629 -0
  236. package/src/components/touchable/touchable.test.ts +102 -0
  237. package/src/components/touchable-native-feedback/index.ts +254 -0
  238. package/src/components/touchable-native-feedback/touchable-native-feedback.test.ts +49 -0
  239. package/src/components/virtualized-list/directives.ts +168 -0
  240. package/src/components/virtualized-list/index.ts +992 -0
  241. package/src/components/virtualized-list/virtualized-list-class-style.test.ts +76 -0
  242. package/src/components/virtualized-section-list/directives.ts +90 -0
  243. package/src/components/virtualized-section-list/index.ts +601 -0
  244. package/src/components/virtualized-section-list/virtualized-section-list-class-style.test.ts +60 -0
  245. package/src/components.ts +149 -0
  246. package/src/create-portal/create-portal.test.ts +90 -0
  247. package/src/create-portal/index.ts +74 -0
  248. package/src/create-tunnel/create-tunnel.test.ts +120 -0
  249. package/src/create-tunnel/index.ts +136 -0
  250. package/src/descriptor-to-angular/descriptor-outlet.test.ts +94 -0
  251. package/src/descriptor-to-angular/index.ts +190 -0
  252. package/src/host-instance/host-instance.test.ts +49 -0
  253. package/src/host-instance/index.ts +36 -0
  254. package/src/index.ts +261 -0
  255. package/src/modules/animated/animated-leaf-binder/animated-leaf-binder.test.ts +116 -0
  256. package/src/modules/animated/animated-leaf-binder/index.ts +101 -0
  257. package/src/modules/animated/animated-leaf-binder.test.ts +116 -0
  258. package/src/modules/animated/animated-leaf-binder.ts +101 -0
  259. package/src/modules/animated/animated-scroll-view.test.ts +102 -0
  260. package/src/modules/animated/create-animated-component.ts +365 -0
  261. package/src/modules/animated/index.ts +105 -0
  262. package/src/modules/app-registry/app-registry.test.ts +106 -0
  263. package/src/modules/app-registry/index.ts +60 -0
  264. package/src/modules/status-bar/index.ts +57 -0
  265. package/src/modules/status-bar/status-bar.test.ts +50 -0
  266. package/src/primitives/index.ts +119 -0
  267. package/src/primitives/shared.ts +190 -0
  268. package/src/render/index.ts +235 -0
  269. package/src/render/render.test.ts +147 -0
  270. package/src/renderer/index.ts +347 -0
  271. package/src/renderer/renderer.test.ts +203 -0
  272. package/src/services/color-scheme.service.ts +27 -0
  273. package/src/services/index.ts +2 -0
  274. package/src/services/services.test.ts +163 -0
  275. package/src/services/window-dimensions.service.ts +41 -0
  276. package/tsconfig.angular.base.json +30 -0
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 A. Prokopenko
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md ADDED
@@ -0,0 +1,157 @@
1
+ # @symbiote-native/angular
2
+
3
+ The **Angular adapter** for [SymbioteNative](../../README.md) — render real native iOS/Android views
4
+ from Angular, on the *same* untouched core as React and Vue, with React Native's own renderer
5
+ never in the path. It is a `Renderer2`/`RendererFactory2` whose calls map onto the engine's
6
+ four-call mutation API; `@symbiote-native/engine` does the clone-on-write commit into Fabric.
7
+
8
+ Angular is the **second proof the core is genuinely framework-agnostic**: a third
9
+ framework, with its own change-detection model and AOT compilation pipeline, driving the
10
+ already-validated engine with zero changes to it.
11
+
12
+ <div align="center">
13
+
14
+ ![Angular driving real native iOS views through SymbioteNative](../../assets/angular-demo.gif)
15
+
16
+ </div>
17
+
18
+ > New to SymbioteNative? The [root README](../../README.md) has the architecture.
19
+
20
+ ---
21
+
22
+ ## Install
23
+
24
+ ```bash
25
+ npm install @symbiote-native/angular react-native @angular/core
26
+ ```
27
+
28
+ `react-native` and `@angular/core` (**>=20**, for stable zoneless change detection) stay your app's
29
+ own top-level dependencies. There's no `create-symbiote` scaffolder yet, so the AOT pipeline
30
+ (`ngc --watch` alongside Metro — see [Run it](#run-it)) and the Metro config come from
31
+ [`examples/angular`](../../examples/angular) rather than a generator.
32
+
33
+ ---
34
+
35
+ ## Use it
36
+
37
+ The native entry reaches the *same* `registerRunnable` seam as React and Vue — only the adapter
38
+ changes. It hands the surface's `rootTag` to `mount` from `@symbiote-native/angular`, which drives the
39
+ engine through Angular's `Renderer2`:
40
+
41
+ ```js
42
+ // index.js
43
+ import { AppRegistry as RNAppRegistry } from 'react-native';
44
+ import { mount } from '@symbiote-native/angular';
45
+ import { AppComponent } from './App';
46
+ import { name as appName } from './app.json';
47
+
48
+ // registerRunnable (not registerComponent): RN stores a raw mount callback and never renders
49
+ // it with its own renderer. We mount the Angular app onto the surface's rootTag.
50
+ RNAppRegistry.registerRunnable(appName, ({ rootTag }) => {
51
+ mount(rootTag, AppComponent);
52
+ });
53
+ ```
54
+
55
+ The app is ordinary standalone Angular — it just imports primitives from `@symbiote-native/angular`
56
+ instead of `react-native`. A tap→increment counter:
57
+
58
+ ```ts
59
+ import { Component, signal } from '@angular/core';
60
+ import { View, Text, Pressable } from '@symbiote-native/angular';
61
+
62
+ @Component({
63
+ selector: 'app-root',
64
+ standalone: true,
65
+ imports: [View, Text, Pressable],
66
+ template: `
67
+ <View [style]="{ padding: 24 }">
68
+ <Text>Taps: {{ count() }}</Text>
69
+ <Pressable (press)="count.set(count() + 1)">
70
+ <Text>Tap me</Text>
71
+ </Pressable>
72
+ </View>
73
+ `,
74
+ })
75
+ export class AppComponent {
76
+ count = signal(0);
77
+ }
78
+ ```
79
+
80
+ The full canary is [`examples/angular`](../../examples/angular) — a stock RN 0.86 app whose
81
+ [`App.ts`](../../examples/angular/App.ts) exercises the same surface as the React and Vue
82
+ reference canaries, standalone components, zoneless change detection.
83
+
84
+ ---
85
+
86
+ ## Parity — and the one gap
87
+
88
+ Angular reaches the same 21+ primitives, runtime modules, `Animated` on both drivers, gestures,
89
+ accessibility, and the `VirtualizedList` family as React and Vue. That parity is **structural, not
90
+ hand-copied**: the component logic (state machines + render functions) is written **once** in
91
+ `@symbiote-native/components`, and Angular supplies only its lifecycle (`Renderer2` + zoneless change
92
+ detection + the descriptor→`createElement` bridge).
93
+
94
+ One deliberate gap, tracked, not blocking the canary — **third-party React component packages**
95
+ (`@react-native-community/slider`) run only under the React adapter: their body calls React hooks
96
+ off the React dispatcher, which is null under Angular. `@symbiote-native/slider` (this repo's own
97
+ wrapper) *does* ship a real Angular build, reachable through the same `createNode`-by-ViewConfig
98
+ path Angular uses for its own primitives — that wrapper is what makes a third-party native view
99
+ usable from a non-React adapter at all.
100
+
101
+ Angular is on the docs site's live framework switcher alongside React and Vue — otherwise it's at
102
+ full canary parity.
103
+
104
+ ---
105
+
106
+ ## An Angular-specific gotcha — AOT compiles separately from Metro
107
+
108
+ Angular templates need `ngc` (Angular's own AOT compiler), which Metro cannot run per-file the way
109
+ it transforms a Vue SFC or JSX — `ngc` needs whole-program `compilationMode: 'partial'` first, then
110
+ `@angular/compiler-cli/linker/babel` drops the linked output into Metro per-file. In practice this
111
+ means every `ios`/`android`/`e2e:build:*` script runs `pnpm ng:build` first, and local development
112
+ needs `ngc --watch` running alongside Metro — `scripts/dev-with-watch.sh` in
113
+ [`examples/angular`](../../examples/angular) does exactly that (`ngc --watch` in the background,
114
+ Metro's `react-native start` in the foreground, since Metro reads raw keypresses off stdin and
115
+ can't sit behind a process manager that owns stdin itself).
116
+
117
+ Angular also requires **zoneless change detection** (`provideZonelessChangeDetection`,
118
+ `@angular/core >=20`) — zone.js fights Hermes, and versions before 20 don't offer a stable
119
+ zoneless API. This is the version floor for the whole adapter, not a suggestion.
120
+
121
+ ---
122
+
123
+ ## Run it
124
+
125
+ [`examples/angular`](../../examples/angular) is a stock React Native 0.86 app. Requires Node ≥
126
+ 22.13 and the [RN environment setup](https://reactnative.dev/docs/set-up-your-environment) (Xcode,
127
+ CocoaPods):
128
+
129
+ ```bash
130
+ cd examples/angular
131
+ pnpm install # workspace root already covers this if you ran it there
132
+ bundle install # first time only — installs CocoaPods itself
133
+ bundle exec pod install # fetch native pods
134
+
135
+ # terminal 1 — ngc --watch (background) + Metro (foreground). DEBUG=1 turns on diagnostic logs.
136
+ DEBUG=1 pnpm dev
137
+
138
+ # terminal 2 — build + launch (each runs ng:build first)
139
+ pnpm ios # iOS simulator
140
+ pnpm android # Android emulator
141
+ ```
142
+
143
+ ---
144
+
145
+ ## Test it
146
+
147
+ ```bash
148
+ pnpm test # vitest, from the workspace root — headless, fake Fabric slot
149
+
150
+ cd examples/angular
151
+ pnpm e2e:build:ios # ng:build, then build the app for Detox
152
+ pnpm e2e:test:ios # run the canary journeys on the iOS simulator
153
+ # …or the android equivalents: e2e:build:android / e2e:test:android
154
+ ```
155
+
156
+ Why these come for free — a SymbioteNative app is a stock RN app underneath, so RN's whole testing
157
+ ecosystem applies unchanged. See [Testing](../../README.md#testing).
@@ -0,0 +1,7 @@
1
+ // Normalizes @angular/compiler-cli/linker/babel's export shape — depending on how a
2
+ // consumer's Metro/Babel setup loads it, the plugin lands as either the plugin function itself
3
+ // or a `{ default: plugin }` wrapper — so a consumer's babel.config.js just requires this
4
+ // instead of re-deriving the `.default ?? angularLinker` fallback itself.
5
+ const angularLinkerModule = require('@angular/compiler-cli/linker/babel');
6
+
7
+ module.exports = angularLinkerModule.default ?? angularLinkerModule;
@@ -0,0 +1,127 @@
1
+ // Auto-registers ANCHOR_HOST_COMPONENTS from compiled @Component metadata, replacing
2
+ // hand-written registerComposedComponent(...) calls (see the angular-adapter skill §11).
3
+ // Runs in the SAME Babel pass as babel-linker.cjs, BEFORE it — Stage A (ngc --compilationMode
4
+ // partial) emits ɵɵngDeclareComponent({..., selector}) calls; the linker only turns those into
5
+ // full Ivy afterwards, so this plugin must see the simpler pre-link shape (see
6
+ // angular-adapter-build skill §1).
7
+ //
8
+ // Primitive selectors are hardcoded here (not required from the .ts source — this is a plain
9
+ // .cjs Babel plugin Metro loads via a raw require(), no transpile step available) — source of
10
+ // truth: core/components/src/component-names/index.ios.ts's ISymbioteIntrinsic union. Kept in
11
+ // sync by the drift-protection test in babel-register-composed.test.ts.
12
+ const PRIMITIVE_SELECTORS = new Set([
13
+ 'symbiote-view',
14
+ 'symbiote-text',
15
+ 'symbiote-image',
16
+ 'symbiote-scroll-view',
17
+ 'symbiote-scroll-content',
18
+ 'symbiote-horizontal-scroll-view',
19
+ 'symbiote-horizontal-scroll-content',
20
+ 'symbiote-text-input',
21
+ 'symbiote-text-input-multiline',
22
+ 'symbiote-switch',
23
+ 'symbiote-activity-indicator',
24
+ 'symbiote-safe-area-view',
25
+ 'symbiote-modal',
26
+ 'symbiote-refresh-control',
27
+ 'symbiote-input-accessory-view',
28
+ ]);
29
+
30
+ // Inject from the package barrel — the ONE resolution route every consumer already uses, so the
31
+ // leaf's registry Set stays a single module instance. `registerComposedComponent` is re-exported
32
+ // from the barrel straight off the dependency-free leaf `anchor-host-registry.ts`, so importing it
33
+ // here does NOT drag in the cyclic renderer graph, yet resolves to the same leaf Set that
34
+ // `createElement` reads. (An earlier attempt injected a dedicated `.../anchor-host-registry`
35
+ // subpath instead; under pnpm symlinks that gave the leaf a SECOND resolved path — a second Set —
36
+ // so navigation-package registrations and createElement's lookup desynced. See the leaf header +
37
+ // angular-adapter §11c.)
38
+ const IMPORT_SOURCE = '@symbiote-native/angular';
39
+ const HELPER_NAME = 'registerComposedComponent';
40
+
41
+ function isNgDeclareComponentCall(node) {
42
+ return (
43
+ node.type === 'CallExpression' &&
44
+ node.callee.type === 'MemberExpression' &&
45
+ !node.callee.computed &&
46
+ node.callee.property.type === 'Identifier' &&
47
+ node.callee.property.name === 'ɵɵngDeclareComponent'
48
+ );
49
+ }
50
+
51
+ function selectorPropertyOf(objectExpression) {
52
+ return objectExpression.properties.find(
53
+ prop =>
54
+ prop.type === 'ObjectProperty' &&
55
+ !prop.computed &&
56
+ ((prop.key.type === 'Identifier' && prop.key.name === 'selector') ||
57
+ (prop.key.type === 'StringLiteral' && prop.key.value === 'selector')),
58
+ );
59
+ }
60
+
61
+ function composedSelectorsFromCall(node) {
62
+ const [arg] = node.arguments;
63
+ if (!arg || arg.type !== 'ObjectExpression') return [];
64
+ const selectorProp = selectorPropertyOf(arg);
65
+ if (!selectorProp || selectorProp.value.type !== 'StringLiteral') return [];
66
+ return selectorProp.value.value
67
+ .split(',')
68
+ .map(token => token.trim())
69
+ .filter(token => token.length > 0 && !PRIMITIVE_SELECTORS.has(token));
70
+ }
71
+
72
+ function hasComposedImport(programNode) {
73
+ return programNode.body.some(
74
+ node =>
75
+ node.type === 'ImportDeclaration' &&
76
+ node.source.value === IMPORT_SOURCE &&
77
+ node.specifiers.some(
78
+ spec =>
79
+ spec.type === 'ImportSpecifier' &&
80
+ spec.imported.type === 'Identifier' &&
81
+ spec.imported.name === HELPER_NAME,
82
+ ),
83
+ );
84
+ }
85
+
86
+ // Exposed as a property on the plugin function (not a separate export) so Babel still loads
87
+ // this file as a plain plugin factory; babel-register-composed.test.ts's drift-protection test
88
+ // reads it to compare against core/components/src/component-names/index.{ios,android}.ts.
89
+ module.exports = function registerComposedPlugin({ types: t }) {
90
+ return {
91
+ name: 'symbiote-register-composed',
92
+ visitor: {
93
+ Program(programPath) {
94
+ const selectors = new Set();
95
+ programPath.traverse({
96
+ CallExpression(path) {
97
+ if (isNgDeclareComponentCall(path.node)) {
98
+ for (const selector of composedSelectorsFromCall(path.node)) selectors.add(selector);
99
+ }
100
+ },
101
+ });
102
+ if (selectors.size === 0) return;
103
+
104
+ const statements = [...selectors].map(selector =>
105
+ t.expressionStatement(
106
+ t.callExpression(t.identifier(HELPER_NAME), [t.stringLiteral(selector)]),
107
+ ),
108
+ );
109
+
110
+ if (!hasComposedImport(programPath.node)) {
111
+ statements.unshift(
112
+ t.importDeclaration(
113
+ [t.importSpecifier(t.identifier(HELPER_NAME), t.identifier(HELPER_NAME))],
114
+ t.stringLiteral(IMPORT_SOURCE),
115
+ ),
116
+ );
117
+ }
118
+
119
+ // Import hoisting makes textual position irrelevant to `registerComposedComponent`'s
120
+ // availability, so unshifting the whole batch to the top keeps this single-pass.
121
+ programPath.unshiftContainer('body', statements);
122
+ },
123
+ },
124
+ };
125
+ };
126
+
127
+ module.exports.PRIMITIVE_SELECTORS = PRIMITIVE_SELECTORS;
@@ -0,0 +1,93 @@
1
+ #!/usr/bin/env node
2
+ // Cross-platform replacement for the old per-app dev-with-watch.sh: Angular needs a pre-Metro
3
+ // AOT compile (ngc), kept in sync via `ngc --watch` while developing. Metro itself must stay
4
+ // the FOREGROUND process — it reads raw keypresses
5
+ // (r/j/d/...) straight off stdin, and any wrapper that pipes stdin through itself
6
+ // (concurrently, npm-run-all, ...) breaks that raw-mode read. So ngc runs as a plain background
7
+ // child process, never a stdin-owning process manager. `shell: true` resolves `ngc`/
8
+ // `react-native` off PATH exactly like the bash script did — npm/pnpm/yarn already prepend
9
+ // every `node_modules/.bin` up the tree to PATH for any script invocation, this one included.
10
+ const { spawn, spawnSync } = require('node:child_process');
11
+ const path = require('node:path');
12
+ const fs = require('node:fs');
13
+ const ts = require('typescript');
14
+
15
+ const TSCONFIG = 'tsconfig.angular.json';
16
+ const metroArgs = process.argv.slice(2);
17
+ const projectRoot = process.cwd();
18
+
19
+ // perform_watch.js chokidar-watches angularCompilerOptions.basePath recursively (filtered only
20
+ // by a hardcoded node_modules/.dotfiles/.js/.map/.metadata.json regex — never ios/android/build),
21
+ // so an app's tsconfig.angular.json narrows basePath to its own src/ to keep the native platform
22
+ // trees out of the watch (see that file's own comment for the EMFILE story this fixes). That
23
+ // value is written relative (portable, checked in) — but @angular/compiler-cli's INCREMENTAL
24
+ // recompile path (oldProgram reuse, only reachable once `ngc --watch` is already running) calls
25
+ // absoluteFrom() on basePath directly and throws "TS500: ... path is not absolute" if it isn't
26
+ // already absolute, even though the initial cold compile tolerates a relative one fine. Resolve
27
+ // it here, at spawn time, into a throwaway override config — the checked-in tsconfig itself never
28
+ // carries a machine-specific absolute path.
29
+ function resolveWatchTsconfig(tsconfigName) {
30
+ const realPath = path.resolve(projectRoot, tsconfigName);
31
+ const { config, error } = ts.readConfigFile(realPath, ts.sys.readFile);
32
+ const basePath = config?.angularCompilerOptions?.basePath;
33
+ if (error || typeof basePath !== 'string' || path.isAbsolute(basePath)) {
34
+ return realPath;
35
+ }
36
+ // Written inside the project (build/, already gitignored everywhere this script runs) rather
37
+ // than os.tmpdir() — TS resolves default typeRoots/@types by walking up from the extending
38
+ // config's OWN directory, and a tmpdir has no node_modules above it, so an os.tmpdir() location
39
+ // broke `@types/node` resolution (TS2688) even though the extended real config was found fine.
40
+ const buildDir = path.resolve(projectRoot, 'build');
41
+ fs.mkdirSync(buildDir, { recursive: true });
42
+ const watchConfigPath = path.join(buildDir, `symbiote-angular-dev-watch-${process.pid}.json`);
43
+ fs.writeFileSync(
44
+ watchConfigPath,
45
+ JSON.stringify({
46
+ extends: realPath,
47
+ angularCompilerOptions: { basePath: path.resolve(projectRoot, basePath) },
48
+ }),
49
+ );
50
+ return watchConfigPath;
51
+ }
52
+
53
+ // Without watchman, Metro falls back to chokidar's native fs.watch, which opens one OS file
54
+ // handle per watched directory. This project's watchFolders spans the whole monorepo, so that
55
+ // reliably blows past macOS's per-process fd limit (EMFILE) — doubly likely here since ngc
56
+ // --watch adds a second watcher on top of Metro's own. Warn instead of letting everyone
57
+ // individually debug a native stack trace down to this one missing binary.
58
+ const watchmanCheck = spawnSync('watchman', ['--version'], { stdio: 'ignore', shell: true });
59
+ if (watchmanCheck.status !== 0) {
60
+ console.warn(
61
+ '[symbiote-angular-dev] watchman not found on PATH. Metro will fall back to watching files ' +
62
+ 'itself, which commonly crashes with "EMFILE: too many open files" on a repo this size. ' +
63
+ 'Install it: https://facebook.github.io/watchman/docs/install (macOS: brew install watchman).',
64
+ );
65
+ }
66
+
67
+ const initialBuild = spawnSync('ngc', ['-p', TSCONFIG], { stdio: 'inherit', shell: true });
68
+ if (initialBuild.status !== 0) {
69
+ process.exit(initialBuild.status ?? 1);
70
+ }
71
+
72
+ const watchTsconfigPath = resolveWatchTsconfig(TSCONFIG);
73
+ const ngcWatch = spawn('ngc', ['-p', watchTsconfigPath, '--watch'], { stdio: 'inherit', shell: true });
74
+ const metro = spawn('react-native', ['start', ...metroArgs], { stdio: 'inherit', shell: true });
75
+
76
+ function stopNgcWatch() {
77
+ ngcWatch.kill();
78
+ if (watchTsconfigPath !== path.resolve(projectRoot, TSCONFIG)) {
79
+ fs.rmSync(watchTsconfigPath, { force: true });
80
+ }
81
+ }
82
+
83
+ metro.on('exit', (code) => {
84
+ stopNgcWatch();
85
+ process.exit(code ?? 0);
86
+ });
87
+
88
+ for (const signal of ['SIGINT', 'SIGTERM']) {
89
+ process.on(signal, () => {
90
+ stopNgcWatch();
91
+ metro.kill(signal);
92
+ });
93
+ }
@@ -0,0 +1,2 @@
1
+ export declare function registerComposedComponent(selector: string): void;
2
+ export declare function isAnchorHostComponent(engineName: string): boolean;
@@ -0,0 +1,84 @@
1
+ // Registry of composed-component selectors that must NOT paint a native view of their own.
2
+ //
3
+ // A dependency-free LEAF module (imports nothing from the adapter barrel `./index` or
4
+ // `./components`, both deeply require-cyclic). Both consumers reach it by RELATIVE path — the
5
+ // renderer imports `isAnchorHostComponent` from `../anchor-host-registry`, the barrel re-exports
6
+ // `registerComposedComponent` from `./anchor-host-registry` — so Metro keys it to ONE module
7
+ // instance / ONE Set. Do NOT give it a package `exports` subpath and inject THAT bare specifier
8
+ // into app code: a subpath resolves via a different path than the relative imports under pnpm
9
+ // symlinks, which splits the Set in two.
10
+ //
11
+ // Housing the registry here rather than inline in `renderer/index.ts` keeps it out of the require
12
+ // cycle (cheap insurance against a load-order strand). The bug that actually surfaced this,
13
+ // though, was STALE BUILD ARTIFACTS, not the cycle: `ngc -p` never deletes orphaned outputs, so
14
+ // after the renderer moved `renderer.ts` → `renderer/index.ts` the orphaned `build/angular/
15
+ // renderer.js` lingered and SHADOWED `build/angular/renderer/index.js` (a file beats a folder in
16
+ // Node/Metro resolution), giving the bundle a second, stale registry Set — fixed by cleaning
17
+ // `build/` before every ngc build (see each Angular package's `clean` script). Full record:
18
+ // angular-adapter §11c, symbiote-dev-examples §5e.
19
+ // Lowercased at construction — isAnchorHostComponent and registerComposedComponent both normalize
20
+ // to lowercase (Angular lowercases a dynamically-mounted component's selector at runtime, see
21
+ // angular-adapter §11a), so the literal entries below must match that or every capitalized one
22
+ // (all but the handful already written lowercase) silently never matches .has() and falls through
23
+ // to a real Fabric createNode — the exact "Unimplemented component" / extra-wrapper-node bug this
24
+ // Set exists to prevent.
25
+ const ANCHOR_HOST_COMPONENTS = new Set([
26
+ // Composed Angular components render their real Fabric descriptor tree from the template;
27
+ // their Angular host element is only a framework bookkeeping node and must not paint. This
28
+ // is NOT limited to adapter-authored components — ANY custom composed @Component used as a
29
+ // plain <Tag> inside another template needs its selector listed here too, or Angular's
30
+ // automatic host-element creation for it falls through to a raw Fabric createNode call with
31
+ // an unrecognized view name, which paints RN's own "Unimplemented component: <Tag>" fallback
32
+ // view instead (a real device-visible bug, not a silent no-op). This Set holds only
33
+ // adapter/engine-owned selectors; app code and third-party packages self-register their own
34
+ // composed components through registerComposedComponent instead of being hardcoded here.
35
+ 'ActivityIndicator',
36
+ 'Button',
37
+ 'FlatList',
38
+ 'AnimatedView',
39
+ 'symbiote-animated-view',
40
+ 'AnimatedText',
41
+ 'symbiote-animated-text',
42
+ 'AnimatedImage',
43
+ 'symbiote-animated-image',
44
+ 'AnimatedScrollView',
45
+ 'symbiote-animated-scroll-view',
46
+ 'symbiote-descriptor-outlet',
47
+ 'tunnel-out',
48
+ 'Image',
49
+ 'ImageBackground',
50
+ 'InputAccessoryView',
51
+ 'KeyboardAvoidingView',
52
+ 'Modal',
53
+ 'Pressable',
54
+ 'RefreshControl',
55
+ 'SafeAreaView',
56
+ 'ScrollView',
57
+ 'ScrollViewStickyHeader',
58
+ 'SectionList',
59
+ 'symbiote-sticky-header',
60
+ 'StatusBar',
61
+ 'Switch',
62
+ 'Text',
63
+ 'TextInput',
64
+ 'TouchableHighlight',
65
+ 'TouchableNativeFeedback',
66
+ 'TouchableOpacity',
67
+ 'TouchableWithoutFeedback',
68
+ 'VirtualizedList',
69
+ 'VirtualizedSectionList',
70
+ 'symbiote-pressable',
71
+ ].map(selector => selector.toLowerCase()));
72
+ // A composed component's selector must be registered so createElement gives it a non-painting
73
+ // anchor host (see the Set comment above). Tests register their own child-component selectors
74
+ // through this at module load; app-authored composed components self-register the same way via
75
+ // the babel-register-composed plugin.
76
+ export function registerComposedComponent(selector) {
77
+ ANCHOR_HOST_COMPONENTS.add(selector.toLowerCase());
78
+ }
79
+ // True when `engineName` is a composed selector that must anchor-host (not paint). Case-
80
+ // insensitive — the Set is lowercased at construction, so callers pass the raw selector.
81
+ export function isAnchorHostComponent(engineName) {
82
+ return ANCHOR_HOST_COMPONENTS.has(engineName.toLowerCase());
83
+ }
84
+ //# sourceMappingURL=anchor-host-registry.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"anchor-host-registry.js","sourceRoot":"","sources":["../../src/anchor-host-registry.ts"],"names":[],"mappings":"AAAA,2FAA2F;AAC3F,EAAE;AACF,sFAAsF;AACtF,8FAA8F;AAC9F,iGAAiG;AACjG,6FAA6F;AAC7F,gGAAgG;AAChG,8FAA8F;AAC9F,yCAAyC;AACzC,EAAE;AACF,kGAAkG;AAClG,4FAA4F;AAC5F,gGAAgG;AAChG,4FAA4F;AAC5F,iGAAiG;AACjG,6FAA6F;AAC7F,4FAA4F;AAC5F,mDAAmD;AAEnD,kGAAkG;AAClG,8FAA8F;AAC9F,+FAA+F;AAC/F,kGAAkG;AAClG,kGAAkG;AAClG,yBAAyB;AACzB,MAAM,sBAAsB,GAAgB,IAAI,GAAG,CACjD;IACE,0FAA0F;IAC1F,2FAA2F;IAC3F,2FAA2F;IAC3F,uFAAuF;IACvF,4FAA4F;IAC5F,6FAA6F;IAC7F,oFAAoF;IACpF,4FAA4F;IAC5F,yFAAyF;IACzF,mBAAmB;IACnB,QAAQ;IACR,UAAU;IACV,cAAc;IACd,wBAAwB;IACxB,cAAc;IACd,wBAAwB;IACxB,eAAe;IACf,yBAAyB;IACzB,oBAAoB;IACpB,+BAA+B;IAC/B,4BAA4B;IAC5B,YAAY;IACZ,OAAO;IACP,iBAAiB;IACjB,oBAAoB;IACpB,sBAAsB;IACtB,OAAO;IACP,WAAW;IACX,gBAAgB;IAChB,cAAc;IACd,YAAY;IACZ,wBAAwB;IACxB,aAAa;IACb,wBAAwB;IACxB,WAAW;IACX,QAAQ;IACR,MAAM;IACN,WAAW;IACX,oBAAoB;IACpB,yBAAyB;IACzB,kBAAkB;IAClB,0BAA0B;IAC1B,iBAAiB;IACjB,wBAAwB;IACxB,oBAAoB;CACrB,CAAC,GAAG,CAAC,QAAQ,CAAC,EAAE,CAAC,QAAQ,CAAC,WAAW,EAAE,CAAC,CAC1C,CAAC;AAEF,8FAA8F;AAC9F,8FAA8F;AAC9F,+FAA+F;AAC/F,sCAAsC;AACtC,MAAM,UAAU,yBAAyB,CAAC,QAAgB;IACxD,sBAAsB,CAAC,GAAG,CAAC,QAAQ,CAAC,WAAW,EAAE,CAAC,CAAC;AACrD,CAAC;AAED,yFAAyF;AACzF,yFAAyF;AACzF,MAAM,UAAU,qBAAqB,CAAC,UAAkB;IACtD,OAAO,sBAAsB,CAAC,GAAG,CAAC,UAAU,CAAC,WAAW,EAAE,CAAC,CAAC;AAC9D,CAAC"}
@@ -0,0 +1,7 @@
1
+ import type { Type } from '@angular/core';
2
+ import { type IBootstrapHostOptions } from '@symbiote-native/components/bootstrap';
3
+ export type { IBootstrapHostOptions } from '@symbiote-native/components/bootstrap';
4
+ export type IBootstrapApplicationOptions = IBootstrapHostOptions & {
5
+ appName: string;
6
+ };
7
+ export declare function bootstrapApplication(AppComponent: Type<unknown>, options: IBootstrapApplicationOptions): void;
@@ -0,0 +1,15 @@
1
+ // Zero-config app entry, the Angular twin of adapters/react/src/bootstrap.ts. Lives OUTSIDE the
2
+ // package's main barrel — see that file's header for why anything importing react-native must
3
+ // stay there. No @Component/@Directive decorators here, so unlike the package's main "." entry
4
+ // this needs no ngc/AOT build step and can stay a plain source reference.
5
+ import { AppRegistry as RNAppRegistry } from 'react-native';
6
+ import { bootstrapHost } from '@symbiote-native/components/bootstrap';
7
+ import { AppRegistry, setHostRegistrar } from './modules/app-registry';
8
+ // Mirrors real Angular's bootstrapApplication(RootComponent, config) idiom.
9
+ export function bootstrapApplication(AppComponent, options) {
10
+ const { appName, ...bootstrapOptions } = options;
11
+ bootstrapHost(bootstrapOptions);
12
+ setHostRegistrar(RNAppRegistry);
13
+ AppRegistry.registerComponent(appName, () => AppComponent);
14
+ }
15
+ //# sourceMappingURL=bootstrap.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"bootstrap.js","sourceRoot":"","sources":["../../src/bootstrap.ts"],"names":[],"mappings":"AAAA,gGAAgG;AAChG,8FAA8F;AAC9F,+FAA+F;AAC/F,0EAA0E;AAE1E,OAAO,EAAE,WAAW,IAAI,aAAa,EAAE,MAAM,cAAc,CAAC;AAE5D,OAAO,EAAE,aAAa,EAA8B,MAAM,uCAAuC,CAAC;AAClG,OAAO,EAAE,WAAW,EAAE,gBAAgB,EAAE,MAAM,wBAAwB,CAAC;AAQvE,4EAA4E;AAC5E,MAAM,UAAU,oBAAoB,CAClC,YAA2B,EAC3B,OAAqC;IAErC,MAAM,EAAE,OAAO,EAAE,GAAG,gBAAgB,EAAE,GAAG,OAAO,CAAC;IACjD,aAAa,CAAC,gBAAgB,CAAC,CAAC;IAChC,gBAAgB,CAAC,aAAa,CAAC,CAAC;IAChC,WAAW,CAAC,iBAAiB,CAAC,OAAO,EAAE,GAAG,EAAE,CAAC,YAAY,CAAC,CAAC;AAC7D,CAAC"}
@@ -0,0 +1,12 @@
1
+ import { ActivityIndicatorBase } from './shared';
2
+ import * as i0 from "@angular/core";
3
+ export type { IActivityIndicatorProps } from './shared';
4
+ export declare class ActivityIndicator extends ActivityIndicatorBase {
5
+ protected readonly defaultColor: null;
6
+ protected readonly nativeExtras: {
7
+ styleAttr: string;
8
+ indeterminate: boolean;
9
+ };
10
+ static ɵfac: i0.ɵɵFactoryDeclaration<ActivityIndicator, never>;
11
+ static ɵcmp: i0.ɵɵComponentDeclaration<ActivityIndicator, "ActivityIndicator", never, {}, {}, never, never, true, never>;
12
+ }
@@ -0,0 +1,21 @@
1
+ import { ChangeDetectionStrategy, Component } from '@angular/core';
2
+ import { DescriptorOutlet } from '../../descriptor-to-angular';
3
+ import { ActivityIndicatorBase } from './shared';
4
+ import * as i0 from "@angular/core";
5
+ export class ActivityIndicator extends ActivityIndicatorBase {
6
+ defaultColor = null;
7
+ nativeExtras = { styleAttr: 'Normal', indeterminate: true };
8
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.0.5", ngImport: i0, type: ActivityIndicator, deps: null, target: i0.ɵɵFactoryTarget.Component });
9
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "22.0.5", type: ActivityIndicator, isStandalone: true, selector: "ActivityIndicator", usesInheritance: true, ngImport: i0, template: `<symbiote-descriptor-outlet [node]="descriptor" />`, isInline: true, dependencies: [{ kind: "component", type: DescriptorOutlet, selector: "symbiote-descriptor-outlet", inputs: ["node"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
10
+ }
11
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImport: i0, type: ActivityIndicator, decorators: [{
12
+ type: Component,
13
+ args: [{
14
+ selector: 'ActivityIndicator',
15
+ standalone: true,
16
+ imports: [DescriptorOutlet],
17
+ changeDetection: ChangeDetectionStrategy.OnPush,
18
+ template: `<symbiote-descriptor-outlet [node]="descriptor" />`,
19
+ }]
20
+ }] });
21
+ //# sourceMappingURL=index.android.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.android.js","sourceRoot":"","sources":["../../../../src/components/activity-indicator/index.android.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,uBAAuB,EAAE,SAAS,EAAE,MAAM,eAAe,CAAC;AACnE,OAAO,EAAE,gBAAgB,EAAE,MAAM,6BAA6B,CAAC;AAC/D,OAAO,EAAE,qBAAqB,EAAE,MAAM,UAAU,CAAC;;AAUjD,MAAM,OAAO,iBAAkB,SAAQ,qBAAqB;IACvC,YAAY,GAAG,IAAI,CAAC;IACX,YAAY,GAAG,EAAE,SAAS,EAAE,QAAQ,EAAE,aAAa,EAAE,IAAI,EAAE,CAAC;uGAF7E,iBAAiB;2FAAjB,iBAAiB,oGAFlB,oDAAoD,4DAFpD,gBAAgB;;2FAIf,iBAAiB;kBAP7B,SAAS;mBAAC;oBACT,QAAQ,EAAE,mBAAmB;oBAC7B,UAAU,EAAE,IAAI;oBAChB,OAAO,EAAE,CAAC,gBAAgB,CAAC;oBAC3B,eAAe,EAAE,uBAAuB,CAAC,MAAM;oBAC/C,QAAQ,EAAE,oDAAoD;iBAC/D"}
@@ -0,0 +1 @@
1
+ export * from './index.ios';
@@ -0,0 +1,8 @@
1
+ import { ActivityIndicatorBase } from './shared';
2
+ import * as i0 from "@angular/core";
3
+ export type { IActivityIndicatorProps } from './shared';
4
+ export declare class ActivityIndicator extends ActivityIndicatorBase {
5
+ protected readonly defaultColor = "#999999";
6
+ static ɵfac: i0.ɵɵFactoryDeclaration<ActivityIndicator, never>;
7
+ static ɵcmp: i0.ɵɵComponentDeclaration<ActivityIndicator, "ActivityIndicator", never, {}, {}, never, never, true, never>;
8
+ }
@@ -0,0 +1,21 @@
1
+ import { ChangeDetectionStrategy, Component } from '@angular/core';
2
+ import { DescriptorOutlet } from '../../descriptor-to-angular';
3
+ import { ActivityIndicatorBase } from './shared';
4
+ import * as i0 from "@angular/core";
5
+ const IOS_DEFAULT_COLOR = '#999999';
6
+ export class ActivityIndicator extends ActivityIndicatorBase {
7
+ defaultColor = IOS_DEFAULT_COLOR;
8
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "22.0.5", ngImport: i0, type: ActivityIndicator, deps: null, target: i0.ɵɵFactoryTarget.Component });
9
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "22.0.5", type: ActivityIndicator, isStandalone: true, selector: "ActivityIndicator", usesInheritance: true, ngImport: i0, template: `<symbiote-descriptor-outlet [node]="descriptor" />`, isInline: true, dependencies: [{ kind: "component", type: DescriptorOutlet, selector: "symbiote-descriptor-outlet", inputs: ["node"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
10
+ }
11
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "22.0.5", ngImport: i0, type: ActivityIndicator, decorators: [{
12
+ type: Component,
13
+ args: [{
14
+ selector: 'ActivityIndicator',
15
+ standalone: true,
16
+ imports: [DescriptorOutlet],
17
+ changeDetection: ChangeDetectionStrategy.OnPush,
18
+ template: `<symbiote-descriptor-outlet [node]="descriptor" />`,
19
+ }]
20
+ }] });
21
+ //# sourceMappingURL=index.ios.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.ios.js","sourceRoot":"","sources":["../../../../src/components/activity-indicator/index.ios.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,uBAAuB,EAAE,SAAS,EAAE,MAAM,eAAe,CAAC;AACnE,OAAO,EAAE,gBAAgB,EAAE,MAAM,6BAA6B,CAAC;AAC/D,OAAO,EAAE,qBAAqB,EAAE,MAAM,UAAU,CAAC;;AAGjD,MAAM,iBAAiB,GAAG,SAAS,CAAC;AASpC,MAAM,OAAO,iBAAkB,SAAQ,qBAAqB;IACvC,YAAY,GAAG,iBAAiB,CAAC;uGADzC,iBAAiB;2FAAjB,iBAAiB,oGAFlB,oDAAoD,4DAFpD,gBAAgB;;2FAIf,iBAAiB;kBAP7B,SAAS;mBAAC;oBACT,QAAQ,EAAE,mBAAmB;oBAC7B,UAAU,EAAE,IAAI;oBAChB,OAAO,EAAE,CAAC,gBAAgB,CAAC;oBAC3B,eAAe,EAAE,uBAAuB,CAAC,MAAM;oBAC/C,QAAQ,EAAE,oDAAoD;iBAC/D"}
@@ -0,0 +1,4 @@
1
+ // Base/default ActivityIndicator. Re-exports the iOS build; Metro picks index.ios.ts /
2
+ // index.android.ts in platform bundles.
3
+ export * from './index.ios';
4
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../src/components/activity-indicator/index.ts"],"names":[],"mappings":"AAAA,uFAAuF;AACvF,wCAAwC;AAExC,cAAc,aAAa,CAAC"}