@swiftbrowser/swift 0.0.0-stage → 0.2.0

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 (400) hide show
  1. package/Package.swift +214 -0
  2. package/README.md +10 -2
  3. package/Sources/AVFoundation/AVFoundation.swift +131 -0
  4. package/Sources/AVFoundation/Asset.swift +487 -0
  5. package/Sources/AVFoundation/AudioSession.swift +144 -0
  6. package/Sources/AVFoundation/CMTime.swift +303 -0
  7. package/Sources/AVFoundation/Capture.swift +688 -0
  8. package/Sources/AVFoundation/Player.swift +749 -0
  9. package/Sources/AVFoundation/PlayerView.swift +117 -0
  10. package/Sources/AVKit/AVKit.swift +132 -0
  11. package/Sources/Accelerate/Accelerate.swift +122 -0
  12. package/Sources/AppIntents/AppIntents.swift +144 -0
  13. package/Sources/AppIntents/Parameters.swift +220 -0
  14. package/Sources/AppIntents/Shortcuts.swift +159 -0
  15. package/Sources/AudioToolbox/AudioToolbox.swift +55 -0
  16. package/Sources/AuthenticationServices/AuthenticationServices.swift +257 -0
  17. package/Sources/AuthenticationServices/Authorization.swift +251 -0
  18. package/Sources/Charts/Charts.swift +61 -0
  19. package/Sources/Combine/AnyCancellable.swift +65 -0
  20. package/Sources/Combine/AnyPublisher.swift +148 -0
  21. package/Sources/Combine/AnySubscriber.swift +230 -0
  22. package/Sources/Combine/Cancellable.swift +35 -0
  23. package/Sources/Combine/Codable.swift +29 -0
  24. package/Sources/Combine/CombineIdentifier.swift +45 -0
  25. package/Sources/Combine/Concurrency/ConcurrencyHelpers.swift +24 -0
  26. package/Sources/Combine/Concurrency/Future+Concurrency.swift +136 -0
  27. package/Sources/Combine/Concurrency/GENERATED-Publisher+Concurrency.swift +397 -0
  28. package/Sources/Combine/CurrentValueSubject.swift +252 -0
  29. package/Sources/Combine/CustomCombineIdentifierConvertible.swift +28 -0
  30. package/Sources/Combine/Future.swift +228 -0
  31. package/Sources/Combine/GENERATED-RootProtocols.swift +426 -0
  32. package/Sources/Combine/Helpers/ConduitBase.swift +40 -0
  33. package/Sources/Combine/Helpers/ConduitList.swift +59 -0
  34. package/Sources/Combine/Helpers/DebugHook.swift +177 -0
  35. package/Sources/Combine/Helpers/FilterProducer.swift +174 -0
  36. package/Sources/Combine/Helpers/Locking.swift +30 -0
  37. package/Sources/Combine/Helpers/PartialCompletion.swift +26 -0
  38. package/Sources/Combine/Helpers/ReduceProducer.swift +249 -0
  39. package/Sources/Combine/Helpers/SubjectSubscriber.swift +96 -0
  40. package/Sources/Combine/Helpers/SubscriberTap.swift +69 -0
  41. package/Sources/Combine/Helpers/SubscriptionStatus.swift +33 -0
  42. package/Sources/Combine/Helpers/SubscriptionTap.swift +33 -0
  43. package/Sources/Combine/Helpers/Utils.swift +30 -0
  44. package/Sources/Combine/Helpers/Violations.swift +33 -0
  45. package/Sources/Combine/ImmediateScheduler.swift +178 -0
  46. package/Sources/Combine/LICENSE +21 -0
  47. package/Sources/Combine/NotificationPublisher.swift +48 -0
  48. package/Sources/Combine/ObjectWillChange.swift +46 -0
  49. package/Sources/Combine/PassthroughSubject.swift +222 -0
  50. package/Sources/Combine/Publisher+Subscribe.swift +53 -0
  51. package/Sources/Combine/Publishers/Deferred.swift +48 -0
  52. package/Sources/Combine/Publishers/Empty.swift +54 -0
  53. package/Sources/Combine/Publishers/Fail.swift +42 -0
  54. package/Sources/Combine/Publishers/GENERATED-Publishers.Catch.swift +673 -0
  55. package/Sources/Combine/Publishers/GENERATED-Publishers.Encode.swift +388 -0
  56. package/Sources/Combine/Publishers/GENERATED-Publishers.MapKeyPath.swift +384 -0
  57. package/Sources/Combine/Publishers/Just.swift +313 -0
  58. package/Sources/Combine/Publishers/Optional.Publisher.swift +315 -0
  59. package/Sources/Combine/Publishers/Publishers.AllSatisfy.swift +217 -0
  60. package/Sources/Combine/Publishers/Publishers.AssertNoFailure.swift +158 -0
  61. package/Sources/Combine/Publishers/Publishers.Autoconnect.swift +193 -0
  62. package/Sources/Combine/Publishers/Publishers.Breakpoint.swift +231 -0
  63. package/Sources/Combine/Publishers/Publishers.Buffer.swift +356 -0
  64. package/Sources/Combine/Publishers/Publishers.Collect.swift +102 -0
  65. package/Sources/Combine/Publishers/Publishers.CollectByCount.swift +195 -0
  66. package/Sources/Combine/Publishers/Publishers.CompactMap.swift +241 -0
  67. package/Sources/Combine/Publishers/Publishers.Comparison.swift +371 -0
  68. package/Sources/Combine/Publishers/Publishers.Concatenate.swift +474 -0
  69. package/Sources/Combine/Publishers/Publishers.Contains.swift +293 -0
  70. package/Sources/Combine/Publishers/Publishers.Count.swift +87 -0
  71. package/Sources/Combine/Publishers/Publishers.Debounce.swift +332 -0
  72. package/Sources/Combine/Publishers/Publishers.Delay.swift +269 -0
  73. package/Sources/Combine/Publishers/Publishers.Drop.swift +155 -0
  74. package/Sources/Combine/Publishers/Publishers.DropUntilOutput.swift +283 -0
  75. package/Sources/Combine/Publishers/Publishers.DropWhile.swift +378 -0
  76. package/Sources/Combine/Publishers/Publishers.Filter.swift +248 -0
  77. package/Sources/Combine/Publishers/Publishers.First.swift +261 -0
  78. package/Sources/Combine/Publishers/Publishers.FlatMap.swift +533 -0
  79. package/Sources/Combine/Publishers/Publishers.HandleEvents.swift +260 -0
  80. package/Sources/Combine/Publishers/Publishers.IgnoreOutput.swift +109 -0
  81. package/Sources/Combine/Publishers/Publishers.Last.swift +252 -0
  82. package/Sources/Combine/Publishers/Publishers.MakeConnectable.swift +82 -0
  83. package/Sources/Combine/Publishers/Publishers.Map.swift +351 -0
  84. package/Sources/Combine/Publishers/Publishers.MapError.swift +140 -0
  85. package/Sources/Combine/Publishers/Publishers.MeasureInterval.swift +187 -0
  86. package/Sources/Combine/Publishers/Publishers.Multicast.swift +284 -0
  87. package/Sources/Combine/Publishers/Publishers.Output.swift +241 -0
  88. package/Sources/Combine/Publishers/Publishers.PrefixUntilOutput.swift +197 -0
  89. package/Sources/Combine/Publishers/Publishers.PrefixWhile.swift +176 -0
  90. package/Sources/Combine/Publishers/Publishers.Print.swift +206 -0
  91. package/Sources/Combine/Publishers/Publishers.ReceiveOn.swift +227 -0
  92. package/Sources/Combine/Publishers/Publishers.Reduce.swift +204 -0
  93. package/Sources/Combine/Publishers/Publishers.RemoveDuplicates.swift +264 -0
  94. package/Sources/Combine/Publishers/Publishers.ReplaceEmpty.swift +201 -0
  95. package/Sources/Combine/Publishers/Publishers.ReplaceError.swift +211 -0
  96. package/Sources/Combine/Publishers/Publishers.Retry.swift +274 -0
  97. package/Sources/Combine/Publishers/Publishers.Scan.swift +331 -0
  98. package/Sources/Combine/Publishers/Publishers.Sequence.swift +437 -0
  99. package/Sources/Combine/Publishers/Publishers.SetFailureType.swift +120 -0
  100. package/Sources/Combine/Publishers/Publishers.Share.swift +104 -0
  101. package/Sources/Combine/Publishers/Publishers.SubscribeOn.swift +197 -0
  102. package/Sources/Combine/Publishers/Publishers.SwitchToLatest.swift +444 -0
  103. package/Sources/Combine/Publishers/Publishers.Throttle.swift +359 -0
  104. package/Sources/Combine/Publishers/Publishers.Timeout.swift +301 -0
  105. package/Sources/Combine/Publishers/Publishers.Zip.swift +720 -0
  106. package/Sources/Combine/Publishers/Publishers.swift +13 -0
  107. package/Sources/Combine/Publishers/Record.swift +237 -0
  108. package/Sources/Combine/Publishers/Result.Publisher.swift +337 -0
  109. package/Sources/Combine/Result.swift +46 -0
  110. package/Sources/Combine/Scheduler.swift +89 -0
  111. package/Sources/Combine/Schedulers.swift +211 -0
  112. package/Sources/Combine/Subject+Void.swift +17 -0
  113. package/Sources/Combine/Subscriber+Void.swift +20 -0
  114. package/Sources/Combine/Subscribers/Subscribers.Assign.swift +175 -0
  115. package/Sources/Combine/Subscribers/Subscribers.Completion.swift +90 -0
  116. package/Sources/Combine/Subscribers/Subscribers.Demand.swift +476 -0
  117. package/Sources/Combine/Subscribers/Subscribers.Sink.swift +206 -0
  118. package/Sources/Combine/Subscribers/Subscribers.swift +9 -0
  119. package/Sources/Combine/Subscription.swift +22 -0
  120. package/Sources/Combine/Subscriptions.swift +42 -0
  121. package/Sources/Combine/SwiftUIObservation.swift +10 -0
  122. package/Sources/Combine/_Introspection.swift +107 -0
  123. package/Sources/CommonCrypto/CommonCrypto.swift +80 -0
  124. package/Sources/Compression/Compression.swift +365 -0
  125. package/Sources/Compression/Deflate.swift +407 -0
  126. package/Sources/Compression/Zlib.swift +179 -0
  127. package/Sources/CoreFoundationTypes/CoreFoundationTypes.swift +101 -0
  128. package/Sources/CoreGraphics/CoreGraphics.swift +411 -0
  129. package/Sources/CoreGraphics/ProjectionTransforms.swift +28 -0
  130. package/Sources/CoreHaptics/CoreHaptics.swift +399 -0
  131. package/Sources/CoreImage/CIColor.swift +41 -0
  132. package/Sources/CoreImage/CIContext.swift +31 -0
  133. package/Sources/CoreImage/CIDetector.swift +57 -0
  134. package/Sources/CoreImage/CIFilter.swift +243 -0
  135. package/Sources/CoreImage/CIFilterBuiltins.swift +136 -0
  136. package/Sources/CoreImage/CIImage.swift +162 -0
  137. package/Sources/CoreImage/QRCode.swift +393 -0
  138. package/Sources/CoreLocation/Coordinate.swift +30 -0
  139. package/Sources/CoreLocation/Location.swift +65 -0
  140. package/Sources/CoreML/Evaluation.swift +414 -0
  141. package/Sources/CoreML/FeatureValue.swift +266 -0
  142. package/Sources/CoreML/Model.swift +269 -0
  143. package/Sources/CoreML/MultiArray.swift +92 -0
  144. package/Sources/CoreML/Specification.swift +233 -0
  145. package/Sources/CoreText/CoreText.swift +64 -0
  146. package/Sources/CoreTransferable/CoreTransferable.swift +606 -0
  147. package/Sources/CryptoKit/ChaChaPoly.swift +258 -0
  148. package/Sources/CryptoKit/CryptoKit.swift +375 -0
  149. package/Sources/CryptoKit/Curve25519.swift +317 -0
  150. package/Sources/CryptoKit/P256.swift +321 -0
  151. package/Sources/FoundationBridge/AppStorage.swift +165 -0
  152. package/Sources/FoundationBridge/AssetResources.swift +90 -0
  153. package/Sources/FoundationBridge/AsyncBytes.swift +128 -0
  154. package/Sources/FoundationBridge/AsyncImage.swift +116 -0
  155. package/Sources/FoundationBridge/AttributedStrings.swift +16 -0
  156. package/Sources/FoundationBridge/Bundle.swift +119 -0
  157. package/Sources/FoundationBridge/CombineExports.swift +8 -0
  158. package/Sources/FoundationBridge/CoreFoundation.swift +77 -0
  159. package/Sources/FoundationBridge/Dispatch.swift +458 -0
  160. package/Sources/FoundationBridge/EnvironmentFoundation.swift +41 -0
  161. package/Sources/FoundationBridge/FileImporter.swift +128 -0
  162. package/Sources/FoundationBridge/FileSystem.swift +68 -0
  163. package/Sources/FoundationBridge/FoundationBridge.swift +29 -0
  164. package/Sources/FoundationBridge/HostResolution.swift +31 -0
  165. package/Sources/FoundationBridge/ItemProvider.swift +655 -0
  166. package/Sources/FoundationBridge/KeyValueObserving.swift +138 -0
  167. package/Sources/FoundationBridge/Links.swift +127 -0
  168. package/Sources/FoundationBridge/ListFormatter.swift +32 -0
  169. package/Sources/FoundationBridge/Locale.swift +86 -0
  170. package/Sources/FoundationBridge/Localization.swift +149 -0
  171. package/Sources/FoundationBridge/Locks.swift +50 -0
  172. package/Sources/FoundationBridge/Markdown.swift +527 -0
  173. package/Sources/FoundationBridge/MeasurementFormat.swift +95 -0
  174. package/Sources/FoundationBridge/NotificationCenter.swift +154 -0
  175. package/Sources/FoundationBridge/OpenURLHandlers.swift +60 -0
  176. package/Sources/FoundationBridge/Operation.swift +195 -0
  177. package/Sources/FoundationBridge/ProcessInfo.swift +32 -0
  178. package/Sources/FoundationBridge/RelativeDateTimeFormatter.swift +136 -0
  179. package/Sources/FoundationBridge/SceneStorage.swift +78 -0
  180. package/Sources/FoundationBridge/SecurityExports.swift +8 -0
  181. package/Sources/FoundationBridge/Selector.swift +226 -0
  182. package/Sources/FoundationBridge/StringComparators.swift +17 -0
  183. package/Sources/FoundationBridge/Table.swift +211 -0
  184. package/Sources/FoundationBridge/TextAttributes.swift +42 -0
  185. package/Sources/FoundationBridge/Timer.swift +53 -0
  186. package/Sources/FoundationBridge/UITextChecker.swift +30 -0
  187. package/Sources/FoundationBridge/URLSession.swift +718 -0
  188. package/Sources/FoundationBridge/UserDefaults.swift +183 -0
  189. package/Sources/FoundationBridge/WebAuthRedirects.swift +227 -0
  190. package/Sources/FoundationBridge/WebSocket.swift +187 -0
  191. package/Sources/FoundationModels/FoundationModels.swift +1098 -0
  192. package/Sources/ImageIO/GIF.swift +72 -0
  193. package/Sources/ImageIO/ImageIO.swift +248 -0
  194. package/Sources/ImageIO/ImageTypes.swift +28 -0
  195. package/Sources/LinkPresentation/LinkPresentation.swift +249 -0
  196. package/Sources/LocalAuthentication/LAContext.swift +86 -0
  197. package/Sources/MapKit/Geometry.swift +223 -0
  198. package/Sources/MapKit/Map.swift +638 -0
  199. package/Sources/MapKit/MapView.swift +229 -0
  200. package/Sources/MobileCoreServices/MobileCoreServices.swift +28 -0
  201. package/Sources/NaturalLanguage/LanguageIdentifier.swift +317 -0
  202. package/Sources/NaturalLanguage/NaturalLanguage.swift +135 -0
  203. package/Sources/OSLog/OSLog.swift +6 -0
  204. package/Sources/Photos/Photos.swift +572 -0
  205. package/Sources/PhotosUI/PhotosPicker.swift +248 -0
  206. package/Sources/PhotosUI/PhotosPickerItem.swift +261 -0
  207. package/Sources/QuickLook/QuickLook.swift +168 -0
  208. package/Sources/SafariServices/SafariServices.swift +106 -0
  209. package/Sources/Security/Security.swift +332 -0
  210. package/Sources/StoreKit/AppStore.swift +207 -0
  211. package/Sources/StoreKit/Products.swift +280 -0
  212. package/Sources/StoreKit/RequestReview.swift +28 -0
  213. package/Sources/StoreKit/StoreKit1.swift +486 -0
  214. package/Sources/StoreKit/StoreViews.swift +428 -0
  215. package/Sources/StoreKit/Transactions.swift +197 -0
  216. package/Sources/SwiftData/Macros.swift +58 -0
  217. package/Sources/SwiftData/ModelActor.swift +38 -0
  218. package/Sources/SwiftData/ModelContainer.swift +129 -0
  219. package/Sources/SwiftData/ModelContext.swift +451 -0
  220. package/Sources/SwiftData/PersistentModel.swift +238 -0
  221. package/Sources/SwiftData/Properties.swift +261 -0
  222. package/Sources/SwiftData/Query.swift +256 -0
  223. package/Sources/SwiftData/Schema.swift +192 -0
  224. package/Sources/SwiftData/Store.swift +146 -0
  225. package/Sources/SwiftData/StringPredicates.swift +125 -0
  226. package/Sources/SwiftDataMacros/EntryMacro.swift +82 -0
  227. package/Sources/SwiftDataMacros/GenerableMacro.swift +183 -0
  228. package/Sources/SwiftDataMacros/ModelActorMacro.swift +46 -0
  229. package/Sources/SwiftDataMacros/ModelMacro.swift +260 -0
  230. package/Sources/SwiftDataMacros/Plugin.swift +18 -0
  231. package/Sources/SwiftDataMacros/PredicateMacro.swift +1244 -0
  232. package/Sources/SwiftUI/API/Accessibility.swift +181 -0
  233. package/Sources/SwiftUI/API/AccessibilityExtras.swift +33 -0
  234. package/Sources/SwiftUI/API/AccessibilityFocus.swift +63 -0
  235. package/Sources/SwiftUI/API/Alert.swift +221 -0
  236. package/Sources/SwiftUI/API/AlignmentGuides.swift +65 -0
  237. package/Sources/SwiftUI/API/Animation.swift +285 -0
  238. package/Sources/SwiftUI/API/App.swift +87 -0
  239. package/Sources/SwiftUI/API/BindingCollections.swift +35 -0
  240. package/Sources/SwiftUI/API/BindingForEach.swift +27 -0
  241. package/Sources/SwiftUI/API/Bitmaps.swift +254 -0
  242. package/Sources/SwiftUI/API/ButtonStyles.swift +96 -0
  243. package/Sources/SwiftUI/API/Canvas.swift +337 -0
  244. package/Sources/SwiftUI/API/Color.swift +237 -0
  245. package/Sources/SwiftUI/API/ColorEffects.swift +52 -0
  246. package/Sources/SwiftUI/API/ColorPickerAndLabeledContent.swift +138 -0
  247. package/Sources/SwiftUI/API/ColorSpaces.swift +161 -0
  248. package/Sources/SwiftUI/API/Commands.swift +106 -0
  249. package/Sources/SwiftUI/API/ContainerBackground.swift +28 -0
  250. package/Sources/SwiftUI/API/ContentShape.swift +33 -0
  251. package/Sources/SwiftUI/API/ContentSizeCategory.swift +35 -0
  252. package/Sources/SwiftUI/API/ContentUnavailable.swift +101 -0
  253. package/Sources/SwiftUI/API/Controls.swift +300 -0
  254. package/Sources/SwiftUI/API/CustomLayout.swift +442 -0
  255. package/Sources/SwiftUI/API/CustomToolbarContent.swift +46 -0
  256. package/Sources/SwiftUI/API/Decorations.swift +92 -0
  257. package/Sources/SwiftUI/API/EditMode.swift +212 -0
  258. package/Sources/SwiftUI/API/Effects.swift +388 -0
  259. package/Sources/SwiftUI/API/Entry.swift +8 -0
  260. package/Sources/SwiftUI/API/Environment.swift +439 -0
  261. package/Sources/SwiftUI/API/EnvironmentSendable.swift +6 -0
  262. package/Sources/SwiftUI/API/Focus.swift +137 -0
  263. package/Sources/SwiftUI/API/Font.swift +131 -0
  264. package/Sources/SwiftUI/API/Gauge.swift +290 -0
  265. package/Sources/SwiftUI/API/Geometry.swift +89 -0
  266. package/Sources/SwiftUI/API/GeometryEffects.swift +232 -0
  267. package/Sources/SwiftUI/API/GeometryReader.swift +135 -0
  268. package/Sources/SwiftUI/API/GestureState.swift +65 -0
  269. package/Sources/SwiftUI/API/Gestures.swift +342 -0
  270. package/Sources/SwiftUI/API/Glass.swift +127 -0
  271. package/Sources/SwiftUI/API/Grid.swift +188 -0
  272. package/Sources/SwiftUI/API/GroupBoxAndControlGroup.swift +130 -0
  273. package/Sources/SwiftUI/API/KeyPress.swift +54 -0
  274. package/Sources/SwiftUI/API/LabelStyle.swift +124 -0
  275. package/Sources/SwiftUI/API/Layout.swift +220 -0
  276. package/Sources/SwiftUI/API/LazyStacks.swift +49 -0
  277. package/Sources/SwiftUI/API/LegacyAlert.swift +97 -0
  278. package/Sources/SwiftUI/API/Lists.swift +331 -0
  279. package/Sources/SwiftUI/API/Menu.swift +58 -0
  280. package/Sources/SwiftUI/API/Modifiers.swift +313 -0
  281. package/Sources/SwiftUI/API/MoreModifiers.swift +100 -0
  282. package/Sources/SwiftUI/API/Namespace.swift +44 -0
  283. package/Sources/SwiftUI/API/Navigation.swift +386 -0
  284. package/Sources/SwiftUI/API/NavigationDestinationBindings.swift +55 -0
  285. package/Sources/SwiftUI/API/ObservableObject.swift +293 -0
  286. package/Sources/SwiftUI/API/OnChange.swift +48 -0
  287. package/Sources/SwiftUI/API/Path.swift +543 -0
  288. package/Sources/SwiftUI/API/Phase8Controls.swift +411 -0
  289. package/Sources/SwiftUI/API/PhaseAnimator.swift +130 -0
  290. package/Sources/SwiftUI/API/Picker.swift +185 -0
  291. package/Sources/SwiftUI/API/PointerAndKeyboard.swift +77 -0
  292. package/Sources/SwiftUI/API/Popover.swift +41 -0
  293. package/Sources/SwiftUI/API/Preferences.swift +262 -0
  294. package/Sources/SwiftUI/API/Presentation.swift +122 -0
  295. package/Sources/SwiftUI/API/PresentationExtras.swift +60 -0
  296. package/Sources/SwiftUI/API/Primitives.swift +517 -0
  297. package/Sources/SwiftUI/API/Publishers.swift +107 -0
  298. package/Sources/SwiftUI/API/Redaction.swift +75 -0
  299. package/Sources/SwiftUI/API/RowActions.swift +84 -0
  300. package/Sources/SwiftUI/API/Scenes.swift +131 -0
  301. package/Sources/SwiftUI/API/ScrollModifiers.swift +132 -0
  302. package/Sources/SwiftUI/API/ScrollTargets.swift +104 -0
  303. package/Sources/SwiftUI/API/ScrollViewReader.swift +144 -0
  304. package/Sources/SwiftUI/API/SectionSupplements.swift +96 -0
  305. package/Sources/SwiftUI/API/Shape.swift +214 -0
  306. package/Sources/SwiftUI/API/ShapeStyle.swift +409 -0
  307. package/Sources/SwiftUI/API/ShapeTrim.swift +78 -0
  308. package/Sources/SwiftUI/API/Sharing.swift +193 -0
  309. package/Sources/SwiftUI/API/StackLayouts.swift +199 -0
  310. package/Sources/SwiftUI/API/State.swift +144 -0
  311. package/Sources/SwiftUI/API/StatusGaps.swift +121 -0
  312. package/Sources/SwiftUI/API/StrokeStyle.swift +30 -0
  313. package/Sources/SwiftUI/API/SymbolEffects.swift +203 -0
  314. package/Sources/SwiftUI/API/TabContent.swift +841 -0
  315. package/Sources/SwiftUI/API/Table.swift +382 -0
  316. package/Sources/SwiftUI/API/Tabs.swift +263 -0
  317. package/Sources/SwiftUI/API/Tasks.swift +35 -0
  318. package/Sources/SwiftUI/API/Text.swift +386 -0
  319. package/Sources/SwiftUI/API/TextDates.swift +61 -0
  320. package/Sources/SwiftUI/API/TextDecorations.swift +52 -0
  321. package/Sources/SwiftUI/API/TextFieldAxis.swift +103 -0
  322. package/Sources/SwiftUI/API/TextFieldCommit.swift +52 -0
  323. package/Sources/SwiftUI/API/Timeline.swift +212 -0
  324. package/Sources/SwiftUI/API/Toolbar.swift +251 -0
  325. package/Sources/SwiftUI/API/Transfer.swift +145 -0
  326. package/Sources/SwiftUI/API/UnevenRoundedRectangle.swift +66 -0
  327. package/Sources/SwiftUI/API/Video.swift +64 -0
  328. package/Sources/SwiftUI/API/View.swift +215 -0
  329. package/Sources/SwiftUI/API/ViewModifier.swift +43 -0
  330. package/Sources/SwiftUI/API/VisualEffect.swift +155 -0
  331. package/Sources/SwiftUI/API/Windows.swift +25 -0
  332. package/Sources/SwiftUI/Charts/Axis.swift +325 -0
  333. package/Sources/SwiftUI/Charts/AxisFormatsAndRanges.swift +68 -0
  334. package/Sources/SwiftUI/Charts/Chart.swift +660 -0
  335. package/Sources/SwiftUI/Charts/ChartContent.swift +376 -0
  336. package/Sources/SwiftUI/Charts/ChartProxy.swift +57 -0
  337. package/Sources/SwiftUI/Charts/Marks.swift +204 -0
  338. package/Sources/SwiftUI/Charts/Plottable.swift +99 -0
  339. package/Sources/SwiftUI/Charts/Scales.swift +326 -0
  340. package/Sources/SwiftUI/Localization/Localization.swift +498 -0
  341. package/Sources/SwiftUI/Localization/PluralRules.swift +127 -0
  342. package/Sources/SwiftUI/Runtime/Executor.swift +85 -0
  343. package/Sources/SwiftUI/Runtime/Exports.swift +101 -0
  344. package/Sources/SwiftUI/Runtime/ImageSource.swift +310 -0
  345. package/Sources/SwiftUI/Runtime/JSON.swift +143 -0
  346. package/Sources/SwiftUI/Runtime/JSONParser.swift +443 -0
  347. package/Sources/SwiftUI/Runtime/LazyRows.swift +99 -0
  348. package/Sources/SwiftUI/Runtime/Measurements.swift +140 -0
  349. package/Sources/SwiftUI/Runtime/Ops.swift +152 -0
  350. package/Sources/SwiftUI/Runtime/Reconciler.swift +219 -0
  351. package/Sources/SwiftUI/Runtime/Replay.swift +382 -0
  352. package/Sources/SwiftUI/Runtime/Runtime.swift +2146 -0
  353. package/Sources/SwiftUI/Runtime/Sameness.swift +152 -0
  354. package/Sources/SwiftUI/Runtime/ViewPath.swift +89 -0
  355. package/Sources/SwiftUI/Runtime/ViewTraits.swift +175 -0
  356. package/Sources/SwiftUI/Runtime/WebAuthHeadless.swift +49 -0
  357. package/Sources/Symbols/Symbols.swift +25 -0
  358. package/Sources/Translation/Translation.swift +423 -0
  359. package/Sources/UIKit/Activity.swift +213 -0
  360. package/Sources/UIKit/Alerts.swift +69 -0
  361. package/Sources/UIKit/AppDelegate.swift +222 -0
  362. package/Sources/UIKit/Appearance.swift +84 -0
  363. package/Sources/UIKit/ColorConversions.swift +70 -0
  364. package/Sources/UIKit/Controls.swift +225 -0
  365. package/Sources/UIKit/Device.swift +200 -0
  366. package/Sources/UIKit/Feedback.swift +65 -0
  367. package/Sources/UIKit/Font.swift +307 -0
  368. package/Sources/UIKit/Graphics.swift +204 -0
  369. package/Sources/UIKit/HostingController.swift +185 -0
  370. package/Sources/UIKit/Identity.swift +24 -0
  371. package/Sources/UIKit/Introspectable.swift +510 -0
  372. package/Sources/UIKit/Pasteboard.swift +363 -0
  373. package/Sources/UIKit/PhotoAlbum.swift +81 -0
  374. package/Sources/UIKit/RemoteNotifications.swift +15 -0
  375. package/Sources/UIKit/Representable.swift +288 -0
  376. package/Sources/UIKit/SafeArea.swift +12 -0
  377. package/Sources/UIKit/SceneDelegates.swift +132 -0
  378. package/Sources/UIKit/Scenes.swift +40 -0
  379. package/Sources/UIKit/ScrollView.swift +157 -0
  380. package/Sources/UIKit/ShortcutItems.swift +67 -0
  381. package/Sources/UIKit/SymbolConfiguration.swift +124 -0
  382. package/Sources/UIKit/TargetAction.swift +123 -0
  383. package/Sources/UIKit/TextPaste.swift +161 -0
  384. package/Sources/UIKit/TextView.swift +538 -0
  385. package/Sources/UIKit/UIKit.swift +292 -0
  386. package/Sources/UIKit/UIView.swift +855 -0
  387. package/Sources/UIKit/ViewTranslation.swift +311 -0
  388. package/Sources/UniformTypeIdentifiers/UTType.swift +196 -0
  389. package/Sources/UserNotifications/Content.swift +370 -0
  390. package/Sources/UserNotifications/NotificationCenter.swift +309 -0
  391. package/Sources/WeatherKit/WeatherKit.swift +228 -0
  392. package/Sources/WebKit/WebKit.swift +245 -0
  393. package/Sources/os/os.swift +376 -0
  394. package/Sources/zlib/zlib.swift +6 -0
  395. package/index.d.ts +2 -0
  396. package/index.mjs +16 -0
  397. package/manifest.d.mts +2 -0
  398. package/manifest.mjs +39 -0
  399. package/package.json +30 -4
  400. package/sync-sources.mjs +33 -0
@@ -0,0 +1,96 @@
1
+ /// Custom button styles: `ButtonStyle` and `.buttonStyle(_:)` with one.
2
+ ///
3
+ /// A button under a custom style draws what the style's
4
+ /// `makeBody(configuration:)` returns in place of its label, inside the same
5
+ /// `button` element (the page's `plain` style: no tint and no chrome of its
6
+ /// own), so taps still run the action. The style's `@Environment` properties
7
+ /// are resolved like a view's. `isPressed` is always false: the page does not
8
+ /// report a press in progress, so a style's pressed look is never drawn.
9
+ /// A nearer `.buttonStyle` wins, custom or built in.
10
+
11
+ /// The view a style gets as `configuration.label`: the button's label.
12
+ public struct ButtonStyleConfiguration {
13
+ public struct Label {
14
+ let view: AnyView
15
+ }
16
+
17
+ /// The button's role (`.destructive`, `.cancel`), if any.
18
+ public let role: ButtonRole?
19
+ public let label: Label
20
+ /// Always false in the browser (see the file comment).
21
+ public let isPressed: Bool
22
+ }
23
+
24
+ extension ButtonStyleConfiguration.Label: View {
25
+ public typealias Body = Never
26
+ public var body: Never { fatalError("ButtonStyleConfiguration.Label is a primitive view") }
27
+ }
28
+ extension ButtonStyleConfiguration.Label: _PrimitiveView {}
29
+ extension ButtonStyleConfiguration.Label: _GroupView {
30
+ var _children: [any View] { [view] }
31
+ }
32
+
33
+ /// A style that draws a button from its label.
34
+ @MainActor @preconcurrency
35
+ public protocol ButtonStyle {
36
+ associatedtype Body: View
37
+ typealias Configuration = ButtonStyleConfiguration
38
+ @ViewBuilder func makeBody(configuration: Configuration) -> Body
39
+ }
40
+
41
+ /// The style a `.buttonStyle(_:)` put in the environment.
42
+ struct _CustomButtonStyle {
43
+ /// `_buttonStyle`'s value under a custom style; the page gets `plain`.
44
+ static let marker = "\u{1}custom"
45
+ let makeBody: @MainActor (ButtonStyleConfiguration) -> any View
46
+ }
47
+
48
+ struct _CustomButtonStyleKey: EnvironmentKey {
49
+ static var defaultValue: _CustomButtonStyle? { nil }
50
+ }
51
+
52
+ extension EnvironmentValues {
53
+ var _customButtonStyle: _CustomButtonStyle? {
54
+ get { self[_CustomButtonStyleKey.self] }
55
+ set { self[_CustomButtonStyleKey.self] = newValue }
56
+ }
57
+ }
58
+
59
+ /// Runs a style's `makeBody` as a view's body, so that the runtime resolves
60
+ /// the style's `@Environment` and `@State` properties (it reflects into a
61
+ /// stored `ButtonStyle` as into a `ViewModifier`).
62
+ struct _ButtonStyleBody<Style: ButtonStyle>: View {
63
+ let style: Style
64
+ let configuration: ButtonStyleConfiguration
65
+ var body: Style.Body { style.makeBody(configuration: configuration) }
66
+ }
67
+
68
+ extension _ButtonStyleBody: _HoldsModifier {}
69
+
70
+ nonisolated extension View {
71
+ /// Draws the buttons inside with `style` (see the file comment).
72
+ public func buttonStyle<S: ButtonStyle>(_ style: S) -> some View {
73
+ // Read on the main actor only, when a button's body is made.
74
+ nonisolated(unsafe) let style = style
75
+ return environment(\._buttonStyle, _CustomButtonStyle.marker)
76
+ .environment(\._customButtonStyle, _CustomButtonStyle { configuration in
77
+ _ButtonStyleBody(style: style, configuration: configuration)
78
+ })
79
+ }
80
+ }
81
+
82
+ /// A host view whose children depend on the environment (a button under a
83
+ /// custom style); checked by the runtime ahead of `_HostView._content`.
84
+ protocol _EnvironmentContent {
85
+ func _content(in environment: EnvironmentValues) -> [any View]
86
+ }
87
+
88
+ extension Button: _EnvironmentContent {
89
+ func _content(in environment: EnvironmentValues) -> [any View] {
90
+ guard environment._buttonStyle == _CustomButtonStyle.marker, let style = environment._customButtonStyle else {
91
+ return [label]
92
+ }
93
+ let configuration = ButtonStyleConfiguration(role: role, label: .init(view: AnyView(label)), isPressed: false)
94
+ return [MainActor.assumeIsolated { style.makeBody(configuration) }]
95
+ }
96
+ }
@@ -0,0 +1,337 @@
1
+ // `Canvas` and its `GraphicsContext`. The renderer closure runs in Swift
2
+ // against a context that records what it draws (paths filled or stroked,
3
+ // images, text) with the context's transform, opacity, blend mode, clip and
4
+ // filters at that moment; the page draws the list as SVG over the canvas's
5
+ // box, clipped to it (Web/src/canvasDrawing.ts, docs/ops-protocol.md,
6
+ // "Canvas"). A canvas fills the size it is offered, which reaches Swift as a
7
+ // `GeometryReader`'s does: the closure runs again with the laid-out size.
8
+ //
9
+ // Not drawn: `resolveSymbol(id:)` views (none resolve), bitmaps
10
+ // (`Image(uiImage:)`), and filters other than blur, shadow and the color
11
+ // adjustments. A resolved image or text knows no size (`.zero`).
12
+
13
+ public struct Canvas<Symbols: View>: View {
14
+ let renderer: (inout GraphicsContext, CGSize) -> Void
15
+ let symbols: Symbols
16
+ let isOpaque: Bool
17
+
18
+ public init(opaque: Bool = false, colorMode: ColorRenderingMode = .nonLinear, rendersAsynchronously: Bool = false,
19
+ renderer: @escaping (inout GraphicsContext, CGSize) -> Void, @ViewBuilder symbols: () -> Symbols) {
20
+ self.renderer = renderer
21
+ self.symbols = symbols()
22
+ self.isOpaque = opaque
23
+ }
24
+
25
+ public var body: some View {
26
+ GeometryReader { proxy in
27
+ _CanvasDrawing(size: proxy.size, renderer: renderer)
28
+ }
29
+ }
30
+ }
31
+
32
+ extension Canvas where Symbols == EmptyView {
33
+ public init(opaque: Bool = false, colorMode: ColorRenderingMode = .nonLinear, rendersAsynchronously: Bool = false,
34
+ renderer: @escaping (inout GraphicsContext, CGSize) -> Void) {
35
+ self.init(opaque: opaque, colorMode: colorMode, rendersAsynchronously: rendersAsynchronously, renderer: renderer) { EmptyView() }
36
+ }
37
+ }
38
+
39
+ /// The drawing of a canvas at one size: a `canvas` element whose props are the commands.
40
+ struct _CanvasDrawing {
41
+ let size: CGSize
42
+ let renderer: (inout GraphicsContext, CGSize) -> Void
43
+ }
44
+ extension _CanvasDrawing: _PrimitiveView {}
45
+ extension _CanvasDrawing: _HostView {
46
+ var _kind: String { "canvas" }
47
+ func _props(in environment: EnvironmentValues) -> _JSON {
48
+ let recorder = GraphicsContext._Recorder()
49
+ var context = GraphicsContext(recorder: recorder, environment: environment)
50
+ renderer(&context, size)
51
+ return .object([
52
+ "width": .number(size.width),
53
+ "height": .number(size.height),
54
+ "commands": .array(recorder.commands),
55
+ ])
56
+ }
57
+ }
58
+
59
+ /// What a `Canvas` draws with. A copy (as `drawLayer` gives) draws into the
60
+ /// same canvas with its own transform, opacity, clip and filters.
61
+ public struct GraphicsContext {
62
+ final class _Recorder {
63
+ var commands: [_JSON] = []
64
+ }
65
+
66
+ let recorder: _Recorder
67
+ public var environment: EnvironmentValues
68
+ public var transform: CGAffineTransform = .identity
69
+ public var opacity: Double = 1
70
+ public var blendMode: BlendMode = .normal
71
+ /// The clip paths, already in the canvas's coordinates.
72
+ var clips: [Path] = []
73
+ var filters: [_JSON] = []
74
+
75
+ init(recorder: _Recorder, environment: EnvironmentValues) {
76
+ self.recorder = recorder
77
+ self.environment = environment
78
+ }
79
+
80
+ // MARK: Transform
81
+
82
+ public mutating func translateBy(x: CGFloat, y: CGFloat) { transform = transform.translatedBy(x: x, y: y) }
83
+ public mutating func scaleBy(x: CGFloat, y: CGFloat) { transform = transform.scaledBy(x: x, y: y) }
84
+ public mutating func rotate(by angle: Angle) { transform = transform.rotated(by: angle.radians) }
85
+ public mutating func concatenate(_ matrix: CGAffineTransform) { transform = matrix.concatenating(transform) }
86
+
87
+ // MARK: Clip
88
+
89
+ public struct ClipOptions: OptionSet, Sendable {
90
+ public let rawValue: UInt32
91
+ public init(rawValue: UInt32) { self.rawValue = rawValue }
92
+ /// Clips to the outside of the path: not drawn here (the clip is left as is).
93
+ public static let inverse = ClipOptions(rawValue: 1)
94
+ }
95
+
96
+ public mutating func clip(to path: Path, style: FillStyle = FillStyle(), options: ClipOptions = []) {
97
+ guard !options.contains(.inverse) else { return }
98
+ clips.append(path.applying(transform))
99
+ }
100
+
101
+ public var clipBoundingRect: CGRect {
102
+ clips.last?.boundingRect ?? CGRect(x: -.greatestFiniteMagnitude / 2, y: -.greatestFiniteMagnitude / 2,
103
+ width: .greatestFiniteMagnitude, height: .greatestFiniteMagnitude)
104
+ }
105
+
106
+ // MARK: Layers and filters
107
+
108
+ public func drawLayer(content: (inout GraphicsContext) throws -> Void) rethrows {
109
+ var layer = self
110
+ try content(&layer)
111
+ }
112
+
113
+ public struct Filter: Sendable {
114
+ let json: _JSON
115
+
116
+ public static func blur(radius: CGFloat, options: BlurOptions = BlurOptions()) -> Filter {
117
+ Filter(json: .object(["blur": .number(radius)]))
118
+ }
119
+ public static func shadow(color: Color = Color(.sRGBLinear, white: 0, opacity: 0.33), radius: CGFloat,
120
+ x: CGFloat = 0, y: CGFloat = 0, blendMode: BlendMode = .normal, options: ShadowOptions = ShadowOptions()) -> Filter {
121
+ Filter(json: .object(["shadow": .object(["color": color._json, "radius": .number(radius), "x": .number(x), "y": .number(y)])]))
122
+ }
123
+ public static func grayscale(_ amount: Double) -> Filter { Filter(json: .object(["grayscale": .number(amount)])) }
124
+ public static func saturation(_ amount: Double) -> Filter { Filter(json: .object(["saturation": .number(amount)])) }
125
+ public static func brightness(_ amount: Double) -> Filter { Filter(json: .object(["brightness": .number(amount)])) }
126
+ public static func contrast(_ amount: Double) -> Filter { Filter(json: .object(["contrast": .number(amount)])) }
127
+ public static func hueRotation(_ angle: Angle) -> Filter { Filter(json: .object(["hueRotation": .number(angle.degrees)])) }
128
+ public static func colorInvert(_ amount: Double = 1) -> Filter { Filter(json: .object(["invert": .number(amount)])) }
129
+ /// Not drawn.
130
+ public static func colorMultiply(_ color: Color) -> Filter { Filter(json: .null) }
131
+ /// Not drawn.
132
+ public static var luminanceToAlpha: Filter { Filter(json: .null) }
133
+ /// Not drawn.
134
+ public static func alphaThreshold(min: Double, max: Double = 1, color: Color = .black) -> Filter { Filter(json: .null) }
135
+ }
136
+
137
+ public struct BlurOptions: OptionSet, Sendable {
138
+ public let rawValue: UInt32
139
+ public init(rawValue: UInt32) { self.rawValue = rawValue }
140
+ public static let opaque = BlurOptions(rawValue: 1)
141
+ public static let dithersResult = BlurOptions(rawValue: 2)
142
+ }
143
+
144
+ public struct ShadowOptions: OptionSet, Sendable {
145
+ public let rawValue: UInt32
146
+ public init(rawValue: UInt32) { self.rawValue = rawValue }
147
+ public static let shadowAbove = ShadowOptions(rawValue: 1)
148
+ public static let shadowOnly = ShadowOptions(rawValue: 2)
149
+ public static let invertsAlpha = ShadowOptions(rawValue: 4)
150
+ public static let disablesGroup = ShadowOptions(rawValue: 8)
151
+ }
152
+
153
+ public struct FilterOptions: OptionSet, Sendable {
154
+ public let rawValue: UInt32
155
+ public init(rawValue: UInt32) { self.rawValue = rawValue }
156
+ public static let linearColor = FilterOptions(rawValue: 1)
157
+ }
158
+
159
+ public mutating func addFilter(_ filter: Filter, options: FilterOptions = FilterOptions()) {
160
+ if filter.json != .null { filters.append(filter.json) }
161
+ }
162
+
163
+ // MARK: Shading
164
+
165
+ /// A paint: a color, a style, or a gradient in the context's coordinates.
166
+ public struct Shading: Sendable {
167
+ let json: _JSON
168
+
169
+ public static var foreground: Shading { Shading(json: ForegroundStyle()._json) }
170
+ public static func color(_ color: Color) -> Shading { Shading(json: color._json) }
171
+ public static func color(_ colorSpace: Color.RGBColorSpace = .sRGB, red: Double, green: Double, blue: Double, opacity: Double = 1) -> Shading {
172
+ .color(Color(colorSpace, red: red, green: green, blue: blue, opacity: opacity))
173
+ }
174
+ public static func color(_ colorSpace: Color.RGBColorSpace = .sRGB, white: Double, opacity: Double = 1) -> Shading {
175
+ .color(Color(colorSpace, white: white, opacity: opacity))
176
+ }
177
+ public static func style<S: ShapeStyle>(_ style: S) -> Shading { Shading(json: style._json) }
178
+ public static func palette(_ array: [Shading]) -> Shading { array.first ?? .foreground }
179
+
180
+ public static func linearGradient(_ gradient: Gradient, startPoint: CGPoint, endPoint: CGPoint, options: GradientOptions = GradientOptions()) -> Shading {
181
+ Shading(json: .object(["canvasLinearGradient": .object([
182
+ "stops": gradient._stopsJSON,
183
+ "start": point(startPoint), "end": point(endPoint),
184
+ ])]))
185
+ }
186
+ public static func radialGradient(_ gradient: Gradient, center: CGPoint, startRadius: CGFloat, endRadius: CGFloat, options: GradientOptions = GradientOptions()) -> Shading {
187
+ Shading(json: .object(["canvasRadialGradient": .object([
188
+ "stops": gradient._stopsJSON,
189
+ "center": point(center),
190
+ "startRadius": .number(startRadius), "endRadius": .number(endRadius),
191
+ ])]))
192
+ }
193
+ /// Drawn as its first color.
194
+ public static func conicGradient(_ gradient: Gradient, center: CGPoint, angle: Angle = Angle(), options: GradientOptions = GradientOptions()) -> Shading {
195
+ .color(gradient.stops.first?.color ?? .clear)
196
+ }
197
+
198
+ static func point(_ p: CGPoint) -> _JSON { .object(["x": .number(p.x), "y": .number(p.y)]) }
199
+ }
200
+
201
+ public struct GradientOptions: OptionSet, Sendable {
202
+ public let rawValue: UInt32
203
+ public init(rawValue: UInt32) { self.rawValue = rawValue }
204
+ public static let `repeat` = GradientOptions(rawValue: 1)
205
+ public static let mirror = GradientOptions(rawValue: 2)
206
+ public static let linearColor = GradientOptions(rawValue: 4)
207
+ }
208
+
209
+ // MARK: Drawing
210
+
211
+ public func fill(_ path: Path, with shading: Shading, style: FillStyle = FillStyle()) {
212
+ var command: [String: _JSON] = ["op": .string("fill"), "path": .string(path._svg), "shading": shading.json]
213
+ if style.isEOFilled { command["evenOdd"] = .bool(true) }
214
+ record(command)
215
+ }
216
+
217
+ public func stroke(_ path: Path, with shading: Shading, style: StrokeStyle) {
218
+ var command: [String: _JSON] = [
219
+ "op": .string("stroke"), "path": .string(path._svg), "shading": shading.json,
220
+ "lineWidth": .number(style.lineWidth),
221
+ ]
222
+ command["lineCap"] = .string(style.lineCap == .round ? "round" : style.lineCap == .square ? "square" : "butt")
223
+ command["lineJoin"] = .string(style.lineJoin == .round ? "round" : style.lineJoin == .bevel ? "bevel" : "miter")
224
+ command["miterLimit"] = .number(style.miterLimit)
225
+ if !style.dash.isEmpty {
226
+ command["dash"] = .array(style.dash.map { .number($0) })
227
+ command["dashPhase"] = .number(style.dashPhase)
228
+ }
229
+ record(command)
230
+ }
231
+
232
+ public func stroke(_ path: Path, with shading: Shading, lineWidth: CGFloat = 1) {
233
+ stroke(path, with: shading, style: StrokeStyle(lineWidth: lineWidth))
234
+ }
235
+
236
+ /// An image or text made ready to draw (`resolve(_:)`); its size is not known here.
237
+ public struct ResolvedImage {
238
+ let image: Image
239
+ public var size: CGSize { .zero }
240
+ public var baseline: CGFloat { 0 }
241
+ public var shading: Shading?
242
+ }
243
+
244
+ public struct ResolvedText {
245
+ let text: Text
246
+ public var shading: Shading = .foreground
247
+ public func measure(in size: CGSize) -> CGSize { .zero }
248
+ public func firstBaseline(in size: CGSize) -> CGFloat { 0 }
249
+ public func lastBaseline(in size: CGSize) -> CGFloat { 0 }
250
+ }
251
+
252
+ /// A view passed to `Canvas(renderer:symbols:)`; none resolve here.
253
+ public struct ResolvedSymbol {
254
+ public var size: CGSize { .zero }
255
+ }
256
+
257
+ public func resolve(_ image: Image) -> ResolvedImage { ResolvedImage(image: image) }
258
+ public func resolve(_ text: Text) -> ResolvedText { ResolvedText(text: text) }
259
+ public func resolveSymbol<ID: Hashable>(id: ID) -> ResolvedSymbol? { nil }
260
+
261
+ public func draw(_ image: ResolvedImage, at point: CGPoint, anchor: UnitPoint = .center) {
262
+ drawImage(image.image, at: point, anchor: anchor, shading: image.shading)
263
+ }
264
+
265
+ public func draw(_ image: ResolvedImage, in rect: CGRect, style: FillStyle = FillStyle()) {
266
+ drawImage(image.image, in: rect, shading: image.shading)
267
+ }
268
+
269
+ public func draw(_ image: Image, at point: CGPoint, anchor: UnitPoint = .center) {
270
+ drawImage(image, at: point, anchor: anchor, shading: nil)
271
+ }
272
+
273
+ public func draw(_ image: Image, in rect: CGRect, style: FillStyle = FillStyle()) {
274
+ drawImage(image, in: rect, shading: nil)
275
+ }
276
+
277
+ public func draw(_ text: ResolvedText, at point: CGPoint, anchor: UnitPoint = .center) {
278
+ drawText(text.text, at: point, anchor: anchor, shading: text.shading)
279
+ }
280
+
281
+ public func draw(_ text: ResolvedText, in rect: CGRect) {
282
+ drawText(text.text, at: CGPoint(x: rect.minX, y: rect.minY), anchor: .topLeading, shading: text.shading)
283
+ }
284
+
285
+ public func draw(_ text: Text, at point: CGPoint, anchor: UnitPoint = .center) {
286
+ drawText(text, at: point, anchor: anchor, shading: .foreground)
287
+ }
288
+
289
+ public func draw(_ text: Text, in rect: CGRect) {
290
+ drawText(text, at: CGPoint(x: rect.minX, y: rect.minY), anchor: .topLeading, shading: .foreground)
291
+ }
292
+
293
+ public func draw(_ symbol: ResolvedSymbol, at point: CGPoint, anchor: UnitPoint = .center) {}
294
+ public func draw(_ symbol: ResolvedSymbol, in rect: CGRect) {}
295
+
296
+ private func drawImage(_ image: Image, at point: CGPoint, anchor: UnitPoint, shading: Shading?) {
297
+ var command: [String: _JSON] = [
298
+ "op": .string("image"), "image": image._props(in: environment),
299
+ "x": .number(point.x), "y": .number(point.y), "anchor": anchor._json,
300
+ ]
301
+ if let shading { command["shading"] = shading.json }
302
+ record(command)
303
+ }
304
+
305
+ private func drawImage(_ image: Image, in rect: CGRect, shading: Shading?) {
306
+ var command: [String: _JSON] = [
307
+ "op": .string("image"), "image": image._props(in: environment),
308
+ "x": .number(rect.minX), "y": .number(rect.minY), "anchor": UnitPoint.topLeading._json,
309
+ "width": .number(rect.width), "height": .number(rect.height),
310
+ ]
311
+ if let shading { command["shading"] = shading.json }
312
+ record(command)
313
+ }
314
+
315
+ private func drawText(_ text: Text, at point: CGPoint, anchor: UnitPoint, shading: Shading) {
316
+ var command: [String: _JSON] = [
317
+ "op": .string("text"), "text": .string(text.content),
318
+ "x": .number(point.x), "y": .number(point.y), "anchor": anchor._json,
319
+ "shading": shading.json,
320
+ ]
321
+ if let font = environment.font { command["font"] = font._json }
322
+ record(command)
323
+ }
324
+
325
+ /// Adds the context's state to a command and records it.
326
+ private func record(_ command: [String: _JSON]) {
327
+ var command = command
328
+ if !transform.isIdentity {
329
+ command["transform"] = .array([transform.a, transform.b, transform.c, transform.d, transform.tx, transform.ty].map { .number($0) })
330
+ }
331
+ if opacity < 1 { command["opacity"] = .number(max(0, opacity)) }
332
+ if blendMode != .normal { command["blendMode"] = .string(blendMode._css) }
333
+ if !clips.isEmpty { command["clips"] = .array(clips.map { .string($0._svg) }) }
334
+ if !filters.isEmpty { command["filters"] = .array(filters) }
335
+ recorder.commands.append(.object(command))
336
+ }
337
+ }
@@ -0,0 +1,237 @@
1
+ public struct Color: Hashable, Sendable {
2
+ enum Storage: Hashable, Sendable {
3
+ case rgba(red: Double, green: Double, blue: Double, opacity: Double)
4
+ case semantic(name: String, opacity: Double)
5
+ /// A `.colorset` from the asset catalog (light/dark resolved by the renderer).
6
+ case named(name: String, opacity: Double)
7
+ }
8
+
9
+ let storage: Storage
10
+
11
+ public init(red: Double, green: Double, blue: Double, opacity: Double = 1) {
12
+ storage = .rgba(red: red, green: green, blue: blue, opacity: opacity)
13
+ }
14
+
15
+ /// A color from the asset catalog, possibly namespaced (`"dough/plain-bg"`).
16
+ /// `Color(_:bundle:)` is FoundationBridge's (see `Image.init(_:)`).
17
+ public init(_ name: String) {
18
+ storage = .named(name: name, opacity: 1)
19
+ }
20
+
21
+ public init(white: Double, opacity: Double = 1) {
22
+ storage = .rgba(red: white, green: white, blue: white, opacity: opacity)
23
+ }
24
+
25
+ init(semantic name: String) {
26
+ storage = .semantic(name: name, opacity: 1)
27
+ }
28
+
29
+ /// A color from hue, saturation and brightness (each 0…1; a hue of 1 is red again).
30
+ public init(hue: Double, saturation: Double, brightness: Double, opacity: Double = 1) {
31
+ let h = (hue - hue.rounded(.down)) * 6
32
+ let s = max(0, min(1, saturation)), v = max(0, min(1, brightness))
33
+ let sector = Int(h) % 6
34
+ let f = h - Double(Int(h))
35
+ let (p, q, t) = (v * (1 - s), v * (1 - s * f), v * (1 - s * (1 - f)))
36
+ let (r, g, b): (Double, Double, Double) = switch sector {
37
+ case 0: (v, t, p)
38
+ case 1: (q, v, p)
39
+ case 2: (p, v, t)
40
+ case 3: (p, q, v)
41
+ case 4: (t, p, v)
42
+ default: (v, p, q)
43
+ }
44
+ storage = .rgba(red: r, green: g, blue: b, opacity: opacity)
45
+ }
46
+
47
+ /// A semantic color the page resolves per color scheme, by its iOS name
48
+ /// (`label`, `systemGroupedBackground`…): UIKit's `Color(uiColor:)`.
49
+ public init(_semantic name: String, opacity: Double = 1) {
50
+ storage = .semantic(name: name, opacity: opacity)
51
+ }
52
+
53
+ // iOS system palette: semantic, so the page draws each in the color
54
+ // scheme's appearance (`--sb-color-<name>`), as iOS does.
55
+ public static let red = Color(semantic: "red")
56
+ public static let orange = Color(semantic: "orange")
57
+ public static let yellow = Color(semantic: "yellow")
58
+ public static let green = Color(semantic: "green")
59
+ public static let mint = Color(semantic: "mint")
60
+ public static let teal = Color(semantic: "teal")
61
+ public static let cyan = Color(semantic: "cyan")
62
+ public static let blue = Color(semantic: "blue")
63
+ public static let indigo = Color(semantic: "indigo")
64
+ public static let purple = Color(semantic: "purple")
65
+ public static let pink = Color(semantic: "pink")
66
+ public static let brown = Color(semantic: "brown")
67
+ public static let gray = Color(semantic: "gray")
68
+ public static let black = Color(red: 0, green: 0, blue: 0)
69
+ public static let white = Color(red: 1, green: 1, blue: 1)
70
+
71
+ // Semantic colors the renderer resolves per color scheme.
72
+ public static let clear = Color(semantic: "clear")
73
+ public static let primary = Color(semantic: "primary")
74
+ public static let secondary = Color(semantic: "secondary")
75
+ public static let accentColor = Color(semantic: "accent")
76
+
77
+ public func opacity(_ opacity: Double) -> Color {
78
+ switch storage {
79
+ case .rgba(let r, let g, let b, let a):
80
+ Color(red: r, green: g, blue: b, opacity: a * opacity)
81
+ case .semantic(let name, let a):
82
+ Color(storage: .semantic(name: name, opacity: a * opacity))
83
+ case .named(let name, let a):
84
+ Color(storage: .named(name: name, opacity: a * opacity))
85
+ }
86
+ }
87
+
88
+ init(storage: Storage) { self.storage = storage }
89
+
90
+ public var _json: _JSON {
91
+ switch storage {
92
+ case .rgba(let r, let g, let b, let a):
93
+ .object(["r": .number(r), "g": .number(g), "b": .number(b), "a": .number(a)])
94
+ case .semantic(let name, let a):
95
+ a == 1 ? .object(["name": .string(name)]) : .object(["name": .string(name), "a": .number(a)])
96
+ case .named(let name, let a):
97
+ .object(["named": .string(name), "opacity": .number(a)])
98
+ }
99
+ }
100
+ }
101
+
102
+ // MARK: - Shapes
103
+
104
+ /// A 2D shape: its outline for a rectangle, drawn as a view (filled with the
105
+ /// foreground style unless `fill` or `stroke` say otherwise).
106
+ ///
107
+ /// The built-in shapes (`_name` other than `"path"`) are drawn by the page
108
+ /// from their name and corner radius. Any other shape is drawn from its
109
+ /// `path(in:)` (Shape.swift): the page reports the size it laid the shape out
110
+ /// at, and the path for that size comes back as SVG, one render later.
111
+ public protocol Shape: Sendable, Animatable, View {
112
+ func path(in rect: CGRect) -> Path
113
+ /// The built-in shape the page draws by name, or `"path"`.
114
+ var _name: String { get }
115
+ var _cornerRadius: CGFloat { get }
116
+ }
117
+
118
+ nonisolated extension Shape {
119
+ public var _name: String { "path" }
120
+ public var _cornerRadius: CGFloat { 0 }
121
+ }
122
+
123
+ nonisolated public struct Rectangle: Shape {
124
+ public init() {}
125
+ public var _name: String { "rectangle" }
126
+ public var _cornerRadius: CGFloat { 0 }
127
+ public func path(in rect: CGRect) -> Path { Path(rect) }
128
+ }
129
+
130
+ /// Accepted for source compatibility; corners render continuous either way.
131
+ public enum RoundedCornerStyle: Hashable, Sendable {
132
+ case circular, continuous
133
+ }
134
+
135
+ nonisolated public struct RoundedRectangle: Shape {
136
+ public var cornerRadius: CGFloat
137
+ public var style: RoundedCornerStyle
138
+ public init(cornerRadius: CGFloat, style: RoundedCornerStyle = .continuous) {
139
+ self.cornerRadius = cornerRadius
140
+ self.style = style
141
+ }
142
+ public init(cornerSize: CGSize, style: RoundedCornerStyle = .continuous) {
143
+ cornerRadius = min(cornerSize.width, cornerSize.height)
144
+ self.style = style
145
+ }
146
+ public var _name: String { "roundedRectangle" }
147
+ public var _cornerRadius: CGFloat { cornerRadius }
148
+ public func path(in rect: CGRect) -> Path { Path(roundedRect: rect, cornerRadius: cornerRadius, style: style) }
149
+ }
150
+
151
+ nonisolated public struct Circle: Shape {
152
+ public init() {}
153
+ public var _name: String { "circle" }
154
+ public var _cornerRadius: CGFloat { 9999 }
155
+ /// The largest circle centered in `rect`.
156
+ public func path(in rect: CGRect) -> Path {
157
+ let side = min(rect.width, rect.height)
158
+ return Path(ellipseIn: CGRect(x: rect.midX - side / 2, y: rect.midY - side / 2, width: side, height: side))
159
+ }
160
+ }
161
+
162
+ nonisolated public struct Capsule: Shape {
163
+ public var style: RoundedCornerStyle
164
+ public init(style: RoundedCornerStyle = .continuous) { self.style = style }
165
+ public var _name: String { "capsule" }
166
+ public var _cornerRadius: CGFloat { 9999 }
167
+ public func path(in rect: CGRect) -> Path {
168
+ Path(roundedRect: rect, cornerRadius: min(rect.width, rect.height) / 2, style: style)
169
+ }
170
+ }
171
+
172
+ nonisolated public struct Ellipse: Shape {
173
+ public init() {}
174
+ public var _name: String { "ellipse" }
175
+ public var _cornerRadius: CGFloat { 9999 }
176
+ public func path(in rect: CGRect) -> Path { Path(ellipseIn: rect) }
177
+ }
178
+
179
+ /// The shape of the nearest container (`.containerShape(_:)`): its corner
180
+ /// radius, read from the environment where the shape is drawn
181
+ /// (`_resolvedCornerRadius`); a rectangle when no container sets one, as in
182
+ /// SwiftUI. Its own path (a custom shape's use) is a rectangle.
183
+ nonisolated public struct ContainerRelativeShape: Shape {
184
+ public init() {}
185
+ public var _name: String { "containerRelative" }
186
+ public var _cornerRadius: CGFloat { 0 }
187
+ public func path(in rect: CGRect) -> Path { Path(rect) }
188
+ }
189
+
190
+ /// The corner radius `shape` is drawn with in `environment`: a
191
+ /// `ContainerRelativeShape` takes its container's.
192
+ func _resolvedCornerRadius(_ shape: some Shape, in environment: EnvironmentValues) -> CGFloat {
193
+ if shape is ContainerRelativeShape { return environment._containerShapeRadius ?? 0 }
194
+ if let inset = shape as? _InsetShape<ContainerRelativeShape> {
195
+ return max(0, (environment._containerShapeRadius ?? 0) - inset.amount)
196
+ }
197
+ return shape._cornerRadius
198
+ }
199
+
200
+ private struct _ContainerShapeRadiusKey: EnvironmentKey {
201
+ static var defaultValue: CGFloat? { nil }
202
+ }
203
+
204
+ extension EnvironmentValues {
205
+ /// The corner radius of the shape `.containerShape(_:)` set above (nil: none).
206
+ var _containerShapeRadius: CGFloat? {
207
+ get { self[_ContainerShapeRadiusKey.self] }
208
+ set { self[_ContainerShapeRadiusKey.self] = newValue }
209
+ }
210
+ }
211
+
212
+ // Shapes as static members (`.clipShape(.capsule)`, `.background(.red, in: .rect(cornerRadius: 8))`).
213
+ extension Shape where Self == Capsule {
214
+ public static var capsule: Capsule { Capsule() }
215
+ /// The shape of a button's border; drawn as a capsule.
216
+ public static var buttonBorder: Capsule { Capsule() }
217
+ }
218
+ extension Shape where Self == Circle {
219
+ public static var circle: Circle { Circle() }
220
+ }
221
+ extension Shape where Self == Ellipse {
222
+ public static var ellipse: Ellipse { Ellipse() }
223
+ }
224
+ extension Shape where Self == Rectangle {
225
+ public static var rect: Rectangle { Rectangle() }
226
+ }
227
+ extension Shape where Self == RoundedRectangle {
228
+ public static func rect(cornerRadius: CGFloat, style: RoundedCornerStyle = .continuous) -> RoundedRectangle {
229
+ RoundedRectangle(cornerRadius: cornerRadius, style: style)
230
+ }
231
+ public static func rect(cornerSize: CGSize, style: RoundedCornerStyle = .continuous) -> RoundedRectangle {
232
+ RoundedRectangle(cornerSize: cornerSize, style: style)
233
+ }
234
+ }
235
+ extension Shape where Self == ContainerRelativeShape {
236
+ public static var containerRelative: ContainerRelativeShape { ContainerRelativeShape() }
237
+ }