@multiplatform.one/forms 7.84.2 → 7.84.3

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 (247) hide show
  1. package/dist/cjs/AdaptivePopup/index.native.js +2 -2
  2. package/dist/cjs/AdaptivePopup/index.native.js.map +1 -1
  3. package/dist/cjs/Button/IconButtonGroup.native.js.map +1 -1
  4. package/dist/cjs/Button/circleGlyph.native.js.map +1 -1
  5. package/dist/cjs/Button/iconButtonGroupContext.native.js.map +1 -1
  6. package/dist/cjs/Button/index.native.js +2 -2
  7. package/dist/cjs/Button/index.native.js.map +1 -1
  8. package/dist/cjs/Button/webGlass.native.js.map +1 -1
  9. package/dist/cjs/Chip/index.native.js.map +1 -1
  10. package/dist/cjs/ContextualSaveBar/UnsavedChangesDialog.native.js +1 -1
  11. package/dist/cjs/ContextualSaveBar/UnsavedChangesDialog.native.js.map +1 -1
  12. package/dist/cjs/ContextualSaveBar/clientKnownIdentity.native.js.map +1 -1
  13. package/dist/cjs/ContextualSaveBar/commitImmediateField.native.js.map +1 -1
  14. package/dist/cjs/ContextualSaveBar/index.native.js +3 -3
  15. package/dist/cjs/ContextualSaveBar/index.native.js.map +1 -1
  16. package/dist/cjs/ContextualSaveBar/useUnsavedChangesGuard.native.js.map +1 -1
  17. package/dist/cjs/ControlGroup/index.native.js +1 -1
  18. package/dist/cjs/ControlGroup/index.native.js.map +1 -1
  19. package/dist/cjs/DescriptionList/index.native.js +2 -2
  20. package/dist/cjs/DescriptionList/index.native.js.map +1 -1
  21. package/dist/cjs/ErrorSummary.native.js.map +1 -1
  22. package/dist/cjs/FieldDisplay/editMode.native.js.map +1 -1
  23. package/dist/cjs/FieldDisplay/formatters.native.js.map +1 -1
  24. package/dist/cjs/FieldDisplay/index.native.js +1 -1
  25. package/dist/cjs/FieldDisplay/index.native.js.map +1 -1
  26. package/dist/cjs/FieldGroup.native.js.map +1 -1
  27. package/dist/cjs/FloatingPanel/PanelHeader.native.js.map +1 -1
  28. package/dist/cjs/FloatingPanel/RegularPanel.native.js.map +1 -1
  29. package/dist/cjs/FloatingPanel/compactFace.native.js.map +1 -1
  30. package/dist/cjs/FloatingPanel/containingBlock.native.js.map +1 -1
  31. package/dist/cjs/FloatingPanel/coverRect.native.js.map +1 -1
  32. package/dist/cjs/FloatingPanel/echoContext.native.js.map +1 -1
  33. package/dist/cjs/FloatingPanel/index.cjs +2 -1
  34. package/dist/cjs/FloatingPanel/nestedAction.native.js.map +1 -1
  35. package/dist/cjs/FloatingPanel/paintedBox.native.js.map +1 -1
  36. package/dist/cjs/FloatingPanel/panelWidth.native.js.map +1 -1
  37. package/dist/cjs/FloatingPanel/pointAnchor.native.js.map +1 -1
  38. package/dist/cjs/FloatingPanel/regularPlacement.native.js.map +1 -1
  39. package/dist/cjs/FloatingPanel/trailingAction.native.js +1 -1
  40. package/dist/cjs/FloatingPanel/trailingAction.native.js.map +1 -1
  41. package/dist/cjs/FloatingPanel/useFloatingPanel.native.js.map +1 -1
  42. package/dist/cjs/Form/index.native.js +1 -1
  43. package/dist/cjs/Form/index.native.js.map +1 -1
  44. package/dist/cjs/Form/submissionController.native.js.map +1 -1
  45. package/dist/cjs/Form/validateOn.native.js.map +1 -1
  46. package/dist/cjs/FormGrid.native.js.map +1 -1
  47. package/dist/cjs/FormSection.native.js.map +1 -1
  48. package/dist/cjs/InputParts/PasswordReveal.native.js.map +1 -1
  49. package/dist/cjs/InputParts/index.native.js.map +1 -1
  50. package/dist/cjs/InputParts/keyboardAppearance.native.js.map +1 -1
  51. package/dist/cjs/Label/index.native.js.map +1 -1
  52. package/dist/cjs/MediaPicker/base64.native.js.map +1 -1
  53. package/dist/cjs/MediaPicker/payload.native.js.map +1 -1
  54. package/dist/cjs/MediaPicker/types.native.js.map +1 -1
  55. package/dist/cjs/MediaPicker/useMediaPicker.native.js.map +1 -1
  56. package/dist/cjs/Skeleton/index.native.js.map +1 -1
  57. package/dist/cjs/Spinner/SpinnerGlyph.native.js.map +1 -1
  58. package/dist/cjs/Spinner/spinnerSize.native.js.map +1 -1
  59. package/dist/cjs/Table/index.native.js.map +1 -1
  60. package/dist/cjs/Wheel/haptic.native.js.map +1 -1
  61. package/dist/cjs/Wheel/index.native.js.map +1 -1
  62. package/dist/cjs/Wheel/wheelShared.native.js.map +1 -1
  63. package/dist/cjs/actionLabel.native.js.map +1 -1
  64. package/dist/cjs/fieldDefaults.native.js.map +1 -1
  65. package/dist/cjs/fieldLayout.native.js +1 -1
  66. package/dist/cjs/fieldLayout.native.js.map +1 -1
  67. package/dist/cjs/fields/Barcode/BarcodePreview.native.js.map +1 -1
  68. package/dist/cjs/fields/Barcode/BarcodeScanner.native.js +1 -1
  69. package/dist/cjs/fields/Barcode/code128.native.js.map +1 -1
  70. package/dist/cjs/fields/Barcode/index.native.js +2 -2
  71. package/dist/cjs/fields/Barcode/index.native.js.map +1 -1
  72. package/dist/cjs/fields/Barcode/qr.native.js.map +1 -1
  73. package/dist/cjs/fields/Barcode/scannerTypes.native.js.map +1 -1
  74. package/dist/cjs/fields/Checkbox/Checkbox.native.js +1 -1
  75. package/dist/cjs/fields/Checkbox/Checkbox.native.js.map +1 -1
  76. package/dist/cjs/fields/Checkbox/CheckboxBox.native.js.map +1 -1
  77. package/dist/cjs/fields/Checkbox/CheckboxCard.native.js.map +1 -1
  78. package/dist/cjs/fields/Checkbox/CheckboxFieldFrame.native.js.map +1 -1
  79. package/dist/cjs/fields/Checkbox/CheckboxGroup.native.js +1 -1
  80. package/dist/cjs/fields/Checkbox/CheckboxGroup.native.js.map +1 -1
  81. package/dist/cjs/fields/Checkbox/checkboxGroupContext.native.js.map +1 -1
  82. package/dist/cjs/fields/Checkbox/index.native.js.map +1 -1
  83. package/dist/cjs/fields/ColorPicker/SystemColorField.native.js.map +1 -1
  84. package/dist/cjs/fields/ColorPicker/index.native.js +2 -2
  85. package/dist/cjs/fields/ColorPicker/index.native.js.map +1 -1
  86. package/dist/cjs/fields/ColorPicker/parts.native.js +2 -2
  87. package/dist/cjs/fields/ColorPicker/parts.native.js.map +1 -1
  88. package/dist/cjs/fields/ColorPicker/systemColorWell.gnome.native.js.map +1 -1
  89. package/dist/cjs/fields/Combobox/authorOptions.native.js.map +1 -1
  90. package/dist/cjs/fields/Combobox/index.native.js +5 -5
  91. package/dist/cjs/fields/Combobox/index.native.js.map +1 -1
  92. package/dist/cjs/fields/DatePicker/Calendar.native.js.map +1 -1
  93. package/dist/cjs/fields/DatePicker/DateRangePicker.native.js +2 -2
  94. package/dist/cjs/fields/DatePicker/DateRangePicker.native.js.map +1 -1
  95. package/dist/cjs/fields/DatePicker/DatetimePicker.catalog.native.js +3 -3
  96. package/dist/cjs/fields/DatePicker/DatetimePicker.catalog.native.js.map +1 -1
  97. package/dist/cjs/fields/DatePicker/DatetimePicker.native.js +2 -2
  98. package/dist/cjs/fields/DatePicker/MonthPicker.native.js +2 -2
  99. package/dist/cjs/fields/DatePicker/MonthPicker.native.js.map +1 -1
  100. package/dist/cjs/fields/DatePicker/MultiDatePicker.native.js +2 -2
  101. package/dist/cjs/fields/DatePicker/MultiDatePicker.native.js.map +1 -1
  102. package/dist/cjs/fields/DatePicker/catalog.native.js +2 -2
  103. package/dist/cjs/fields/DatePicker/catalog.native.js.map +1 -1
  104. package/dist/cjs/fields/DatePicker/fieldValueSync.native.js.map +1 -1
  105. package/dist/cjs/fields/DatePicker/index.native.js +2 -2
  106. package/dist/cjs/fields/DatePicker/parts.native.js +2 -2
  107. package/dist/cjs/fields/DatePicker/parts.native.js.map +1 -1
  108. package/dist/cjs/fields/DatePicker/utils.native.js.map +1 -1
  109. package/dist/cjs/fields/Duration/DurationWheel.native.js +1 -1
  110. package/dist/cjs/fields/Duration/durationMath.native.js.map +1 -1
  111. package/dist/cjs/fields/Duration/durationWheelTypes.native.js.map +1 -1
  112. package/dist/cjs/fields/Duration/index.native.js +3 -3
  113. package/dist/cjs/fields/Duration/index.native.js.map +1 -1
  114. package/dist/cjs/fields/FileUpload/filePickerTypes.native.js.map +1 -1
  115. package/dist/cjs/fields/FileUpload/index.native.js +2 -2
  116. package/dist/cjs/fields/FileUpload/index.native.js.map +1 -1
  117. package/dist/cjs/fields/FileUpload/nativePickerLoader.native.js.map +1 -1
  118. package/dist/cjs/fields/Geolocation/expoMapsLoader.native.js.map +1 -1
  119. package/dist/cjs/fields/Geolocation/geoValue.native.js.map +1 -1
  120. package/dist/cjs/fields/Geolocation/geocoder.native.js.map +1 -1
  121. package/dist/cjs/fields/Geolocation/geocoderContext.native.js.map +1 -1
  122. package/dist/cjs/fields/Geolocation/index.native.js +5 -5
  123. package/dist/cjs/fields/Geolocation/index.native.js.map +1 -1
  124. package/dist/cjs/fields/Geolocation/mapMath.native.js.map +1 -1
  125. package/dist/cjs/fields/Geolocation/mapTypes.native.js.map +1 -1
  126. package/dist/cjs/fields/Geolocation/nativeSearchFocus.native.js.map +1 -1
  127. package/dist/cjs/fields/Geolocation/photonGeocoder.native.js.map +1 -1
  128. package/dist/cjs/fields/Icon/drawnSet.native.js.map +1 -1
  129. package/dist/cjs/fields/Icon/index.native.js +3 -3
  130. package/dist/cjs/fields/Icon/index.native.js.map +1 -1
  131. package/dist/cjs/fields/ImageField/index.native.js +2 -2
  132. package/dist/cjs/fields/ImageField/index.native.js.map +1 -1
  133. package/dist/cjs/fields/Input/index.native.js +3 -3
  134. package/dist/cjs/fields/Input/index.native.js.map +1 -1
  135. package/dist/cjs/fields/MentionInput/index.native.js +3 -3
  136. package/dist/cjs/fields/MentionInput/index.native.js.map +1 -1
  137. package/dist/cjs/fields/OTPInput/index.native.js +3 -3
  138. package/dist/cjs/fields/OTPInput/index.native.js.map +1 -1
  139. package/dist/cjs/fields/OTPInput/otpCellCss.native.js.map +1 -1
  140. package/dist/cjs/fields/PhoneInput/dialCodes.native.js.map +1 -1
  141. package/dist/cjs/fields/PhoneInput/index.native.js +3 -3
  142. package/dist/cjs/fields/PhoneInput/index.native.js.map +1 -1
  143. package/dist/cjs/fields/PhoneInput/phone.native.js.map +1 -1
  144. package/dist/cjs/fields/PhoneInput/regionNames.native.js.map +1 -1
  145. package/dist/cjs/fields/Progress/index.native.js +1 -1
  146. package/dist/cjs/fields/Progress/index.native.js.map +1 -1
  147. package/dist/cjs/fields/RadioGroup/index.native.js +1 -1
  148. package/dist/cjs/fields/RadioGroup/index.native.js.map +1 -1
  149. package/dist/cjs/fields/Rating/index.native.js +1 -1
  150. package/dist/cjs/fields/Rating/index.native.js.map +1 -1
  151. package/dist/cjs/fields/Rating/ratingMath.native.js.map +1 -1
  152. package/dist/cjs/fields/Rating/types.native.js.map +1 -1
  153. package/dist/cjs/fields/SearchInput/index.native.js +2 -2
  154. package/dist/cjs/fields/SearchInput/index.native.js.map +1 -1
  155. package/dist/cjs/fields/Select/InlineChoices.native.js.map +1 -1
  156. package/dist/cjs/fields/Select/SheetPickerRow.native.js.map +1 -1
  157. package/dist/cjs/fields/Select/index.native.js +4 -4
  158. package/dist/cjs/fields/Select/index.native.js.map +1 -1
  159. package/dist/cjs/fields/Select/shouldInlineChoices.native.js.map +1 -1
  160. package/dist/cjs/fields/Signature/index.native.js +2 -2
  161. package/dist/cjs/fields/Signature/index.native.js.map +1 -1
  162. package/dist/cjs/fields/Slider/index.native.js +1 -1
  163. package/dist/cjs/fields/Slider/index.native.js.map +1 -1
  164. package/dist/cjs/fields/Slider/jumpMotion.native.js.map +1 -1
  165. package/dist/cjs/fields/Stepper/index.native.js +2 -2
  166. package/dist/cjs/fields/Stepper/index.native.js.map +1 -1
  167. package/dist/cjs/fields/Stepper/resolveStepperPlacement.native.js.map +1 -1
  168. package/dist/cjs/fields/Switch/footprint.native.js.map +1 -1
  169. package/dist/cjs/fields/Switch/index.native.js +2 -2
  170. package/dist/cjs/fields/Switch/index.native.js.map +1 -1
  171. package/dist/cjs/fields/TextArea/index.native.js +2 -2
  172. package/dist/cjs/fields/TextArea/index.native.js.map +1 -1
  173. package/dist/cjs/fields/TimePicker/catalog.native.js +3 -3
  174. package/dist/cjs/fields/TimePicker/catalog.native.js.map +1 -1
  175. package/dist/cjs/fields/TimePicker/index.native.js +2 -2
  176. package/dist/cjs/fields/TimePicker/parts.native.js +1 -1
  177. package/dist/cjs/fields/TimePicker/parts.native.js.map +1 -1
  178. package/dist/cjs/fields/TimeRangeScrubber/geometry.native.js.map +1 -1
  179. package/dist/cjs/fields/TimeRangeScrubber/index.native.js +2 -2
  180. package/dist/cjs/fields/TimeRangeScrubber/index.native.js.map +1 -1
  181. package/dist/cjs/fields/ToggleGroup/index.native.js +1 -1
  182. package/dist/cjs/fields/ToggleGroup/index.native.js.map +1 -1
  183. package/dist/cjs/fields/nativeDateTime/OsDateTimeSheet.native.js +1 -1
  184. package/dist/cjs/fields/nativeDateTime/OsDateTimeSheet.native.js.map +1 -1
  185. package/dist/cjs/fields/nativeDateTime/dateTimePickerLoader.native.js.map +1 -1
  186. package/dist/cjs/fields/nativeDateTime/osDateTimeIosDisplay.native.js.map +1 -1
  187. package/dist/cjs/fields/nativeDateTime/sheetKeyboard.native.js.map +1 -1
  188. package/dist/cjs/fields/nativeSelect.native.js.map +1 -1
  189. package/dist/cjs/fields/selectedOrder.native.js.map +1 -1
  190. package/dist/cjs/formSpacing.native.js.map +1 -1
  191. package/dist/cjs/hooks/useFocusManagement.native.js.map +1 -1
  192. package/dist/cjs/index.native.js +45 -45
  193. package/dist/cjs/index.native.js.map +1 -1
  194. package/dist/cjs/keyboard/KeyboardDoneBar.native.js +1 -1
  195. package/dist/cjs/keyboard/chain.native.js.map +1 -1
  196. package/dist/cjs/keyboard/index.native.js.map +1 -1
  197. package/dist/cjs/keyboard/types.native.js.map +1 -1
  198. package/dist/cjs/requiredMarking.native.js.map +1 -1
  199. package/dist/cjs/shared/CheckGlyph.native.js.map +1 -1
  200. package/dist/cjs/shared/TimeColumn.native.js +1 -1
  201. package/dist/cjs/shared/TimeColumn.native.js.map +1 -1
  202. package/dist/cjs/shared/capabilityPreflight.native.js.map +1 -1
  203. package/dist/cjs/shared/checkedOnField.native.js.map +1 -1
  204. package/dist/cjs/shared/choiceRowPress.native.js.map +1 -1
  205. package/dist/cjs/shared/colorRamps.native.js.map +1 -1
  206. package/dist/cjs/shared/devWarn.native.js.map +1 -1
  207. package/dist/cjs/shared/fieldRowContext.native.js.map +1 -1
  208. package/dist/cjs/shared/floatingList.native.js +1 -1
  209. package/dist/cjs/shared/floatingList.native.js.map +1 -1
  210. package/dist/cjs/shared/focusManagement.native.js.map +1 -1
  211. package/dist/cjs/shared/groupContext.native.js.map +1 -1
  212. package/dist/cjs/shared/i18n.native.js.map +1 -1
  213. package/dist/cjs/shared/instantMotion.native.js.map +1 -1
  214. package/dist/cjs/shared/nativeA11y.native.js.map +1 -1
  215. package/dist/cjs/shared/nativeAutoFocus.native.js.map +1 -1
  216. package/dist/cjs/shared/overlaySizeClass.native.js.map +1 -1
  217. package/dist/cjs/shared/overlayStack.native.js.map +1 -1
  218. package/dist/cjs/shared/panelPortal.native.js.map +1 -1
  219. package/dist/cjs/shared/pickerTriggerContract.native.js.map +1 -1
  220. package/dist/cjs/shared/pressSlopProps.native.js.map +1 -1
  221. package/dist/cjs/shared/restoreRetries.native.js.map +1 -1
  222. package/dist/cjs/shared/sheetNavigation.native.js.map +1 -1
  223. package/dist/cjs/shared/systemControlModules.gnome.native.js.map +1 -1
  224. package/dist/cjs/shared/systemControls.native.js.map +1 -1
  225. package/dist/cjs/shared/t.native.js.map +1 -1
  226. package/dist/cjs/shared/tableCellContext.native.js.map +1 -1
  227. package/dist/cjs/shared/useDragScroll.native.js.map +1 -1
  228. package/dist/cjs/shared/useKeyboardInset.native.js.map +1 -1
  229. package/dist/cjs/shared/useSheetEscapeDismiss.native.js.map +1 -1
  230. package/dist/cjs/shared/useWheelIncrement.native.js.map +1 -1
  231. package/dist/cjs/shared/utils.native.js +1 -1
  232. package/dist/cjs/shared/utils.native.js.map +1 -1
  233. package/dist/cjs/shared/zIndex.native.js.map +1 -1
  234. package/dist/cjs/standardActions.native.js.map +1 -1
  235. package/dist/cjs/themedPrimitives.native.js.map +1 -1
  236. package/dist/cjs/types.native.js.map +1 -1
  237. package/dist/cjs/utils/LinkCell.native.js.map +1 -1
  238. package/dist/esm/FloatingPanel/index.mjs +2 -1
  239. package/dist/esm/FloatingPanel/index.mjs.map +1 -1
  240. package/dist/jsx/FloatingPanel/index.mjs +2 -1
  241. package/dist/jsx/FloatingPanel/index.mjs.map +1 -1
  242. package/package.json +8 -8
  243. package/src/FloatingPanel/FloatingPanel.coverTrigger.spec.tsx +53 -9
  244. package/src/FloatingPanel/FloatingPanel.seamlessCover.spec.tsx +7 -2
  245. package/src/FloatingPanel/index.tsx +5 -2
  246. package/types/FloatingPanel/index.d.ts +2 -1
  247. package/types/FloatingPanel/index.d.ts.map +1 -1
@@ -4,7 +4,9 @@ import { renderWithProviders } from "@multiplatform.one/test-utils";
4
4
  import { useState } from "react";
5
5
  import { Preset, defaultPreset, heroPreset, boldPreset } from "@multiplatform.one/theme";
6
6
  import { Button } from "../Button";
7
+ import type { CompactFace } from "./compactFace";
7
8
  import { FloatingPanel } from "./index";
9
+ import { panelViewportPadding } from "./useFloatingPanel";
8
10
 
9
11
  const triggerBounds = {
10
12
  x: 80,
@@ -37,7 +39,7 @@ function measure(bounds = triggerBounds, panelWidth = 240, panelHeight = 180) {
37
39
  );
38
40
  }
39
41
 
40
- function Harness({ scrollable }: { scrollable?: boolean }) {
42
+ function Harness({ scrollable, compactFace }: { scrollable?: boolean; compactFace?: CompactFace }) {
41
43
  const [open, setOpen] = useState(false);
42
44
  return (
43
45
  <FloatingPanel
@@ -45,6 +47,7 @@ function Harness({ scrollable }: { scrollable?: boolean }) {
45
47
  onOpenChange={setOpen}
46
48
  anchorMode="cover-trigger"
47
49
  scrollable={scrollable}
50
+ compactFace={compactFace}
48
51
  trigger={
49
52
  <Button aria-label="Timeline filters">
50
53
  <span aria-hidden="true">◇</span>Filters
@@ -57,9 +60,23 @@ function Harness({ scrollable }: { scrollable?: boolean }) {
57
60
  );
58
61
  }
59
62
 
63
+ function viewport(width: number, height: number) {
64
+ for (const [key, value] of [
65
+ ["innerWidth", width],
66
+ ["innerHeight", height],
67
+ ] as const) {
68
+ Object.defineProperty(window, key, { configurable: true, writable: true, value });
69
+ }
70
+ }
71
+
72
+ const desktop = { width: 1280, height: 800 };
73
+ const phone = { width: 390, height: 844 };
74
+ const initial = { width: window.innerWidth, height: window.innerHeight };
75
+
60
76
  afterEach(() => {
61
77
  vi.restoreAllMocks();
62
78
  document.documentElement.removeAttribute("dir");
79
+ viewport(initial.width, initial.height);
63
80
  });
64
81
 
65
82
  describe("LC-112 exact cover-trigger placement", () => {
@@ -124,11 +141,31 @@ describe("LC-112 exact cover-trigger placement", () => {
124
141
  await waitFor(() => expect(result.queryByTestId("floating-panel-viewport")).toBeNull());
125
142
  });
126
143
 
127
- it("uses a bottom sheet at the bottom edge instead of moving the first row upward", async () => {
128
- measure({ ...triggerBounds, y: 730, top: 730, bottom: 770 });
144
+ it("slides back on screen at the bottom edge on a desktop-width page, never a sheet (LC-139, FZ-9053)", async () => {
145
+ viewport(desktop.width, desktop.height);
146
+ measure({ ...triggerBounds, y: 760, top: 760, bottom: 800 });
129
147
  const result = renderWithProviders(<Harness />);
130
148
  const trigger = result.getByRole("button", { name: "Timeline filters" });
131
149
  trigger.focus();
150
+ fireEvent.click(trigger, { detail: 0 });
151
+ const panel = await result.findByTestId("floating-panel-viewport");
152
+ expect(result.queryByTestId("floating-panel-sheet")).toBeNull();
153
+ await waitFor(() => expect(parseFloat(panel.style.top)).toBeLessThan(760));
154
+ expect(parseFloat(panel.style.top) + 180).toBeLessThanOrEqual(
155
+ desktop.height - panelViewportPadding,
156
+ );
157
+ expect(result.getByRole("button", { name: "Assigned to me" })).toBeTruthy();
158
+ fireEvent.keyDown(document, { key: "Escape" });
159
+ await waitFor(() => expect(result.queryByTestId("floating-panel-viewport")).toBeNull());
160
+ await waitFor(() => expect(document.activeElement).toBe(trigger));
161
+ });
162
+
163
+ it("keeps the collision sheet at phone width (LC-139)", async () => {
164
+ viewport(phone.width, phone.height);
165
+ measure({ ...triggerBounds, y: 800, top: 800, bottom: 840 });
166
+ const result = renderWithProviders(<Harness compactFace="menu" />);
167
+ const trigger = result.getByRole("button", { name: "Timeline filters" });
168
+ trigger.focus();
132
169
  const parentChildren = trigger.closest("[data-fp-reference]")?.parentElement?.children.length;
133
170
  fireEvent.click(trigger, { detail: 0 });
134
171
  await result.findByTestId("floating-panel-sheet");
@@ -143,13 +180,14 @@ describe("LC-112 exact cover-trigger placement", () => {
143
180
  });
144
181
 
145
182
  it("closes the collision sheet on Escape while the trigger's tooltip is open", async () => {
146
- measure({ ...triggerBounds, y: 730, top: 730, bottom: 770 });
183
+ viewport(phone.width, phone.height);
184
+ measure({ ...triggerBounds, y: 800, top: 800, bottom: 840 });
147
185
  const tooltipEscape = (event: KeyboardEvent) => {
148
186
  if (event.key === "Escape") event.stopPropagation();
149
187
  };
150
188
  document.addEventListener("keydown", tooltipEscape);
151
189
  try {
152
- const result = renderWithProviders(<Harness />);
190
+ const result = renderWithProviders(<Harness compactFace="menu" />);
153
191
  const trigger = result.getByRole("button", { name: "Timeline filters" });
154
192
  fireEvent.click(trigger, { detail: 0 });
155
193
  await result.findByTestId("floating-panel-sheet");
@@ -160,12 +198,18 @@ describe("LC-112 exact cover-trigger placement", () => {
160
198
  }
161
199
  });
162
200
 
163
- it("uses a bottom sheet for horizontal collisions instead of shifting the trigger row", async () => {
164
- measure({ ...triggerBounds, x: 900, left: 900, right: 1020 });
201
+ it("slides back inside the end edge on a desktop-width page, never a sheet (LC-139, FZ-9053)", async () => {
202
+ viewport(desktop.width, desktop.height);
203
+ measure({ ...triggerBounds, x: 1150, left: 1150, right: 1270 });
165
204
  const result = renderWithProviders(<Harness />);
166
205
  fireEvent.click(result.getByRole("button", { name: "Timeline filters" }), { detail: 0 });
167
- await result.findByTestId("floating-panel-sheet");
168
- expect(result.queryByTestId("floating-panel-viewport")).toBeNull();
206
+ const panel = await result.findByTestId("floating-panel-viewport");
207
+ expect(result.queryByTestId("floating-panel-sheet")).toBeNull();
208
+ await waitFor(() =>
209
+ expect(parseFloat(panel.style.left) + 240).toBeLessThanOrEqual(
210
+ desktop.width - panelViewportPadding,
211
+ ),
212
+ );
169
213
  });
170
214
 
171
215
  it("aligns the trigger row at the logical start edge in RTL", async () => {
@@ -13,6 +13,7 @@ import { afterEach, describe, expect, it, vi } from "vitest";
13
13
  import { Text } from "tamagui";
14
14
  import { Button } from "../Button";
15
15
  import { FloatingPanel } from "./index";
16
+ import { panelViewportPadding } from "./useFloatingPanel";
16
17
 
17
18
  type Rect = { x: number; y: number; width: number; height: number };
18
19
 
@@ -238,12 +239,16 @@ describe("LC-112 icon trigger: the menu opens on its button (rv_d86cc201997dffd4
238
239
  expect(result.queryByTestId("floating-panel-sheet")).toBeNull();
239
240
  });
240
241
 
241
- it("never end-aligns a custom first row (triggerEcho off, coverAlign start): it collides to the sheet", async () => {
242
+ it("never end-aligns a custom first row (triggerEcho off, coverAlign start): on a desktop-width page it slides back inside the end edge, never a sheet (LC-139, FZ-9053)", async () => {
242
243
  const viewportWidth = document.documentElement.clientWidth || window.innerWidth;
243
244
  const button = { x: viewportWidth - 16 - 44, y: 12, width: 44, height: 44 };
244
245
  measure(button, 200);
245
246
  const result = renderWithProviders(<IconPanel align="start" />);
246
247
  fireEvent.click(result.getByRole("button", { name: "Appearance" }), { detail: 0 });
247
- expect(await result.findByTestId("floating-panel-sheet")).toBeTruthy();
248
+ const panel = (await result.findByTestId("floating-panel-viewport")) as HTMLElement;
249
+ await waitFor(() => expect(panel.style.visibility).toBe("visible"));
250
+ expect(parseFloat(panel.style.left)).toBe(viewportWidth - panelViewportPadding - 200);
251
+ expect(parseFloat(panel.style.left)).not.toBe(button.x + button.width - 200);
252
+ expect(result.queryByTestId("floating-panel-sheet")).toBeNull();
248
253
  });
249
254
  });
@@ -236,7 +236,8 @@ export interface FloatingPanelProps {
236
236
  * COVER-TRIGGER (LC-105): the panel's top edge sits on the trigger's TOP
237
237
  * edge instead of attaching below it, so the trigger becomes the panel's
238
238
  * first row by default. Set triggerEcho=false for a custom first row. The panel scales from
239
- * the trigger's top start corner. Viewport collisions use the bottom sheet.
239
+ * the trigger's top start corner. A viewport collision slides the panel back on screen;
240
+ * only a phone-width page takes the bottom sheet (LC-139).
240
241
  * Enabled by default. Web float only; the native and narrow-web sheet is unchanged.
241
242
  */
242
243
  cover?: boolean;
@@ -582,8 +583,10 @@ export function FloatingPanel(props: FloatingPanelProps) {
582
583
  ),
583
584
  };
584
585
 
586
+ const clampCollisions = viewportGtSm || (compactMenu && insideOverlay);
587
+
585
588
  if (shouldUseSheet) return <FloatingPanelSheet {...panelProps} />;
586
- return <FloatingPanelWeb {...panelProps} clampCollisions={compactMenu && insideOverlay} />;
589
+ return <FloatingPanelWeb {...panelProps} clampCollisions={clampCollisions} />;
587
590
  }
588
591
 
589
592
  // ── Sheet (mobile / native / forced) ──────────────────────────
@@ -175,7 +175,8 @@ export interface FloatingPanelProps {
175
175
  * COVER-TRIGGER (LC-105): the panel's top edge sits on the trigger's TOP
176
176
  * edge instead of attaching below it, so the trigger becomes the panel's
177
177
  * first row by default. Set triggerEcho=false for a custom first row. The panel scales from
178
- * the trigger's top start corner. Viewport collisions use the bottom sheet.
178
+ * the trigger's top start corner. A viewport collision slides the panel back on screen;
179
+ * only a phone-width page takes the bottom sheet (LC-139).
179
180
  * Enabled by default. Web float only; the native and narrow-web sheet is unchanged.
180
181
  */
181
182
  cover?: boolean;
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/FloatingPanel/index.tsx"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/FloatingPanel/index.tsx"],"names":[],"mappings":"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"}