@satinhq/kit 0.1.0-beta.3 → 0.1.0-beta.4

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 (240) hide show
  1. package/NOTICE +1 -1
  2. package/README.md +1 -2
  3. package/dist/acknowledgements/inventory.json +1 -1
  4. package/dist/actions/RowActions.d.ts +2 -2
  5. package/dist/actions/RowActions.js +91 -25
  6. package/dist/actions/fullSwipeContact.d.ts +73 -0
  7. package/dist/actions/fullSwipeContact.js +186 -0
  8. package/dist/actions/rowScrub.d.ts +7 -4
  9. package/dist/actions/rowScrub.js +39 -37
  10. package/dist/actions/types.d.ts +13 -7
  11. package/dist/app/InstallComponents.d.ts +4 -7
  12. package/dist/app/InstallComponents.js +7 -7
  13. package/dist/app/InstallationDiagnostics.d.ts +2 -1
  14. package/dist/app/InstallationDiagnostics.js +2 -1
  15. package/dist/app/appearance.d.ts +5 -3
  16. package/dist/app/appearance.js +5 -3
  17. package/dist/app/appearanceStore.d.ts +3 -2
  18. package/dist/app/buildInfo.d.ts +4 -4
  19. package/dist/app/buildInfo.js +2 -2
  20. package/dist/app/definition.d.ts +11 -3
  21. package/dist/app/definition.js +2 -0
  22. package/dist/app/head.d.ts +2 -1
  23. package/dist/app/head.js +13 -16
  24. package/dist/app/inlineCSP.d.ts +6 -0
  25. package/dist/app/inlineCSP.js +25 -0
  26. package/dist/app/install.d.ts +1 -0
  27. package/dist/app/install.js +5 -2
  28. package/dist/app/installCheck.js +32 -86
  29. package/dist/app/installContext.d.ts +10 -5
  30. package/dist/app/installContext.js +2 -0
  31. package/dist/app/installCustom.js +1 -0
  32. package/dist/app/installExperience.js +0 -60
  33. package/dist/app/installationFailure.d.ts +3 -2
  34. package/dist/app/installationFailure.js +1 -1
  35. package/dist/app/launchScreen.d.ts +6 -2
  36. package/dist/app/launchScreen.js +104 -1
  37. package/dist/app/launchScreenRuntime.d.ts +31 -4
  38. package/dist/app/launchScreenRuntime.js +150 -22
  39. package/dist/app/launchWatchdog.js +25 -65
  40. package/dist/app/platformScripts.js +11 -0
  41. package/dist/app/styles.d.ts +3 -0
  42. package/dist/app/styles.js +42 -0
  43. package/dist/app/viewportValue.d.ts +2 -1
  44. package/dist/app/vite.d.ts +4 -0
  45. package/dist/app/vite.js +22 -24
  46. package/dist/content/content.d.ts +35 -30
  47. package/dist/content/content.js +19 -16
  48. package/dist/content/layout.d.ts +10 -2
  49. package/dist/content/layout.js +4 -2
  50. package/dist/content/scaledMetric.d.ts +2 -1
  51. package/dist/content/scaledMetric.js +2 -1
  52. package/dist/controls/ColorPicker.d.ts +2 -4
  53. package/dist/controls/ColorPicker.js +2 -4
  54. package/dist/controls/DatePicker.d.ts +4 -4
  55. package/dist/controls/DatePicker.js +2 -2
  56. package/dist/controls/ProgressView.d.ts +4 -4
  57. package/dist/controls/ProgressView.js +1 -2
  58. package/dist/data/database.d.ts +9 -8
  59. package/dist/data/database.js +4 -4
  60. package/dist/docs/reference.md +982 -964
  61. package/dist/docs/tailwind.md +76 -0
  62. package/dist/docs/tokens.md +1 -1
  63. package/dist/gestures/GestureView.d.ts +3 -1
  64. package/dist/gestures/GestureView.js +2 -1
  65. package/dist/gestures/gesture.d.ts +22 -2
  66. package/dist/gestures/gesture.js +7 -2
  67. package/dist/glass/GlassEffect.d.ts +2 -1
  68. package/dist/glass/GlassEffect.js +2 -1
  69. package/dist/glass/GlassPresentation.d.ts +1 -0
  70. package/dist/glass/GlassPresentation.js +21 -4
  71. package/dist/glass/TabBar.js +23 -1
  72. package/dist/glass/errorAlert.js +2 -1
  73. package/dist/glass/errors.d.ts +3 -1
  74. package/dist/glass/fallback/runtime.d.ts +1 -0
  75. package/dist/glass/fallback/runtime.js +8 -1
  76. package/dist/glass/liquidContext.d.ts +2 -0
  77. package/dist/glass/menuPresenter.d.ts +2 -0
  78. package/dist/glass/regions.d.ts +2 -1
  79. package/dist/glass/renderSpecs.d.ts +1 -0
  80. package/dist/glass/renderSpecs.js +1 -0
  81. package/dist/glass/webgpu/controlRim.d.ts +29 -0
  82. package/dist/glass/webgpu/controlRim.js +68 -0
  83. package/dist/glass/webgpu/passes.d.ts +2 -2
  84. package/dist/glass/webgpu/production.d.ts +1 -0
  85. package/dist/glass/webgpu/production.js +27 -1
  86. package/dist/glass/webgpu/rasterUniforms.js +9 -0
  87. package/dist/glass/webgpu/shaders.d.ts +2 -2
  88. package/dist/glass/webgpu/shaders.js +5 -1
  89. package/dist/haptics/SensoryButton.d.ts +4 -4
  90. package/dist/haptics/SensoryButton.js +3 -3
  91. package/dist/image/Image.d.ts +6 -3
  92. package/dist/image/Image.js +4 -3
  93. package/dist/image/asset.d.ts +2 -1
  94. package/dist/keyboard/adapter.d.ts +3 -4
  95. package/dist/keyboard/geometry.d.ts +1 -1
  96. package/dist/list-form/ListForm.d.ts +8 -7
  97. package/dist/list-form/ListForm.js +2 -2
  98. package/dist/list-form/editing.d.ts +5 -6
  99. package/dist/list-form/editing.js +4 -5
  100. package/dist/list-form/offsets.d.ts +2 -2
  101. package/dist/list-form/offsets.js +2 -2
  102. package/dist/media/react.d.ts +2 -1
  103. package/dist/media/react.js +2 -1
  104. package/dist/media/types.d.ts +6 -3
  105. package/dist/motion/TransitionView.d.ts +4 -2
  106. package/dist/motion/TransitionView.js +3 -2
  107. package/dist/motion/animationValue.d.ts +1 -1
  108. package/dist/motion/matchedGeometry.d.ts +6 -5
  109. package/dist/motion/matchedGeometry.js +2 -1
  110. package/dist/motion/transition.d.ts +4 -1
  111. package/dist/motion/transition.js +2 -0
  112. package/dist/navigation/DetailList.d.ts +1 -1
  113. package/dist/navigation/DetailList.js +1 -1
  114. package/dist/navigation/Sidebar.d.ts +3 -1
  115. package/dist/navigation/Sidebar.js +1 -1
  116. package/dist/navigation/SidebarSymbol.d.ts +2 -1
  117. package/dist/navigation/SidebarSymbol.js +2 -1
  118. package/dist/navigation/navigationContext.d.ts +2 -1
  119. package/dist/navigation/navigationContext.js +2 -1
  120. package/dist/navigation/splitContext.d.ts +2 -1
  121. package/dist/navigation/splitContext.js +2 -1
  122. package/dist/navigation/toolbarMinimization.d.ts +4 -3
  123. package/dist/navigation/types.d.ts +7 -5
  124. package/dist/presentation/Presentation.d.ts +8 -7
  125. package/dist/presentation/Presentation.js +3 -2
  126. package/dist/presentation/model.d.ts +2 -1
  127. package/dist/press/Pressable.d.ts +5 -1
  128. package/dist/press/Pressable.js +2 -0
  129. package/dist/press/stateMachine.d.ts +1 -1
  130. package/dist/public/Label.d.ts +2 -1
  131. package/dist/public/Label.js +2 -1
  132. package/dist/public/Screen.d.ts +4 -6
  133. package/dist/public/actions.d.ts +2 -1
  134. package/dist/public/actions.js +2 -1
  135. package/dist/public/buttonBorderShape.d.ts +2 -1
  136. package/dist/public/colors.d.ts +7 -4
  137. package/dist/public/colors.js +3 -2
  138. package/dist/public/controlStyle.d.ts +17 -14
  139. package/dist/public/controls.d.ts +27 -26
  140. package/dist/public/controls.js +20 -19
  141. package/dist/public/deviceActions.d.ts +6 -4
  142. package/dist/public/deviceActions.js +4 -2
  143. package/dist/public/environment.d.ts +16 -13
  144. package/dist/public/environment.js +11 -9
  145. package/dist/public/filePickers.d.ts +6 -4
  146. package/dist/public/filePickers.js +3 -2
  147. package/dist/public/glass.d.ts +6 -3
  148. package/dist/public/glass.js +2 -1
  149. package/dist/public/glassValue.d.ts +3 -4
  150. package/dist/public/glassValue.js +3 -4
  151. package/dist/public/keyboard.d.ts +4 -1
  152. package/dist/public/keyboard.js +2 -1
  153. package/dist/public/navigationTransition.d.ts +5 -5
  154. package/dist/public/navigationTransition.js +2 -2
  155. package/dist/public/presentation.d.ts +8 -7
  156. package/dist/public/presentation.js +5 -5
  157. package/dist/public/runtime.d.ts +9 -8
  158. package/dist/public/runtime.js +7 -7
  159. package/dist/public/scroll.d.ts +6 -3
  160. package/dist/public/scroll.js +3 -1
  161. package/dist/public/structure.d.ts +2 -2
  162. package/dist/public/toolbar.d.ts +15 -11
  163. package/dist/public/toolbar.js +12 -7
  164. package/dist/reachability/model.d.ts +4 -3
  165. package/dist/reachability/react.d.ts +4 -1
  166. package/dist/reachability/react.js +2 -1
  167. package/dist/root/SatinRoot.d.ts +3 -3
  168. package/dist/root/SatinRoot.js +12 -36
  169. package/dist/root/mountSatin.d.ts +1 -1
  170. package/dist/root/mountSatin.js +26 -35
  171. package/dist/root/runtimeContext.d.ts +2 -1
  172. package/dist/root/runtimeContext.js +2 -1
  173. package/dist/safe-area/Overlay.d.ts +3 -2
  174. package/dist/safe-area/Overlay.js +2 -1
  175. package/dist/safe-area/SafeAreaInset.d.ts +11 -7
  176. package/dist/safe-area/SafeAreaInset.js +7 -6
  177. package/dist/safe-area/context.d.ts +3 -3
  178. package/dist/safe-area/context.js +1 -1
  179. package/dist/safe-area/displayCorners.d.ts +4 -2
  180. package/dist/safe-area/displayCorners.js +4 -2
  181. package/dist/safe-area/modifiers.d.ts +14 -10
  182. package/dist/safe-area/modifiers.js +8 -4
  183. package/dist/scroll/ScrollSurface.js +5 -1
  184. package/dist/scroll/ScrollTarget.d.ts +1 -1
  185. package/dist/scroll/ScrollTarget.js +1 -1
  186. package/dist/scroll/edgePolicy.d.ts +2 -2
  187. package/dist/scroll/position.d.ts +5 -3
  188. package/dist/scroll/types.d.ts +1 -1
  189. package/dist/search/PadSearchDrawer.d.ts +7 -0
  190. package/dist/search/PadSearchDrawer.js +8 -0
  191. package/dist/search/PadSearchPresentationContext.d.ts +6 -0
  192. package/dist/search/PadSearchPresentationContext.js +4 -0
  193. package/dist/search/SearchDrawer.d.ts +1 -1
  194. package/dist/search/SearchDrawer.js +6 -1
  195. package/dist/search/SearchSuggestionsPopover.d.ts +6 -0
  196. package/dist/search/SearchSuggestionsPopover.js +42 -0
  197. package/dist/search/SearchToolbarField.d.ts +2 -1
  198. package/dist/search/SearchToolbarField.js +28 -7
  199. package/dist/search/padSearchBarMotion.d.ts +69 -0
  200. package/dist/search/padSearchBarMotion.js +73 -0
  201. package/dist/search/padSearchFieldSamples.json +491 -0
  202. package/dist/search/searchPlacement.d.ts +3 -0
  203. package/dist/search/searchPlacement.js +7 -0
  204. package/dist/search/searchable.d.ts +14 -12
  205. package/dist/search/usePadSearchFieldMotion.d.ts +4 -0
  206. package/dist/search/usePadSearchFieldMotion.js +100 -0
  207. package/dist/search/useSearchPresentation.d.ts +2 -1
  208. package/dist/search/useSearchPresentation.js +23 -5
  209. package/dist/server.d.ts +4 -4
  210. package/dist/server.js +4 -4
  211. package/dist/shapes/corners.d.ts +3 -3
  212. package/dist/shapes/corners.js +1 -2
  213. package/dist/styles.css +8289 -8244
  214. package/dist/sw/vite.d.ts +4 -0
  215. package/dist/sw/vite.js +2 -0
  216. package/dist/symbols/Symbol.d.ts +7 -5
  217. package/dist/symbols/Symbol.js +5 -3
  218. package/dist/symbols/catalogue.d.ts +1 -1
  219. package/dist/symbols/types.d.ts +6 -4
  220. package/dist/tabs/TabSection.d.ts +3 -2
  221. package/dist/tabs/TabSection.js +2 -1
  222. package/dist/tabs/TabView.js +54 -51
  223. package/dist/tasks/useTask.d.ts +5 -4
  224. package/dist/tasks/useTask.js +4 -3
  225. package/dist/testing.d.ts +3 -2
  226. package/dist/testing.js +3 -2
  227. package/dist/text-input/focusChain.d.ts +4 -3
  228. package/dist/text-input/focusChain.js +3 -2
  229. package/dist/text-input/kinds.d.ts +1 -1
  230. package/dist/web/WebView.d.ts +10 -3
  231. package/dist/web/WebView.js +3 -2
  232. package/dist/web/authentication.d.ts +12 -1
  233. package/dist/web/authentication.js +2 -1
  234. package/dist/web/openURL.d.ts +10 -4
  235. package/dist/web/openURL.js +4 -2
  236. package/dist/web/useWebAuthentication.d.ts +2 -1
  237. package/dist/web/useWebAuthentication.js +2 -1
  238. package/dist/zoom/Zoomable.d.ts +3 -3
  239. package/dist/zoom/Zoomable.js +2 -2
  240. package/package.json +1 -1
@@ -1,5 +1,8 @@
1
1
  import { Fragment as _Fragment, jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
+ import { usePadSearchFieldMotion } from './usePadSearchFieldMotion.js';
3
+ import { PadSearchPresentationContext, PadSearchTabContext, } from './PadSearchPresentationContext.js';
2
4
  import { useContext, useLayoutEffect, useRef, useSyncExternalStore } from 'react';
5
+ import { readDeviceIdiom } from '../layout/deviceIdiom.js';
3
6
  import { createPortal } from 'react-dom';
4
7
  import { GlassBackground } from '../glass/GlassEffect.js';
5
8
  import { MaterialEffectContext } from '../glass/liquidContext.js';
@@ -9,6 +12,7 @@ import { contactTarget, MENU_CONTACT_CLICK_WINDOW_MS, ownPhysicalContact, } from
9
12
  import { focusFromFramework } from '../focus/programmaticFocus.js';
10
13
  import { SymbolImage } from '../symbols/Symbol.js';
11
14
  import { TextField } from '../text-input/TextField.js';
15
+ import { SearchSuggestionsPopover } from './SearchSuggestionsPopover.js';
12
16
  import { SearchScopesBar } from './SearchScopesBar.js';
13
17
  import { navigationChromeOf, ownBarParts, stackedOver, subscribeNever } from './searchChrome.js';
14
18
  import { useSearchPresentation } from './useSearchPresentation.js';
@@ -24,20 +28,31 @@ import { useSearchPresentation } from './useSearchPresentation.js';
24
28
  * placed among the bottom items. Suggestions stand in for the scroll view's content, as in the
25
29
  * drawer. Presentation is not animated yet: native's motion is not measured (spec notes, reference).
26
30
  */
27
- export function SearchToolbarField({ configuration, scroller, host, navigation = false, }) {
31
+ export function SearchToolbarField({ configuration, scroller, host, navigation = false, drawer = false, }) {
32
+ const tabSearch = useContext(PadSearchPresentationContext);
33
+ const searchTab = useContext(PadSearchTabContext);
34
+ const setSearchOwner = tabSearch?.setOwner;
28
35
  const liquid = useContext(MaterialEffectContext);
29
36
  const navigator = useContext(NavigatorContext);
30
37
  const screenKey = useContext(ScreenContext)?.key;
31
38
  const stacked = useSyncExternalStore(navigator?.subscribe ?? subscribeNever, () => stackedOver(navigator, screenKey, scroller.current));
32
39
  const inputRef = useRef(null);
33
40
  const rowRef = useRef(null);
34
- const search = useSearchPresentation(configuration, inputRef);
41
+ const pad = navigation && readDeviceIdiom() === 'pad';
42
+ const search = useSearchPresentation(configuration, inputRef, pad);
35
43
  const { presented } = search;
44
+ usePadSearchFieldMotion(rowRef, pad && !drawer, presented, searchTab !== null, liquid?.regions);
45
+ useLayoutEffect(() => {
46
+ if (!pad || !searchTab || !setSearchOwner || !presented || stacked)
47
+ return;
48
+ setSearchOwner(searchTab);
49
+ return () => setSearchOwner(null);
50
+ }, [pad, searchTab, setSearchOwner, presented, stacked]);
36
51
  // The bar's title and items give way while search is presented; its back control too, unless a
37
52
  // screen is stacked over this one (as the drawer, SearchDrawer.tsx).
38
53
  useLayoutEffect(() => {
39
54
  const element = scroller.current;
40
- if (!element || navigation)
55
+ if (!element || (navigation && !drawer))
41
56
  return;
42
57
  element.toggleAttribute('data-satin-search-presented', presented);
43
58
  const { header } = navigationChromeOf(element);
@@ -57,7 +72,7 @@ export function SearchToolbarField({ configuration, scroller, host, navigation =
57
72
  part.removeAttribute('data-satin-search-presented');
58
73
  header?.removeAttribute('data-satin-search-presented');
59
74
  };
60
- }, [presented, scroller, screenKey, stacked, navigation]);
75
+ }, [presented, scroller, screenKey, stacked, navigation, drawer]);
61
76
  // The field moves with the keyboard on the keyboard's own curve (styles.css). Glass regions
62
77
  // follow a moving element only when told: refresh them while it moves.
63
78
  useLayoutEffect(() => {
@@ -93,16 +108,20 @@ export function SearchToolbarField({ configuration, scroller, host, navigation =
93
108
  }, [liquid?.regions, presented]);
94
109
  const prompt = configuration.prompt ?? 'Search';
95
110
  const ownsItem = !host.hasAttribute('data-satin-search-toolbar-host');
96
- const row = (_jsxs("div", { ref: rowRef, role: "search", "data-satin-search-toolbar": "", "data-satin-search-navigation": navigation || undefined, "data-satin-search-toolbar-presented": presented || undefined, children: [_jsxs("div", { "data-satin-search-toolbar-field": "", children: [_jsx(GlassBackground, { shape: "capsule" }), _jsx(SymbolImage, { name: "magnifyingglass", weight: "medium", "data-satin-search-toolbar-magnifier": "" }), _jsx(TextField, { ref: inputRef, label: prompt, labelVisibility: "hidden", variant: "plain", placeholder: prompt, kind: "search", submitLabel: "search", value: configuration.text, onChange: search.change, onFocus: search.present, onSubmit: search.submit, onKeyDown: event => {
111
+ const row = (_jsxs("div", { ref: rowRef, role: "search", "data-satin-search-toolbar": "", "data-satin-search-navigation": navigation || undefined, "data-satin-search-pad": pad || undefined, "data-satin-search-toolbar-presented": presented || undefined, children: [_jsxs("div", { "data-satin-search-toolbar-field": "", children: [_jsx(GlassBackground, { shape: "capsule" }), _jsx(SymbolImage, { name: "magnifyingglass", weight: "medium", "data-satin-search-toolbar-magnifier": "" }), _jsx(TextField, { ref: inputRef, label: prompt, labelVisibility: "hidden", variant: "plain", placeholder: prompt, kind: "search", submitLabel: "search", value: configuration.text, onChange: search.change, onFocus: search.present, onBlur: pad ? search.resign : undefined, onSubmit: search.submit, onKeyDown: event => {
97
112
  if (event.key !== 'Escape' || event.nativeEvent.isComposing)
98
113
  return;
99
114
  event.preventDefault();
100
115
  search.dismiss();
101
116
  } }), configuration.text && (_jsx(Pressable, { iconOnly: true, "aria-label": "Clear text", "data-satin-search-toolbar-clear": "", onPress: () => {
117
+ if (pad && searchTab) {
118
+ search.dismiss();
119
+ return;
120
+ }
102
121
  search.change('');
103
122
  if (inputRef.current)
104
123
  focusFromFramework(inputRef.current);
105
- }, children: _jsx(SymbolImage, { name: "xmark.circle.fill" }) }))] }), presented && (_jsxs(Pressable, { iconOnly: true, "aria-label": "Close", "data-satin-search-toolbar-close": "", "data-satin-glass-press": "true", onPress: () => {
124
+ }, children: _jsx(SymbolImage, { name: "xmark.circle.fill" }) }))] }), presented && !pad && (_jsxs(Pressable, { iconOnly: true, "aria-label": "Close", "data-satin-search-toolbar-close": "", "data-satin-glass-press": "true", onPress: () => {
106
125
  // The touch ends here: WebKit's synthesized mouse events must not refocus the field
107
126
  // that moves under the finger (as the drawer's close button).
108
127
  ownPhysicalContact(contactTarget(), closeContactOwner, MENU_CONTACT_CLICK_WINDOW_MS, {
@@ -110,6 +129,8 @@ export function SearchToolbarField({ configuration, scroller, host, navigation =
110
129
  });
111
130
  search.dismiss();
112
131
  }, children: [_jsx(GlassBackground, { shape: "circle", interactive: true }), _jsx(SymbolImage, { name: "xmark", weight: "medium" })] }))] }));
113
- return (_jsxs(_Fragment, { children: [createPortal(ownsItem ? _jsx("div", { "data-satin-toolbar-item": "search", children: row }) : row, host), navigation && configuration.scopes && presented && (_jsx("div", { "data-satin-search-navigation-scopes": "", "data-satin-search-presented": "", children: _jsx(SearchScopesBar, { scopes: configuration.scopes, presented: presented }) })), search.suggestions.length > 0 && (_jsx("div", { "data-satin-search-suggestions": "", role: "list", "aria-label": "Suggestions", children: search.suggestions.map(suggestion => (_jsx(Pressable, { role: "listitem", feedback: "row", "data-satin-search-suggestion": "", onPress: () => search.complete(suggestion), children: suggestion.label ?? suggestion.text }, suggestion.id))) }))] }));
132
+ const suggestions = search.suggestions.map(suggestion => (_jsx(Pressable, { role: "listitem", feedback: "row", "data-satin-search-suggestion": "", onPress: () => search.complete(suggestion), children: suggestion.label ?? suggestion.text }, suggestion.id)));
133
+ return (_jsxs(_Fragment, { children: [createPortal(ownsItem ? (_jsx("div", { "data-satin-toolbar-item": "search", "data-satin-search-pad-item": pad || undefined, "data-satin-search-expanded": (pad && presented) || undefined, children: row })) : (row), host), navigation && (!pad || drawer) && configuration.scopes && presented && (_jsx("div", { "data-satin-search-navigation-scopes": "", "data-satin-search-presented": "", children: _jsx(SearchScopesBar, { scopes: configuration.scopes, presented: presented }) })), search.suggestions.length > 0 &&
134
+ (pad ? (_jsx(SearchSuggestionsPopover, { anchor: rowRef, children: suggestions })) : (_jsx("div", { "data-satin-search-suggestions": "", role: "list", "aria-label": "Suggestions", children: suggestions })))] }));
114
135
  }
115
136
  const closeContactOwner = {};
@@ -0,0 +1,69 @@
1
+ import type { SurfaceRenderSpec } from '../glass/renderSpecs.js';
2
+ /** iPad, iPadOS 27.0 (24A437), reference. Activation fit from original video
3
+ * F742–751: omega 17.8734, critical damping, RMS 0.104 pt. Dismissal
4
+ * presentation-layer fit: omega 17.9118, zeta .9982, RMS .038 pt.
5
+ * Translation and effective opacity are one group track; scale remains 1. */
6
+ export declare const PAD_SEARCH_BAR_OMEGA = 17.9;
7
+ export declare const PAD_SEARCH_BAR_TRAVEL = 64;
8
+ export declare class PadSearchBarMotion {
9
+ private run?;
10
+ private animation?;
11
+ get active(): boolean;
12
+ sample(at: number): {
13
+ value: number;
14
+ velocity: number;
15
+ };
16
+ retarget(target: number, at: number): void;
17
+ start(element: HTMLElement, target: number, finalSpec: SurfaceRenderSpec | undefined, at?: number): {
18
+ at: number;
19
+ duration: number;
20
+ specs: {
21
+ touchLight?: import("../internal.js").GlassTouchLight;
22
+ excludeRegionIds?: readonly string[];
23
+ restHidden?: boolean;
24
+ occluder?: import("../internal.js").CapsuleShape;
25
+ prewarmTransparent?: boolean;
26
+ recipeMix?: number;
27
+ sheetOpaqueMix?: number;
28
+ popoverArrow?: import("../glass/regions.js").PopoverArrow;
29
+ variant?: import("../glass/lens/referenceProfiles.js").ReferenceVariant;
30
+ treatment?: 'sheet' | 'expandedSheet' | 'alert' | 'confirmation' | 'contextBackdrop' | 'contextPreview' | 'contextMenu';
31
+ tint?: import("../index.js").GlassTint;
32
+ memberHighlight?: Readonly<{
33
+ member: number;
34
+ amount: number;
35
+ light?: import("../internal.js").GlassTouchLight;
36
+ }>;
37
+ backdropExclusions?: readonly string[];
38
+ backdropMenuOverlay?: boolean;
39
+ blurSigmaCssPx?: number;
40
+ frameHeight: number;
41
+ frameWidth: number;
42
+ frameX: number;
43
+ id: import("../internal.js").SurfaceId;
44
+ materialMix: number;
45
+ materialProfile: 'chrome' | 'searchField' | 'menu';
46
+ menuTintMix?: number;
47
+ returningTrigger?: import("../internal.js").ReturningMenuTrigger;
48
+ radius: number;
49
+ sampleHeight: number;
50
+ sampleInsetX: number;
51
+ sampleInsetY: number;
52
+ sampleWidth: number;
53
+ shaderAperture: boolean;
54
+ shape: import("../internal.js").SurfaceShape;
55
+ tabSelection?: import("../internal.js").TabSelectionShape;
56
+ ink?: Readonly<{
57
+ atlas: Readonly<{
58
+ width: number;
59
+ height: number;
60
+ }>;
61
+ layers: readonly import("../glass/lens/menuField.js").MenuInkLayer[];
62
+ }>;
63
+ frameY: number;
64
+ opacity: number;
65
+ }[];
66
+ finished: Promise<void | Animation>;
67
+ };
68
+ dispose(): void;
69
+ }
@@ -0,0 +1,73 @@
1
+ import { animateElement, timelineStart } from '../motion/animate.js';
2
+ /** iPad, iPadOS 27.0 (24A437), reference. Activation fit from original video
3
+ * F742–751: omega 17.8734, critical damping, RMS 0.104 pt. Dismissal
4
+ * presentation-layer fit: omega 17.9118, zeta .9982, RMS .038 pt.
5
+ * Translation and effective opacity are one group track; scale remains 1. */
6
+ export const PAD_SEARCH_BAR_OMEGA = 17.9;
7
+ export const PAD_SEARCH_BAR_TRAVEL = 64;
8
+ export class PadSearchBarMotion {
9
+ run;
10
+ animation;
11
+ get active() {
12
+ return this.animation?.playState === 'running';
13
+ }
14
+ sample(at) {
15
+ const run = this.run;
16
+ if (!run)
17
+ return { value: 0, velocity: 0 };
18
+ const t = Math.max(0, at - run.at) / 1000;
19
+ const displacement = run.from - run.target;
20
+ const slope = run.velocity + PAD_SEARCH_BAR_OMEGA * displacement;
21
+ const decay = Math.exp(-PAD_SEARCH_BAR_OMEGA * t);
22
+ return {
23
+ value: run.target + (displacement + slope * t) * decay,
24
+ velocity: (slope - PAD_SEARCH_BAR_OMEGA * (displacement + slope * t)) * decay,
25
+ };
26
+ }
27
+ retarget(target, at) {
28
+ const current = this.sample(at);
29
+ this.run = { at, from: current.value, target, velocity: current.velocity };
30
+ }
31
+ start(element, target, finalSpec, at = performance.now()) {
32
+ this.retarget(target, at);
33
+ this.animation?.cancel();
34
+ this.animation = undefined;
35
+ const reduced = matchMedia('(prefers-reduced-motion: reduce)').matches;
36
+ let duration = 0;
37
+ if (!reduced) {
38
+ do {
39
+ duration += 1000 / 60;
40
+ } while (duration < 2000 &&
41
+ (Math.abs(this.sample(at + duration).value - target) > 0.0015 ||
42
+ Math.abs(this.sample(at + duration).velocity) > 0.02));
43
+ }
44
+ const count = Math.max(1, Math.round(duration / (1000 / 60)));
45
+ const values = Array.from({ length: count + 1 }, (_, index) => reduced || index === count ? target : this.sample(at + (duration * index) / count).value);
46
+ const specs = finalSpec
47
+ ? values.map(value => ({
48
+ ...finalSpec,
49
+ frameY: finalSpec.frameY - PAD_SEARCH_BAR_TRAVEL * (value - target),
50
+ opacity: Math.max(0, Math.min(1, 1 - value)),
51
+ }))
52
+ : [];
53
+ const frames = values.map(value => ({
54
+ transform: `translateY(${-PAD_SEARCH_BAR_TRAVEL * (value - target)}px)`,
55
+ opacity: Math.max(0, Math.min(1, 1 - value)),
56
+ }));
57
+ if (duration) {
58
+ this.animation = animateElement(element, frames, { duration, easing: 'linear' });
59
+ this.animation.startTime = timelineStart(at);
60
+ }
61
+ else
62
+ this.run = { at, from: target, target, velocity: 0 };
63
+ return {
64
+ at,
65
+ duration,
66
+ specs,
67
+ finished: this.animation?.finished.catch(() => { }) ?? Promise.resolve(),
68
+ };
69
+ }
70
+ dispose() {
71
+ this.animation?.cancel();
72
+ }
73
+ }