@kanso-labs/react-native-kanso-ui 0.11.25 → 0.11.26

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.
@@ -1,56 +1,129 @@
1
1
  import { c } from "react/compiler-runtime";
2
- import { Keyboard, Platform } from "react-native";
2
+ import { Dimensions, Keyboard, Platform } from "react-native";
3
3
  import { useEffect, useState } from "react";
4
4
  // src/overlay/keyboard.ts
5
+ let loading;
6
+ function currentTop() {
7
+ return Platform.OS === "web" ? null : topOf(Keyboard.metrics());
8
+ }
9
+ async function load() {
10
+ try {
11
+ return await import(
12
+ /* @vite-ignore */
13
+ "react-native-keyboard-controller"
14
+ );
15
+ } catch {
16
+ return null;
17
+ }
18
+ }
19
+ async function loadController() {
20
+ loading ??= load();
21
+ return loading;
22
+ }
5
23
  function topOf(metrics) {
6
24
  return metrics === void 0 || metrics === null || metrics.height === 0 ? null : metrics.screenY;
7
25
  }
8
26
  /**
9
- * Where the software keyboard's top edge is in the window, in dp, or null
10
- * while no keyboard is shown, for a surface that has to stay above it. A
11
- * field's list opens while its keyboard is up, and the keyboard is drawn
12
- * over the window rather than shrinking it, so the window's own edge would
13
- * put the bottom of the list under the keys.
27
+ * How far the software keyboard reaches up over a window that fills the
28
+ * screen, in dp, or 0 while no keyboard is shown. A sheet or a dialog pads
29
+ * its content's bottom by this much, so what it holds stays above the
30
+ * keyboard. `enabled` false watches nothing and answers 0.
14
31
  */
15
- function useKeyboardTop() {
32
+ function useKeyboardInset(t0) {
16
33
  const $ = c(2);
17
- const [top, setTop] = useState(_temp);
18
- let t0;
34
+ const top = useKeyboardTop(t0 === void 0 ? true : t0);
19
35
  let t1;
20
- if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
21
- t0 = () => watchKeyboard(setTop);
22
- t1 = [];
23
- $[0] = t0;
36
+ if ($[0] !== top) {
37
+ t1 = top === null ? 0 : Math.max(0, Dimensions.get("screen").height - top);
38
+ $[0] = top;
24
39
  $[1] = t1;
40
+ } else t1 = $[1];
41
+ return t1;
42
+ }
43
+ /**
44
+ * Where the software keyboard's top edge is on the screen, in dp, or null
45
+ * while no keyboard is shown. `enabled` false watches nothing and answers
46
+ * null.
47
+ */
48
+ function useKeyboardTop(t0) {
49
+ const $ = c(5);
50
+ const enabled = t0 === void 0 ? true : t0;
51
+ let t1;
52
+ if ($[0] !== enabled) {
53
+ t1 = () => enabled ? currentTop() : null;
54
+ $[0] = enabled;
55
+ $[1] = t1;
56
+ } else t1 = $[1];
57
+ const [top, setTop] = useState(t1);
58
+ const [watching, setWatching] = useState(enabled);
59
+ if (watching !== enabled) {
60
+ setWatching(enabled);
61
+ setTop(enabled ? currentTop() : null);
62
+ }
63
+ let t2;
64
+ let t3;
65
+ if ($[2] !== enabled) {
66
+ t2 = () => enabled ? watchKeyboard(setTop) : void 0;
67
+ t3 = [enabled];
68
+ $[2] = enabled;
69
+ $[3] = t2;
70
+ $[4] = t3;
25
71
  } else {
26
- t0 = $[0];
27
- t1 = $[1];
72
+ t2 = $[3];
73
+ t3 = $[4];
28
74
  }
29
- useEffect(t0, t1);
75
+ useEffect(t2, t3);
30
76
  return top;
31
77
  }
32
78
  /**
33
- * Hands `listener` where the software keyboard's top edge is, or null, each
34
- * time the keyboard moves, and returns what stops it. iOS reports a frame as
35
- * the keyboard starts to move, and Android once it has arrived or gone,
36
- * which is all either reports. React Native Web has no keyboard to report,
37
- * and reports nothing.
79
+ * Hands `listener` where the software keyboard's top edge is on the screen,
80
+ * or null, each time the keyboard moves, and returns what stops it. iOS
81
+ * reports a frame as the keyboard starts to move, and Android once it has
82
+ * arrived or gone. On Android react-native-keyboard-controller reports it as
83
+ * well, from whichever window holds the focused field, and where both report
84
+ * a keyboard the higher edge wins. React Native Web has no keyboard to
85
+ * report, and reports nothing.
38
86
  */
39
- function _temp() {
40
- return Platform.OS === "web" ? null : topOf(Keyboard.metrics());
41
- }
42
87
  function watchKeyboard(listener) {
88
+ let native = null;
89
+ let controlled = null;
90
+ let stopped = false;
91
+ const report = () => {
92
+ const tops = [native, controlled].filter((top) => top !== null);
93
+ listener(tops.length === 0 ? null : Math.min(...tops));
94
+ };
43
95
  const moved = (event) => {
44
- listener(topOf(event.endCoordinates));
96
+ native = topOf(event.endCoordinates);
97
+ report();
45
98
  };
46
99
  const hidden = () => {
47
- listener(null);
100
+ native = null;
101
+ report();
48
102
  };
49
103
  const subscriptions = Platform.OS === "ios" ? [Keyboard.addListener("keyboardWillChangeFrame", moved), Keyboard.addListener("keyboardWillHide", hidden)] : [Keyboard.addListener("keyboardDidShow", moved), Keyboard.addListener("keyboardDidHide", hidden)];
104
+ const shown = ({ height }) => {
105
+ controlled = height > 0 ? Dimensions.get("screen").height - height : null;
106
+ native = controlled === null ? null : native;
107
+ report();
108
+ };
109
+ const gone = () => {
110
+ controlled = null;
111
+ native = null;
112
+ report();
113
+ };
114
+ const listen = async () => {
115
+ const controller = await loadController();
116
+ if (controller === null || stopped) return;
117
+ try {
118
+ subscriptions.push(controller.KeyboardEvents.addListener("keyboardWillShow", shown), controller.KeyboardEvents.addListener("keyboardDidShow", shown), controller.KeyboardEvents.addListener("keyboardWillHide", gone), controller.KeyboardEvents.addListener("keyboardDidHide", gone));
119
+ } catch {}
120
+ };
121
+ if (Platform.OS === "android") listen();
50
122
  return () => {
123
+ stopped = true;
51
124
  for (const subscription of subscriptions) subscription.remove();
52
125
  };
53
126
  }
54
- export { useKeyboardTop, watchKeyboard };
127
+ export { useKeyboardInset, useKeyboardTop, watchKeyboard };
55
128
 
56
129
  //# sourceMappingURL=keyboard.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"keyboard.js","names":["KeyboardEvent","KeyboardMetrics","useEffect","useState","Keyboard","Platform","topOf","metrics","undefined","height","screenY","useKeyboardTop","$","_c","top","setTop","_temp","t0","t1","Symbol","for","watchKeyboard","OS","listener","moved","event","endCoordinates","hidden","subscriptions","addListener","subscription","remove","_c"],"sources":["../../src/overlay/keyboard.ts"],"sourcesContent":["import type { KeyboardEvent, KeyboardMetrics } from 'react-native'\n\nimport { useEffect, useState } from 'react'\nimport { Keyboard, Platform } from 'react-native'\n\n// A keyboard reported with no height covers nothing.\nfunction topOf(metrics: KeyboardMetrics | null | undefined): null | number {\n return metrics === undefined || metrics === null || metrics.height === 0\n ? null\n : metrics.screenY\n}\n\n/**\n * Where the software keyboard's top edge is in the window, in dp, or null\n * while no keyboard is shown, for a surface that has to stay above it. A\n * field's list opens while its keyboard is up, and the keyboard is drawn\n * over the window rather than shrinking it, so the window's own edge would\n * put the bottom of the list under the keys.\n */\nfunction useKeyboardTop(): null | number {\n const [top, setTop] = useState(() =>\n Platform.OS === 'web' ? null : topOf(Keyboard.metrics()),\n )\n\n useEffect(() => watchKeyboard(setTop), [])\n\n return top\n}\n\n/**\n * Hands `listener` where the software keyboard's top edge is, or null, each\n * time the keyboard moves, and returns what stops it. iOS reports a frame as\n * the keyboard starts to move, and Android once it has arrived or gone,\n * which is all either reports. React Native Web has no keyboard to report,\n * and reports nothing.\n */\nfunction watchKeyboard(listener: (top: null | number) => void): () => void {\n const moved = (event: KeyboardEvent) => {\n listener(topOf(event.endCoordinates))\n }\n const hidden = () => {\n listener(null)\n }\n const subscriptions =\n Platform.OS === 'ios'\n ? [\n Keyboard.addListener('keyboardWillChangeFrame', moved),\n Keyboard.addListener('keyboardWillHide', hidden),\n ]\n : [\n Keyboard.addListener('keyboardDidShow', moved),\n Keyboard.addListener('keyboardDidHide', hidden),\n ]\n\n return () => {\n for (const subscription of subscriptions) {\n subscription.remove()\n }\n }\n}\n\nexport { useKeyboardTop, watchKeyboard }\n"],"mappings":";;;;AAMA,SAASM,MAAMC,SAA4D;CACzE,OAAOA,YAAYC,KAAAA,KAAaD,YAAY,QAAQA,QAAQE,WAAW,IACnE,OACAF,QAAQG;AACd;;;;;;;;AASA,SAAAC,iBAAA;CAAA,MAAAC,IAAAC,EAAA,CAAA;CACE,MAAA,CAAAC,KAAAC,UAAsBZ,SAASa,KAE/B;CAAC,IAAAC;CAAA,IAAAC;CAAA,IAAAN,EAAA,OAAAO,OAAAC,IAAA,2BAAA,GAAA;EAESH,WAAMI,cAAcN,MAAM;EAAGG,KAAA,CAAA;EAAEN,EAAA,KAAAK;EAAAL,EAAA,KAAAM;CAAA,OAAA;EAAAD,KAAAL,EAAA;EAAAM,KAAAN,EAAA;CAAA;CAAzCV,UAAUe,IAA6BC,EAAE;CAAC,OAEnCJ;AAAG;;;;;;;;AAPZ,SAAAE,QAAA;CAAA,OAEIX,SAAQiB,OAAQ,QAAhB,OAA+BhB,MAAMF,SAAQG,QAAS,CAAC;AAAC;AAe5D,SAASc,cAAcE,UAAoD;CACzE,MAAMC,SAASC,UAAyB;EACtCF,SAASjB,MAAMmB,MAAMC,cAAc,CAAC;CACtC;CACA,MAAMC,eAAe;EACnBJ,SAAS,IAAI;CACf;CACA,MAAMK,gBACJvB,SAASiB,OAAO,QACZ,CACElB,SAASyB,YAAY,2BAA2BL,KAAK,GACrDpB,SAASyB,YAAY,oBAAoBF,MAAM,CAAC,IAElD,CACEvB,SAASyB,YAAY,mBAAmBL,KAAK,GAC7CpB,SAASyB,YAAY,mBAAmBF,MAAM,CAAC;CAGvD,aAAa;EACX,KAAK,MAAMG,gBAAgBF,eACzBE,aAAaC,OAAO;CAExB;AACF"}
1
+ {"version":3,"file":"keyboard.js","names":["KeyboardEvent","KeyboardMetrics","useEffect","useState","Dimensions","Keyboard","Platform","Controller","loading","Promise","currentTop","OS","topOf","metrics","load","loadController","undefined","height","screenY","useKeyboardInset","t0","$","_c","enabled","top","useKeyboardTop","t1","Math","max","get","setTop","watching","setWatching","t2","t3","watchKeyboard","listener","native","controlled","stopped","report","tops","filter","length","min","moved","event","endCoordinates","hidden","subscriptions","addListener","shown","gone","listen","controller","push","KeyboardEvents","subscription","remove","_c"],"sources":["../../src/overlay/keyboard.ts"],"sourcesContent":["import type { KeyboardEvent, KeyboardMetrics } from 'react-native'\n\nimport { useEffect, useState } from 'react'\nimport { Dimensions, Keyboard, Platform } from 'react-native'\n\ntype Controller = typeof import('react-native-keyboard-controller')\n\n// Android reports the keyboard to React Native's `Keyboard` only from the\n// app's own window, and a sheet, a dialog or a popover is a `Modal`, which is\n// a window of its own: a field focused there moves the keyboard and reports\n// nothing. react-native-keyboard-controller reports it from every window,\n// once the app mounts its `KeyboardProvider`. It is an optional peer, so it\n// is imported where its absence can be caught, as src/clipboard/index.ts\n// imports expo-clipboard, and an app without it keeps React Native's reports\n// alone. The import settles once, and to `null` once it has failed.\nlet loading: Promise<Controller | null> | undefined\n\n// Where the keyboard's top edge is now, as far as React Native has heard.\nfunction currentTop(): null | number {\n return Platform.OS === 'web' ? null : topOf(Keyboard.metrics())\n}\n\nasync function load(): Promise<Controller | null> {\n try {\n return await import(/* @vite-ignore */ 'react-native-keyboard-controller')\n } catch {\n return null\n }\n}\n\nasync function loadController(): Promise<Controller | null> {\n loading ??= load()\n return loading\n}\n\n// A keyboard reported with no height covers nothing.\nfunction topOf(metrics: KeyboardMetrics | null | undefined): null | number {\n return metrics === undefined || metrics === null || metrics.height === 0\n ? null\n : metrics.screenY\n}\n\n/**\n * How far the software keyboard reaches up over a window that fills the\n * screen, in dp, or 0 while no keyboard is shown. A sheet or a dialog pads\n * its content's bottom by this much, so what it holds stays above the\n * keyboard. `enabled` false watches nothing and answers 0.\n */\nfunction useKeyboardInset(enabled = true): number {\n const top = useKeyboardTop(enabled)\n\n return top === null ? 0 : Math.max(0, Dimensions.get('screen').height - top)\n}\n\n/**\n * Where the software keyboard's top edge is on the screen, in dp, or null\n * while no keyboard is shown. `enabled` false watches nothing and answers\n * null.\n */\nfunction useKeyboardTop(enabled = true): null | number {\n const [top, setTop] = useState(() => (enabled ? currentTop() : null))\n const [watching, setWatching] = useState(enabled)\n\n // Nothing is heard while it is not watched, so it starts again from where\n // the keyboard is now.\n if (watching !== enabled) {\n setWatching(enabled)\n setTop(enabled ? currentTop() : null)\n }\n\n useEffect(() => (enabled ? watchKeyboard(setTop) : undefined), [enabled])\n\n return top\n}\n\n/**\n * Hands `listener` where the software keyboard's top edge is on the screen,\n * or null, each time the keyboard moves, and returns what stops it. iOS\n * reports a frame as the keyboard starts to move, and Android once it has\n * arrived or gone. On Android react-native-keyboard-controller reports it as\n * well, from whichever window holds the focused field, and where both report\n * a keyboard the higher edge wins. React Native Web has no keyboard to\n * report, and reports nothing.\n */\nfunction watchKeyboard(listener: (top: null | number) => void): () => void {\n let native: null | number = null\n let controlled: null | number = null\n let stopped = false\n\n const report = () => {\n const tops = [native, controlled].filter((top) => top !== null)\n listener(tops.length === 0 ? null : Math.min(...tops))\n }\n const moved = (event: KeyboardEvent) => {\n native = topOf(event.endCoordinates)\n report()\n }\n const hidden = () => {\n native = null\n report()\n }\n const subscriptions =\n Platform.OS === 'ios'\n ? [\n Keyboard.addListener('keyboardWillChangeFrame', moved),\n Keyboard.addListener('keyboardWillHide', hidden),\n ]\n : [\n Keyboard.addListener('keyboardDidShow', moved),\n Keyboard.addListener('keyboardDidHide', hidden),\n ]\n\n // The controller sees every window, so its keyboard going away is the\n // keyboard gone, whatever React Native last heard from the app's own.\n const shown = ({ height }: { readonly height: number }) => {\n controlled = height > 0 ? Dimensions.get('screen').height - height : null\n native = controlled === null ? null : native\n report()\n }\n const gone = () => {\n controlled = null\n native = null\n report()\n }\n const listen = async () => {\n const controller = await loadController()\n\n if (controller === null || stopped) {\n return\n }\n\n // A controller installed without its native half throws as it is read,\n // which leaves React Native's reports alone.\n try {\n subscriptions.push(\n controller.KeyboardEvents.addListener('keyboardWillShow', shown),\n controller.KeyboardEvents.addListener('keyboardDidShow', shown),\n controller.KeyboardEvents.addListener('keyboardWillHide', gone),\n controller.KeyboardEvents.addListener('keyboardDidHide', gone),\n )\n } catch {\n // Nothing to watch.\n }\n }\n\n if (Platform.OS === 'android') {\n void listen()\n }\n\n return () => {\n stopped = true\n\n for (const subscription of subscriptions) {\n subscription.remove()\n }\n }\n}\n\nexport { useKeyboardInset, useKeyboardTop, watchKeyboard }\n"],"mappings":"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"}
@@ -63,7 +63,7 @@ function changedOf(line) {
63
63
  };
64
64
  }
65
65
  function commonPrefixLength(texts) {
66
- const sorted = texts.toSorted();
66
+ const sorted = [...texts].sort();
67
67
  const first = sorted.at(0) ?? "";
68
68
  const last = sorted.at(-1) ?? "";
69
69
  let length = 0;
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","names":["Calendar","ComponentRef","Dispatch","Ref","RefObject","SetStateAction","AccessibilityActionEvent","AccessibilityActionInfo","HostInstance","PressableProps","StyleProp","TextStyle","ViewStyle","DateFieldState","DateSegment","DateSegmentType","CalendarDate","DateFormatter","toCalendar","useEffect","useEffectEvent","useId","useImperativeHandle","useRef","useState","I18nManager","Text","NativeText","Platform","Pressable","StyleSheet","TextInput","FieldDescriptionPart","Focusable","LibraryMessages","startsWithIn","descriptionOf","FieldSegments","messagesFor","NumberParser","useTheme","composeStyles","useTypeRole","segmentStylesOf","DateSegmentsProps","described","drawing","SegmentDrawing","holding","isInvalid","label","locale","onActiveChange","type","onBeforeStart","onBlur","onEdit","onFocus","onPastEnd","ref","SegmentsHandle","state","Focusing","Pick","SegmentLineProps","Moves","away","next","previous","box","isActive","literal","parts","ReadonlySet","raisesKeyboard","text","Omit","active","entered","input","inside","nodes","Map","setActive","focusLast","focusOn","keyboard","Step","WebSegmentProps","ADJUSTABLE","name","INVISIBLE","SENTINEL","AFTER_SENTINEL","end","length","start","NUMERIC","Set","styles","create","height","opacity","position","top","width","notDrawn","display","actionOf","line","segment","event","actionName","nativeEvent","stepKey","arrivedIn","current","changedOf","segments","find","each","undefined","eraseKey","point","replace","codePointAt","typeKey","String","fromCodePoint","commonPrefixLength","texts","sorted","toSorted","first","at","last","DateSegments","t0","$","_c","props","t1","Symbol","for","t2","reportActive","t3","t4","t5","focus","typedInto","focusTo","findLast","segment_0","type_0","t6","dayPeriodsOf","formatter","hour","hour12","periodAt","hours","date","Date","setHours","formatToParts","part","value","drawn","replaceAll","has","edited","changed","eraseFrom","moves","isDisabled","isReadOnly","placeholder","parser","maximumFractionDigits","isValidPartialNumber","isPlaceholder","shortened","slice","parsed","parse","kept","clearSegment","setSegment","movesFrom","erasOf","calendar","era","timeZone","year","eras","getEras","map","set","day","month","toDate","formatted","prefix","OS","get","blur","hidesEra","identifier","inputFocusedOf","inputOf","node","leftOf","confirmPlaceholder","editable","filter","findIndex","to","index","beyond","nameOf","nodeOf","delete","pressOf","relatedTargetOf","relatedTarget","SegmentLine","id","theme","own","role","words","valueOf","valueId","canEdit","T0","isEditable","textDisabled","textMuted","focused","describes","webPropsOf","webStateOf","maxValue","minValue","valueTextOf","empty","segmentFocused","textStyleOf","stepBy","by","ReturnType","textFocused","typeInto","key","startsWith","typed","number","Number","isNaN","over","am","pm","matched","written","formatValue","maxGranularity","selectedTime","selectedDate","dateFormatter","resolvedOptions","format","dateValue","step","erase","keys","isRTL","values","some","onKeyDown","altKey","ctrlKey","metaKey","handler","preventDefault","isRequired","_c","NativeText"],"sources":["../../src/segments/index.tsx"],"sourcesContent":["import type { Calendar } from '@internationalized/date'\nimport type {\n ComponentRef,\n Dispatch,\n Ref,\n RefObject,\n SetStateAction,\n} from 'react'\nimport type {\n AccessibilityActionEvent,\n AccessibilityActionInfo,\n HostInstance,\n PressableProps,\n StyleProp,\n TextStyle,\n ViewStyle,\n} from 'react-native'\nimport type {\n DateFieldState,\n DateSegment,\n DateSegmentType,\n} from 'react-stately/useDateFieldState'\n\nimport {\n CalendarDate,\n DateFormatter,\n toCalendar,\n} from '@internationalized/date'\nimport {\n useEffect,\n useEffectEvent,\n useId,\n useImperativeHandle,\n useRef,\n useState,\n} from 'react'\nimport {\n I18nManager,\n Text as NativeText,\n Platform,\n Pressable,\n StyleSheet,\n TextInput,\n} from 'react-native'\n\nimport type { FieldDescriptionPart } from '../field'\nimport type { Focusable } from '../form'\nimport type { LibraryMessages } from '../i18n/messages'\n\nimport { startsWithIn } from '../autocomplete'\nimport { descriptionOf, FieldSegments } from '../field'\nimport { messagesFor } from '../i18n'\nimport { NumberParser } from '../number/parser'\nimport { useTheme } from '../theme/scope'\nimport { composeStyles } from '../theme/styles'\nimport { useTypeRole } from '../typography/roles'\nimport { segmentStylesOf } from './styles'\n\n// The segments a date or a time is typed into, one part of the value each, as\n// web's src/segments draws them. React Stately's date field state decides\n// what the parts are, how many, in what order and what each may hold, from\n// the locale and the granularity, so a field built on it draws them from that\n// state rather than writing any of them out. What is here is how a person\n// types into them and how a screen reader reads them, which is React Aria's\n// useDateSegment ported, since React Aria does not run on native.\n//\n// **Typing is React Aria's, digit for digit.** A digit goes into the segment\n// after the ones typed before it, and moves on to the next segment once no\n// further digit could fit, so `9` in a month moves on and `1` waits for a\n// second. A letter picks a day period or an era by the start of its name in\n// the locale, backspace takes a digit off the end, and on an empty segment\n// moves back to the one before it.\n//\n// **On iOS and Android one hidden input takes the keys.** A view cannot raise\n// the keyboard, so a press on a segment makes it the one being typed and\n// focuses a text input no one sees or reads, which holds one space and hands\n// over each key typed after it. Its keyboard is a number pad for a segment of\n// digits and the full one for a day period or an era. A screen reader reaches\n// each segment as an adjustable element instead, which a swipe steps up or\n// down, and which opens the keyboard when activated.\n//\n// **Under React Native Web each segment is its own focus stop**, as web's\n// are, read as a spin button and typed into with the keys a browser hands\n// it: digits and letters, backspace, the arrow keys up and down to step, and\n// left and right to move between segments, which follow the direction the\n// page reads in.\n//\n// **A drawing of their own replaces a field's line**, for segments that are\n// not a field's: a box per part, the text inside it and the punctuation\n// between them, each the caller's, as a time picker's modal draws its hour\n// and minute. It names the parts it draws, and focus passes the others by,\n// so a day period a selector beside the boxes stands for is never typed into.\n// Punctuation is drawn only where it holds something to see, since a\n// locale's literals carry bidirectional marks and spaces beside it.\n\ntype DateSegmentsProps = {\n /** What describes the field after the value it holds: the line under it. */\n readonly described: readonly FieldDescriptionPart[]\n /** How the segments are drawn where they are not a field's line. */\n readonly drawing?: SegmentDrawing\n /**\n * What the segments are read as holding, after their own names: the date\n * or the time written out, unless a range picker around them reads its\n * whole range here instead. `''` reads nothing.\n */\n readonly holding?: string\n /** Whether the field shows an error, which every segment then says. */\n readonly isInvalid: boolean\n /** The field's label, which each segment's name ends in. */\n readonly label: string\n /** The locale the field writes in: its `useLocaleOf`. */\n readonly locale: string\n /**\n * Called with the segment in focus as it changes, and with `null` as focus\n * leaves them.\n */\n readonly onActiveChange?: (type: DateSegmentType | null) => void\n /**\n * Called where focus would move back from the first segment, as a\n * backspace on it does, which a range picker sends on to the start's last.\n */\n readonly onBeforeStart?: () => void\n /** Called as focus leaves the segments, once they fill in what they can. */\n readonly onBlur?: () => void\n /** Called after each edit a person makes, typed or stepped. */\n readonly onEdit?: () => void\n /** Called as focus arrives in the segments from outside them. */\n readonly onFocus?: () => void\n /**\n * Called where focus would move on from the last segment, as a full one\n * does, which a range picker sends on to the end's first.\n */\n readonly onPastEnd?: () => void\n /** What focuses the segments: the first, or the last. */\n readonly ref?: Ref<SegmentsHandle>\n readonly state: DateFieldState\n}\n\n// What moving focus to a segment reaches for.\ntype Focusing = Pick<\n SegmentLineProps,\n 'entered' | 'input' | 'nodes' | 'setActive' | 'state'\n>\n\ntype Moves = {\n // Where focus goes from a segment that stops being drawn, as React Aria's\n // goes from one it removes: the one before it, or the one after it where it\n // was the first.\n readonly away: () => void\n readonly next: () => void\n readonly previous: () => void\n}\n\n/**\n * How segments are drawn in place of a field's line of body large text, each\n * style chosen for whether its part is the one in focus.\n */\ntype SegmentDrawing = {\n /** The box a part a person types into is drawn in. */\n readonly box: (\n type: DateSegmentType,\n isActive: boolean,\n ) => StyleProp<ViewStyle>\n /** The punctuation between two parts. */\n readonly literal: StyleProp<TextStyle>\n /** The parts drawn. The rest are left out, and focus passes them by. */\n readonly parts: ReadonlySet<DateSegmentType>\n /**\n * Whether a press on a part raises the keyboard on iOS and Android, as a\n * field's does, rather than only making it the one in focus.\n */\n readonly raisesKeyboard: boolean\n /** The text inside a part's box. */\n readonly text: (\n type: DateSegmentType,\n isActive: boolean,\n ) => StyleProp<TextStyle>\n}\n\n// The segments' own props, with what the component around them keeps for\n// them: which one is being typed, what has been typed into it, whether focus\n// is among them, the hidden input and each segment's element.\ntype SegmentLineProps = Omit<DateSegmentsProps, 'ref'> & {\n readonly active: DateSegmentType | null\n readonly entered: RefObject<string>\n readonly input: RefObject<ComponentRef<typeof TextInput> | null>\n readonly inside: RefObject<boolean>\n readonly nodes: RefObject<Map<DateSegmentType, HostInstance>>\n readonly setActive: Dispatch<SetStateAction<DateSegmentType | null>>\n}\n\n/**\n * What focuses a field's segments: `focus` the first, unless focus is among\n * them already, `focusLast` the last, and `focusOn` the one of `type`, with\n * the keyboard raised on iOS and Android or put away.\n */\ntype SegmentsHandle = Focusable & {\n readonly focusLast: () => void\n readonly focusOn: (type: DateSegmentType, keyboard: boolean) => void\n}\n\n// A step a spin button takes, each one a method of the field's state.\ntype Step =\n | 'decrement'\n | 'decrementPage'\n | 'decrementToMin'\n | 'increment'\n | 'incrementPage'\n | 'incrementToMax'\n\n// What a segment is handed under React Native Web, which takes keys and focus\n// on any element.\ntype WebSegmentProps = Pick<PressableProps, 'onBlur' | 'onFocus' | 'onKeyDown'>\n\n// What a screen reader can ask of a segment: a step up, or a step down.\nconst ADJUSTABLE: readonly AccessibilityActionInfo[] = [\n { name: 'increment' },\n { name: 'decrement' },\n]\n\n// What a literal holds besides what it is drawn for: the spaces, and the\n// marks a locale sets a direction with.\nconst INVISIBLE = /[\\s\\u061C\\u200E\\u200F\\u202A-\\u202E\\u2066-\\u2069]/gu\n\n// The text the hidden input holds, which a backspace has something to take\n// from and which every key typed lands after.\nconst SENTINEL = ' '\n\n// Where the hidden input's caret stays: after the space.\nconst AFTER_SENTINEL = { end: SENTINEL.length, start: SENTINEL.length }\n\n// The segments a number is typed into, which the number pad serves.\nconst NUMERIC = new Set<DateSegmentType>([\n 'day',\n 'hour',\n 'minute',\n 'month',\n 'second',\n 'year',\n])\n\nconst styles = StyleSheet.create({\n // The input no one sees, which is there to raise the keyboard and take its\n // keys. Still laid out, since an input with no size takes no focus.\n input: {\n height: 1,\n opacity: 0,\n position: 'absolute',\n start: 0,\n top: 0,\n width: 1,\n },\n // The date written out, in the document under React Native Web for the\n // first segment to point at, and drawn nowhere.\n notDrawn: {\n display: 'none',\n },\n})\n\n// What a screen reader's swipe up or down does to a segment.\nfunction actionOf(line: SegmentLineProps, segment: DateSegment) {\n return (event: AccessibilityActionEvent) => {\n const { actionName } = event.nativeEvent\n if (actionName === 'increment' || actionName === 'decrement') {\n stepKey(line, segment, actionName)\n }\n }\n}\n\n// Where focus goes once a person is in the segments: what the field calls on\n// arriving, which it hears once however many segments focus passes through.\nfunction arrivedIn({ inside, onFocus }: SegmentLineProps) {\n if (!inside.current) {\n inside.current = true\n onFocus?.()\n }\n}\n\n// What the hidden input does with each change to its text: a shorter text is\n// a backspace, and a longer one a key typed after the space.\nfunction changedOf(line: SegmentLineProps) {\n return (text: string) => {\n const segment = line.state.segments.find(\n (each) => each.type === line.active,\n )\n\n if (segment === undefined) {\n return\n }\n\n if (text.length < SENTINEL.length) {\n eraseKey(line, segment)\n return\n }\n\n // One key at a time, the first typed after the space: a second handed\n // over in the same change would be written over by the first, since\n // both are set from the value this render holds.\n const point = text.replace(SENTINEL, '').codePointAt(0)\n\n if (point !== undefined) {\n typeKey(line, segment, String.fromCodePoint(point))\n }\n }\n}\n\n// The number of characters at the start of every one of `texts` that they\n// share, which an era's name is typed after, as React Aria finds it.\nfunction commonPrefixLength(texts: readonly string[]) {\n const sorted = texts.toSorted()\n const first = sorted.at(0) ?? ''\n const last = sorted.at(-1) ?? ''\n let length = 0\n\n while (length < first.length && first[length] === last[length]) {\n length++\n }\n\n return length\n}\n\n/**\n * A date or a time's segments, inside a field's box, from React Stately's\n * date field state: each part of the value typed or stepped on its own, the\n * one being typed drawn as a filled shape and the empty ones in their\n * placeholders, muted.\n */\nfunction DateSegments({ onActiveChange, ref, ...props }: DateSegmentsProps) {\n const [active, setActive] = useState<DateSegmentType | null>(null)\n // What has been typed into the segment in focus since it took focus, which\n // the next digit is read after.\n const entered = useRef('')\n // Whether focus is in the segments, which a press on the box around them\n // leaves where it is.\n const inside = useRef(false)\n const input = useRef<ComponentRef<typeof TextInput>>(null)\n // Each segment's element under React Native Web, which focus moves to.\n const nodes = useRef(new Map<DateSegmentType, HostInstance>())\n const { drawing, state } = props\n const reportActive = useEffectEvent((type: DateSegmentType | null) => {\n onActiveChange?.(type)\n })\n\n useEffect(() => {\n reportActive(active)\n }, [active])\n\n useImperativeHandle(ref, () => ({\n focus: () => {\n const first = state.segments.find((segment) =>\n typedInto(drawing, segment),\n )\n if (!inside.current && first !== undefined) {\n focusTo({ entered, input, nodes, setActive, state }, first.type)\n }\n },\n focusLast: () => {\n const last = state.segments.findLast((segment) =>\n typedInto(drawing, segment),\n )\n if (last !== undefined) {\n focusTo({ entered, input, nodes, setActive, state }, last.type)\n }\n },\n focusOn: (type, keyboard) => {\n focusTo({ entered, input, nodes, setActive, state }, type, keyboard)\n },\n }))\n\n return (\n <SegmentLine\n {...props}\n active={active}\n entered={entered}\n input={input}\n inside={inside}\n nodes={nodes}\n setActive={setActive}\n />\n )\n}\n\n// What the locale calls the morning and the afternoon, which a key picks\n// between by the start of each.\nfunction dayPeriodsOf(locale: string): readonly [string, string] {\n const formatter = new DateFormatter(locale, { hour: 'numeric', hour12: true })\n const periodAt = (hours: number) => {\n const date = new Date()\n date.setHours(hours)\n return (\n formatter.formatToParts(date).find((part) => part.type === 'dayPeriod')\n ?.value ?? ''\n )\n }\n\n return [periodAt(0), periodAt(12)]\n}\n\n// Whether a segment is drawn: every one on a field's line, and in a drawing\n// of its own the parts it names and the punctuation that holds something to\n// see.\nfunction drawn(drawing: SegmentDrawing | undefined, segment: DateSegment) {\n if (drawing === undefined) {\n return true\n }\n\n return segment.type === 'literal'\n ? segment.text.replaceAll(INVISIBLE, '') !== ''\n : drawing.parts.has(segment.type)\n}\n\nfunction edited({ onEdit }: SegmentLineProps, changed: boolean) {\n if (changed) {\n onEdit?.()\n }\n}\n\n// Takes a digit off the end of a segment, as backspace does in React Aria's,\n// and clears a day period or an era outright. On a segment already empty it\n// moves to the one before. Whether it changed the value.\nfunction eraseFrom(\n state: DateFieldState,\n segment: DateSegment,\n locale: string,\n entered: RefObject<string>,\n moves: Moves,\n): boolean {\n if (state.isDisabled || state.isReadOnly) {\n return false\n }\n\n if (segment.text === segment.placeholder) {\n moves.previous()\n }\n\n const parser = new NumberParser(locale, { maximumFractionDigits: 0 })\n\n if (parser.isValidPartialNumber(segment.text) && !segment.isPlaceholder) {\n const shortened = segment.text.slice(0, -1)\n const parsed = parser.parse(shortened)\n const kept = parsed === 0 ? '' : shortened\n\n if (kept === '') {\n state.clearSegment(segment.type)\n } else {\n state.setSegment(segment.type, parsed)\n }\n entered.current = kept\n return true\n }\n\n if (segment.type === 'dayPeriod' || segment.type === 'era') {\n state.clearSegment(segment.type)\n return true\n }\n\n return false\n}\n\nfunction eraseKey(line: SegmentLineProps, segment: DateSegment) {\n edited(\n line,\n eraseFrom(\n line.state,\n segment,\n line.locale,\n line.entered,\n movesFrom(line, segment.type),\n ),\n )\n}\n\n// The calendar's eras with the names a key picks them by: each era's name in\n// the locale, less what every name begins with, so a calendar whose eras are\n// ERA0 and ERA1 is typed with 0 and 1, as React Aria's is.\nfunction erasOf(calendar: Calendar, locale: string) {\n const formatter = new DateFormatter(locale, {\n era: 'narrow',\n timeZone: 'UTC',\n year: 'numeric',\n })\n const first = toCalendar(new CalendarDate(1, 1, 1), calendar)\n const eras = calendar.getEras().map((era) => {\n const date = first.set({ day: 1, era, month: 1, year: 1 }).toDate('UTC')\n\n return {\n era,\n // An era with no name in the locale is typed by its identifier.\n formatted:\n formatter.formatToParts(date).find((part) => part.type === 'era')\n ?.value ?? era,\n }\n })\n const prefix = commonPrefixLength(eras.map((era) => era.formatted))\n\n return eras.map(({ era, formatted }) => ({\n era,\n formatted: formatted.slice(prefix),\n }))\n}\n\n// Moves focus to the segment of `type`: the segment's own element under React\n// Native Web, and on iOS and Android the hidden input, with the segment made\n// the one it types into. A read-only field raises no keyboard, and nor does a\n// move that puts the keyboard away, which makes the segment the one in focus\n// and takes focus off the input.\nfunction focusTo(\n { entered, input, nodes, setActive, state }: Focusing,\n type: DateSegmentType,\n keyboard = true,\n) {\n entered.current = ''\n\n if (Platform.OS === 'web') {\n nodes.current.get(type)?.focus()\n return\n }\n\n if (!keyboard) {\n setActive(type)\n input.current?.blur()\n return\n }\n\n if (state.isReadOnly) {\n return\n }\n\n setActive(type)\n input.current?.focus()\n}\n\n// Whether setting the era to `era` stops the era segment being drawn, which\n// React Stately draws in a Gregorian calendar only while the date is BC.\nfunction hidesEra(state: DateFieldState, era: string) {\n return state.calendar.identifier === 'gregory' && era !== 'BC'\n}\n\n// What the hidden input does on taking focus: types into the segment it was\n// focused for, or the first where it was focused some other way.\nfunction inputFocusedOf(line: SegmentLineProps) {\n return () => {\n const first =\n line.state.segments.find((segment) => typedInto(line.drawing, segment))\n ?.type ?? null\n line.setActive((current) => current ?? first)\n arrivedIn(line)\n }\n}\n\n// Keeps the hidden input, which focus is moved to on iOS and Android.\nfunction inputOf({ input }: SegmentLineProps) {\n return (node: ComponentRef<typeof TextInput> | null) => {\n input.current = node\n }\n}\n\n// What focus leaving the segments does: fills in what the placeholder can,\n// as React Aria's field does on blur, then tells the field.\nfunction leftOf({\n entered,\n inside,\n onBlur,\n setActive,\n state,\n}: SegmentLineProps) {\n return () => {\n inside.current = false\n entered.current = ''\n setActive(null)\n state.confirmPlaceholder()\n onBlur?.()\n }\n}\n\n// The segments on either side of the one of `type`, among those a person\n// types into, which a full segment moves on to and a backspace back to. Past\n// either end it is the field's to say, as a range picker's focus moves on\n// from one date's segments to the other's.\nfunction movesFrom(line: SegmentLineProps, type: DateSegmentType): Moves {\n const editable = line.state.segments.filter((segment) =>\n typedInto(line.drawing, segment),\n )\n const at = editable.findIndex((segment) => segment.type === type)\n const to = (index: number, beyond?: () => void) => () => {\n const segment = index < 0 ? undefined : editable.at(index)\n if (segment === undefined) {\n beyond?.()\n } else {\n focusTo(line, segment.type)\n }\n }\n\n return {\n away: to(at > 0 ? at - 1 : at + 1),\n next: to(at + 1, line.onPastEnd),\n previous: to(at - 1, line.onBeforeStart),\n }\n}\n\n// The name a segment of `type` is read by. A literal is never read, and is\n// named as a day only to keep the lookup total.\nfunction nameOf(\n type: DateSegmentType,\n): keyof Omit<\n LibraryMessages['segments'],\n 'empty' | 'selectedDate' | 'selectedTime'\n> {\n return type === 'literal' ? 'day' : type\n}\n\n// Keeps each segment's element, which focus is moved to under React Native\n// Web, for as long as it is drawn.\nfunction nodeOf({ nodes }: SegmentLineProps, type: DateSegmentType) {\n return (node: HostInstance | null) => {\n if (node === null) {\n return undefined\n }\n\n nodes.current.set(type, node)\n return () => {\n nodes.current.delete(type)\n }\n }\n}\n\n// What a press on a segment does on iOS and Android: makes it the one typed\n// into, and raises the keyboard, unless the drawing says a press only makes\n// it the one in focus.\nfunction pressOf(line: SegmentLineProps, type: DateSegmentType) {\n return () => {\n focusTo(line, type, line.drawing?.raisesKeyboard ?? true)\n }\n}\n\n// The element focus moved to, off a browser's blur event.\nfunction relatedTargetOf(event: unknown): unknown {\n return typeof event === 'object' && event !== null && 'relatedTarget' in event\n ? event.relatedTarget\n : undefined\n}\n\n// The segments themselves, drawn from the field's state.\nfunction SegmentLine(line: SegmentLineProps) {\n const { active, described, drawing, isInvalid, label, locale, state } = line\n const id = useId()\n const theme = useTheme()\n const own = segmentStylesOf(theme)\n const role = useTypeRole('bodyLarge')\n const words = messagesFor(locale).segments\n const first = state.segments.find((segment) => typedInto(drawing, segment))\n const value = line.holding ?? valueOf(state, words)\n const valueId = `${id}-value`\n const parts =\n value === '' ? described : [{ id: valueId, text: value }, ...described]\n const canEdit = !state.isDisabled && !state.isReadOnly\n\n return (\n <FieldSegments>\n {state.segments.map((segment, index) => {\n if (!drawn(drawing, segment)) {\n return null\n }\n\n if (!segment.isEditable) {\n return (\n <NativeText\n aria-hidden={segment.type === 'literal'}\n // A segment's place is its key, and a literal's its index, since\n // a locale can put the same punctuation between several.\n // oxlint-disable-next-line react/no-array-index-key -- see above\n key={`${segment.type}-${index}`}\n style={\n drawing === undefined\n ? composeStyles<TextStyle>(\n role,\n segment.type === 'literal' ? undefined : own.segment,\n state.isDisabled\n ? own.textDisabled\n : segment.type === 'literal'\n ? own.textMuted\n : own.text,\n )\n : drawing.literal\n }\n >\n {segment.text}\n </NativeText>\n )\n }\n\n const focused = segment.type === active\n // The field's description is said on the first segment alone, so it\n // is not heard again at every step, unless the field has an error.\n const describes = isInvalid || segment.type === first?.type\n\n return (\n <Pressable\n {...(Platform.OS === 'web' ? webPropsOf(line, segment) : undefined)}\n {...(describes ? descriptionOf(parts) : undefined)}\n {...webStateOf(isInvalid, state)}\n accessibilityActions={canEdit ? ADJUSTABLE : undefined}\n accessibilityRole={Platform.OS === 'web' ? undefined : 'adjustable'}\n aria-disabled={state.isDisabled}\n aria-label={`${words[nameOf(segment.type)]}, ${label}`}\n aria-valuemax={segment.maxValue}\n aria-valuemin={segment.minValue}\n aria-valuenow={segment.value ?? undefined}\n aria-valuetext={valueTextOf(segment, state, locale, words.empty)}\n disabled={state.isDisabled}\n key={segment.type}\n onAccessibilityAction={actionOf(line, segment)}\n onPress={\n Platform.OS === 'web' ? undefined : pressOf(line, segment.type)\n }\n ref={nodeOf(line, segment.type)}\n role={Platform.OS === 'web' ? 'spinbutton' : undefined}\n style={\n drawing === undefined\n ? composeStyles<ViewStyle>(\n own.segment,\n focused ? own.segmentFocused : undefined,\n )\n : drawing.box(segment.type, focused)\n }\n >\n <NativeText\n style={\n drawing === undefined\n ? composeStyles<TextStyle>(\n role,\n textStyleOf(own, segment, focused, state.isDisabled),\n )\n : drawing.text(segment.type, focused)\n }\n >\n {segment.text}\n </NativeText>\n </Pressable>\n )\n })}\n {Platform.OS === 'web' ? (\n value === '' ? null : (\n <NativeText id={valueId} style={styles.notDrawn}>\n {value}\n </NativeText>\n )\n ) : (\n <TextInput\n aria-hidden\n autoCapitalize=\"none\"\n autoComplete=\"off\"\n autoCorrect={false}\n caretHidden\n contextMenuHidden\n editable={canEdit}\n importantForAutofill=\"no\"\n keyboardType={\n active === null || NUMERIC.has(active) ? 'number-pad' : 'default'\n }\n onBlur={leftOf(line)}\n onChangeText={changedOf(line)}\n onFocus={inputFocusedOf(line)}\n ref={inputOf(line)}\n selection={AFTER_SENTINEL}\n spellCheck={false}\n style={styles.input}\n value={SENTINEL}\n />\n )}\n </FieldSegments>\n )\n}\n\n// Steps a segment, as an arrow key or a swipe does, which starts what is\n// typed into it again. Whether it changed the value.\nfunction stepBy(\n state: DateFieldState,\n segment: DateSegment,\n by: Step,\n entered: RefObject<string>,\n): boolean {\n if (state.isDisabled || state.isReadOnly) {\n return false\n }\n\n entered.current = ''\n state[by](segment.type)\n return true\n}\n\nfunction stepKey(line: SegmentLineProps, segment: DateSegment, by: Step) {\n const changed = stepBy(line.state, segment, by, line.entered)\n\n // A Gregorian era is drawn only while it is BC, so a step, which can only\n // take it to AD, takes the segment away, and focus with it where it is the\n // segment in focus. A screen reader's swipe moves no focus of ours, and\n // raises no keyboard.\n if (\n changed &&\n segment.type === 'era' &&\n line.active === 'era' &&\n hidesEra(line.state, 'AD')\n ) {\n movesFrom(line, 'era').away()\n }\n edited(line, changed)\n}\n\nfunction textStyleOf(\n own: ReturnType<typeof segmentStylesOf>,\n segment: DateSegment,\n focused: boolean,\n isDisabled: boolean,\n) {\n if (isDisabled) {\n return own.textDisabled\n }\n\n if (focused) {\n return own.textFocused\n }\n\n return segment.isPlaceholder ? own.textMuted : own.text\n}\n\n// Whether a person types into `segment`: one they can edit, which the\n// drawing, where there is one, draws.\nfunction typedInto(drawing: SegmentDrawing | undefined, segment: DateSegment) {\n return segment.isEditable && drawn(drawing, segment)\n}\n\n// Types `key` into a segment, as React Aria's segment takes a key typed into\n// it, and moves on once the segment can take no more. Whether it changed the\n// value.\nfunction typeInto(\n state: DateFieldState,\n segment: DateSegment,\n key: string,\n locale: string,\n entered: RefObject<string>,\n moves: Moves,\n): boolean {\n if (state.isDisabled || state.isReadOnly) {\n return false\n }\n\n const startsWith = startsWithIn(locale)\n\n switch (segment.type) {\n case 'day':\n case 'hour':\n case 'minute':\n case 'month':\n case 'second':\n case 'year': {\n const parser = new NumberParser(locale, { maximumFractionDigits: 0 })\n const typed = entered.current + key\n\n if (!parser.isValidPartialNumber(typed)) {\n return false\n }\n\n const number = parser.parse(typed)\n\n if (Number.isNaN(number)) {\n return false\n }\n\n const { maxValue } = segment\n const over = maxValue !== undefined && number > maxValue\n\n // A number past the segment's largest starts again from the key alone,\n // so 13 in a month is a 3.\n state.setSegment(segment.type, over ? parser.parse(key) : number)\n\n if (\n maxValue !== undefined &&\n (Number(`${number}0`) > maxValue ||\n typed.length >= String(maxValue).length)\n ) {\n entered.current = ''\n moves.next()\n } else {\n entered.current = typed\n }\n return true\n }\n case 'dayPeriod': {\n const [am, pm] = dayPeriodsOf(locale)\n\n if (startsWith(am, key)) {\n state.setSegment('dayPeriod', 0)\n } else if (startsWith(pm, key)) {\n state.setSegment('dayPeriod', 1)\n } else {\n return false\n }\n moves.next()\n return true\n }\n case 'era': {\n const matched = erasOf(state.calendar, locale).find((era) =>\n startsWith(era.formatted, key),\n )\n\n if (matched === undefined) {\n return false\n }\n state.setSegment('era', matched.era)\n\n if (hidesEra(state, matched.era)) {\n moves.away()\n } else {\n moves.next()\n }\n return true\n }\n case 'literal':\n case 'timeZoneName': {\n break\n }\n }\n\n // A literal and a time zone are written by the locale and the value, and\n // nothing typed reaches them.\n return false\n}\n\nfunction typeKey(line: SegmentLineProps, segment: DateSegment, key: string) {\n edited(\n line,\n typeInto(\n line.state,\n segment,\n key,\n line.locale,\n line.entered,\n movesFrom(line, segment.type),\n ),\n )\n}\n\n// The date or the time a field holds, written out, which describes the\n// field after its segments, as React Aria describes it. Nothing while the\n// field is empty.\nfunction valueOf(state: DateFieldState, words: LibraryMessages['segments']) {\n if (state.value === null) {\n return ''\n }\n\n const written = state.formatValue({ month: 'long' })\n\n return state.maxGranularity === 'hour'\n ? words.selectedTime.replace('{time}', written)\n : words.selectedDate.replace('{date}', written)\n}\n\n// What a segment's value reads as, as React Aria writes it: a month with its\n// name beside its number, an hour with its day period, and an empty segment\n// as empty.\nfunction valueTextOf(\n segment: DateSegment,\n state: DateFieldState,\n locale: string,\n empty: string,\n) {\n if (segment.isPlaceholder) {\n return empty\n }\n\n const { hour12, timeZone } = state.dateFormatter.resolvedOptions()\n\n if (segment.type === 'month') {\n const month = new DateFormatter(locale, { month: 'long', timeZone }).format(\n state.dateValue,\n )\n return month === segment.text ? month : `${segment.text} – ${month}`\n }\n\n if (segment.type === 'hour') {\n return new DateFormatter(locale, {\n hour: 'numeric',\n hour12,\n timeZone,\n }).format(state.dateValue)\n }\n\n return segment.text\n}\n\n// What a segment takes under React Native Web: focus, and the keys a browser\n// hands it.\nfunction webPropsOf(\n line: SegmentLineProps,\n segment: DateSegment,\n): WebSegmentProps {\n const moves = movesFrom(line, segment.type)\n const step = (by: Step) => () => {\n stepKey(line, segment, by)\n }\n const erase = () => {\n eraseKey(line, segment)\n }\n // The arrow keys move along the line as it reads, so left is the next\n // segment in a right-to-left page.\n const keys = new Map<string, () => void>([\n ['ArrowDown', step('decrement')],\n ['ArrowLeft', I18nManager.isRTL ? moves.next : moves.previous],\n ['ArrowRight', I18nManager.isRTL ? moves.previous : moves.next],\n ['ArrowUp', step('increment')],\n ['Backspace', erase],\n ['Delete', erase],\n ['End', step('incrementToMax')],\n ['Home', step('decrementToMin')],\n ['PageDown', step('decrementPage')],\n ['PageUp', step('incrementPage')],\n ])\n\n return {\n // Focus moving to another segment stays in the field, and only focus\n // leaving the segments altogether is the field's blur.\n onBlur: (event) => {\n const to = relatedTargetOf(event.nativeEvent)\n if (![...line.nodes.current.values()].some((node) => node === to)) {\n leftOf(line)()\n }\n },\n onFocus: () => {\n line.entered.current = ''\n line.setActive(segment.type)\n arrivedIn(line)\n },\n onKeyDown: (event) => {\n const { altKey, ctrlKey, key, metaKey } = event.nativeEvent\n const handler = keys.get(key)\n\n if (handler !== undefined) {\n event.preventDefault()\n handler()\n return\n }\n\n // A key that types one character, rather than one held with a key that\n // makes it a shortcut, is typed into the segment.\n const point = key.codePointAt(0)\n\n if (\n point !== undefined &&\n String.fromCodePoint(point) === key &&\n !altKey &&\n !ctrlKey &&\n !metaKey\n ) {\n event.preventDefault()\n typeKey(line, segment, key)\n }\n },\n }\n}\n\n// What a browser reads off a segment that React Native has no prop for.\nfunction webStateOf(isInvalid: boolean, state: DateFieldState) {\n if (Platform.OS !== 'web') {\n return undefined\n }\n\n return {\n ...(isInvalid ? { 'aria-invalid': true } : undefined),\n ...(state.isReadOnly ? { 'aria-readonly': true } : undefined),\n ...(state.isRequired ? { 'aria-required': true } : undefined),\n }\n}\n\nexport { DateSegments }\nexport type { DateSegmentsProps, SegmentDrawing, SegmentsHandle }\n"],"mappings":";;;;;;;;;;;;;;AAuNA,MAAMyF,aAAiD,CACrD,EAAEC,MAAM,YAAY,GACpB,EAAEA,MAAM,YAAY,CAAC;AAKvB,MAAMC,YAAY;AAIlB,MAAMC,WAAW;AAGjB,MAAMC,iBAAiB;CAAEC,KAAKF;CAAiBI,OAAOJ;AAAgB;AAGtE,MAAMK,0BAAU,IAAIC,IAAqB;CACvC;CACA;CACA;CACA;CACA;CACA;AAAM,CACP;AAED,MAAMC,SAASrE,WAAWsE,OAAO;CAG/BrB,OAAO;EACLsB,QAAQ;EACRC,SAAS;EACTC,UAAU;EACVP,OAAO;EACPQ,KAAK;EACLC,OAAO;CACT;CAGAC,UAAU,EACRC,SAAS,OACX;AACF,CAAC;AAGD,SAASC,SAASC,MAAwBC,SAAsB;CAC9D,QAAQC,UAAoC;EAC1C,MAAM,EAAEC,eAAeD,MAAME;EAC7B,IAAID,eAAe,eAAeA,eAAe,aAC/CE,QAAQL,MAAMC,SAASE,UAAU;CAErC;AACF;AAIA,SAASG,UAAU,EAAEnC,QAAQvB,WAA6B;CACxD,IAAI,CAACuB,OAAOoC,SAAS;EACnBpC,OAAOoC,UAAU;EACjB3D,UAAU;CACZ;AACF;AAIA,SAAS4D,UAAUR,MAAwB;CACzC,QAAQlC,SAAiB;EACvB,MAAMmC,UAAUD,KAAKhD,MAAMyD,SAASC,MACjCC,SAASA,KAAKnE,SAASwD,KAAKhC,MAC/B;EAEA,IAAIiC,YAAYW,KAAAA,GACd;EAGF,IAAI9C,KAAKoB,SAASH,GAAiB;GACjC8B,SAASb,MAAMC,OAAO;GACtB;EACF;EAKA,MAAMa,QAAQhD,KAAKiD,QAAQhC,UAAU,EAAE,CAAC,CAACiC,YAAY,CAAC;EAEtD,IAAIF,UAAUF,KAAAA,GACZK,QAAQjB,MAAMC,SAASiB,OAAOC,cAAcL,KAAK,CAAC;CAEtD;AACF;AAIA,SAASM,mBAAmBC,OAA0B;CACpD,MAAMC,SAASD,MAAME,SAAS;CAC9B,MAAMC,QAAQF,OAAOG,GAAG,CAAC,KAAK;CAC9B,MAAMC,OAAOJ,OAAOG,GAAG,EAAE,KAAK;CAC9B,IAAIvC,SAAS;CAEb,OAAOA,SAASsC,MAAMtC,UAAUsC,MAAMtC,YAAYwC,KAAKxC,SACrDA;CAGF,OAAOA;AACT;;;;;;;AAQA,SAAAyC,aAAAC,IAAA;CAAA,MAAAC,IAAAC,EAAA,EAAA;CAAA,IAAAvF;CAAA,IAAAwF;CAAA,IAAAjF;CAAA,IAAA+E,EAAA,OAAAD,IAAA;EAAsB,CAAA,CAAArF,gBAAAO,KAAA,GAAAiF,SAAAH;EAAoDC,EAAA,KAAAD;EAAAC,EAAA,KAAAtF;EAAAsF,EAAA,KAAAE;EAAAF,EAAA,KAAA/E;CAAA,OAAA;EAAAP,iBAAAsF,EAAA;EAAAE,QAAAF,EAAA;EAAA/E,MAAA+E,EAAA;CAAA;CACxE,MAAA,CAAA7D,QAAAM,aAA4B3D,SAAiC,IAAI;CAGjE,MAAAsD,UAAgBvD,OAAO,EAAE;CAGzB,MAAAyD,SAAezD,OAAO,KAAK;CAC3B,MAAAwD,QAAcxD,OAAuC,IAAI;CAAC,IAAAsH;CAAA,IAAAH,EAAA,OAAAI,OAAAC,IAAA,2BAAA,GAAA;EAErCF,qBAAA,IAAI3D,IAAmC;EAACwD,EAAA,KAAAG;CAAA,OAAAA,KAAAH,EAAA;CAA7D,MAAAzD,QAAc1D,OAAOsH,EAAwC;CAC7D,MAAA,EAAA/F,SAAAe,UAA2B+E;CAAK,IAAAI;CAAA,IAAAN,EAAA,OAAAtF,gBAAA;EACI4F,MAAA3F,SAAA;GAClCD,iBAAiBC,IAAI;EAAC;EACvBqF,EAAA,KAAAtF;EAAAsF,EAAA,KAAAM;CAAA,OAAAA,KAAAN,EAAA;CAFD,MAAAO,eAAqB7H,eAAe4H,EAEnC;CAAC,IAAAE;CAAA,IAAAR,EAAA,OAAA7D,UAAA6D,EAAA,OAAAO,cAAA;EAEQC,WAAA;GACRD,aAAapE,MAAM;EAAC;EACrB6D,EAAA,KAAA7D;EAAA6D,EAAA,KAAAO;EAAAP,EAAA,KAAAQ;CAAA,OAAAA,KAAAR,EAAA;CAAA,IAAAS;CAAA,IAAAT,EAAA,QAAA7D,QAAA;EAAEsE,KAAA,CAACtE,MAAM;EAAC6D,EAAA,MAAA7D;EAAA6D,EAAA,MAAAS;CAAA,OAAAA,KAAAT,EAAA;CAFXvH,UAAU+H,IAEPC,EAAQ;CAAC,IAAAC;CAAA,IAAAV,EAAA,QAAA5F,WAAA4F,EAAA,QAAA7E,OAAA;EAEauF,YAAO;GAAAC,aACvB;IACL,MAAAhB,QAAcxE,MAAKyD,SAASC,MAAMT,YAChCwC,UAAUxG,SAASgE,OAAO,CAC5B;IACA,IAAI,CAAC9B,OAAMoC,WAAYiB,UAAUZ,KAAAA,GAC/B8B,QAAQ;KAAAzE;KAAAC;KAAAE;KAAAE;KAAAtB;IAA0C,GAAGwE,MAAKhF,IAAK;GAChE;GACF+B,iBACU;IACT,MAAAmD,OAAa1E,MAAKyD,SAASkC,UAAUC,cACnCH,UAAUxG,SAASgE,SAAO,CAC5B;IACA,IAAIyB,SAASd,KAAAA,GACX8B,QAAQ;KAAAzE;KAAAC;KAAAE;KAAAE;KAAAtB;IAA0C,GAAG0E,KAAIlF,IAAK;GAC/D;GACFgC,UACQqE,QAAApE,aAAA;IACPiE,QAAQ;KAAAzE;KAAAC;KAAAE;KAAAE;KAAAtB;IAA0C,GAAGR,QAAMiC,QAAQ;GAAC;EAExE;EAAEoD,EAAA,MAAA5F;EAAA4F,EAAA,MAAA7E;EAAA6E,EAAA,MAAAU;CAAA,OAAAA,KAAAV,EAAA;CApBFpH,oBAAoBqC,KAAKyF,EAoBvB;CAAC,IAAAO;CAAA,IAAAjB,EAAA,QAAA7D,UAAA6D,EAAA,QAAAE,OAAA;EAGDe,KAAA,oBAAC,aAAD;GAAY,GACNf;GACI/D;GACCC;GACFC;GACCC;GACDC;GACIE;EAAS,CAAA;EACpBuD,EAAA,MAAA7D;EAAA6D,EAAA,MAAAE;EAAAF,EAAA,MAAAiB;CAAA,OAAAA,KAAAjB,EAAA;CAAA,OARFiB;AAQE;AAMN,SAASC,aAAazG,QAA2C;CAC/D,MAAM0G,YAAY,IAAI5I,cAAckC,QAAQ;EAAE2G,MAAM;EAAWC,QAAQ;CAAK,CAAC;CAC7E,MAAMC,YAAYC,UAAkB;EAClC,MAAMC,uBAAO,IAAIC,KAAK;EACtBD,KAAKE,SAASH,KAAK;EACnB,OACEJ,UAAUQ,cAAcH,IAAI,CAAC,CAAC3C,MAAM+C,SAASA,KAAKjH,SAAS,WAAW,CAAC,EACnEkH,SAAS;CAEjB;CAEA,OAAO,CAACP,SAAS,CAAC,GAAGA,SAAS,EAAE,CAAC;AACnC;AAKA,SAASQ,MAAM1H,SAAqCgE,SAAsB;CACxE,IAAIhE,YAAY2E,KAAAA,GACd,OAAO;CAGT,OAAOX,QAAQzD,SAAS,YACpByD,QAAQnC,KAAK8F,WAAW9E,WAAW,EAAE,MAAM,KAC3C7C,QAAQ0B,MAAMkG,IAAI5D,QAAQzD,IAAI;AACpC;AAEA,SAASsH,OAAO,EAAEnH,UAA4BoH,SAAkB;CAC9D,IAAIA,SACFpH,SAAS;AAEb;AAKA,SAASqH,UACPhH,OACAiD,SACA3D,QACA2B,SACAgG,OACS;CACT,IAAIjH,MAAMkH,cAAclH,MAAMmH,YAC5B,OAAO;CAGT,IAAIlE,QAAQnC,SAASmC,QAAQmE,aAC3BH,MAAM1G,SAAS;CAGjB,MAAM8G,SAAS,IAAI3I,aAAaY,QAAQ,EAAEgI,uBAAuB,EAAE,CAAC;CAEpE,IAAID,OAAOE,qBAAqBtE,QAAQnC,IAAI,KAAK,CAACmC,QAAQuE,eAAe;EACvE,MAAMC,YAAYxE,QAAQnC,KAAK4G,MAAM,GAAG,EAAE;EAC1C,MAAMC,SAASN,OAAOO,MAAMH,SAAS;EACrC,MAAMI,OAAOF,WAAW,IAAI,KAAKF;EAEjC,IAAII,SAAS,IACX7H,MAAM8H,aAAa7E,QAAQzD,IAAI;OAE/BQ,MAAM+H,WAAW9E,QAAQzD,MAAMmI,MAAM;EAEvC1G,QAAQsC,UAAUsE;EAClB,OAAO;CACT;CAEA,IAAI5E,QAAQzD,SAAS,eAAeyD,QAAQzD,SAAS,OAAO;EAC1DQ,MAAM8H,aAAa7E,QAAQzD,IAAI;EAC/B,OAAO;CACT;CAEA,OAAO;AACT;AAEA,SAASqE,SAASb,MAAwBC,SAAsB;CAC9D6D,OACE9D,MACAgE,UACEhE,KAAKhD,OACLiD,SACAD,KAAK1D,QACL0D,KAAK/B,SACL+G,UAAUhF,MAAMC,QAAQzD,IAAI,CAC9B,CACF;AACF;AAKA,SAASyI,OAAOC,UAAoB5I,QAAgB;CAClD,MAAM0G,YAAY,IAAI5I,cAAckC,QAAQ;EAC1C6I,KAAK;EACLC,UAAU;EACVC,MAAM;CACR,CAAC;CACD,MAAM7D,QAAQnH,WAAW,IAAIF,aAAa,GAAG,GAAG,CAAC,GAAG+K,QAAQ;CAC5D,MAAMI,OAAOJ,SAASK,QAAQ,CAAC,CAACC,KAAKL,QAAQ;EAC3C,MAAM9B,OAAO7B,MAAMiE,IAAI;GAAEC,KAAK;GAAGP;GAAKQ,OAAO;GAAGN,MAAM;EAAE,CAAC,CAAC,CAACO,OAAO,KAAK;EAEvE,OAAO;GACLT;GAEAU,WACE7C,UAAUQ,cAAcH,IAAI,CAAC,CAAC3C,MAAM+C,SAASA,KAAKjH,SAAS,KAAK,CAAC,EAC7DkH,SAASyB;EACjB;CACF,CAAC;CACD,MAAMW,SAAS1E,mBAAmBkE,KAAKE,KAAKL,QAAQA,IAAIU,SAAS,CAAC;CAElE,OAAOP,KAAKE,KAAK,EAAEL,KAAKU,iBAAiB;EACvCV;EACAU,WAAWA,UAAUnB,MAAMoB,MAAM;CACnC,EAAE;AACJ;AAOA,SAASpD,QACP,EAAEzE,SAASC,OAAOE,OAAOE,WAAWtB,SACpCR,MACAiC,WAAW,MACX;CACAR,QAAQsC,UAAU;CAElB,IAAIxF,SAASgL,OAAO,OAAO;EACzB3H,MAAMmC,QAAQyF,IAAIxJ,IAAI,CAAC,EAAEgG,MAAM;EAC/B;CACF;CAEA,IAAI,CAAC/D,UAAU;EACbH,UAAU9B,IAAI;EACd0B,MAAMqC,SAAS0F,KAAK;EACpB;CACF;CAEA,IAAIjJ,MAAMmH,YACR;CAGF7F,UAAU9B,IAAI;CACd0B,MAAMqC,SAASiC,MAAM;AACvB;AAIA,SAAS0D,SAASlJ,OAAuBmI,KAAa;CACpD,OAAOnI,MAAMkI,SAASiB,eAAe,aAAahB,QAAQ;AAC5D;AAIA,SAASiB,eAAepG,MAAwB;CAC9C,aAAa;EACX,MAAMwB,QACJxB,KAAKhD,MAAMyD,SAASC,MAAMT,YAAYwC,UAAUzC,KAAK/D,SAASgE,OAAO,CAAC,CAAC,EACnEzD,QAAQ;EACdwD,KAAK1B,WAAWiC,YAAYA,WAAWiB,KAAK;EAC5ClB,UAAUN,IAAI;CAChB;AACF;AAGA,SAASqG,QAAQ,EAAEnI,SAA2B;CAC5C,QAAQoI,SAAgD;EACtDpI,MAAMqC,UAAU+F;CAClB;AACF;AAIA,SAASC,OAAO,EACdtI,SACAE,QACAzB,QACA4B,WACAtB,SACmB;CACnB,aAAa;EACXmB,OAAOoC,UAAU;EACjBtC,QAAQsC,UAAU;EAClBjC,UAAU,IAAI;EACdtB,MAAMwJ,mBAAmB;EACzB9J,SAAS;CACX;AACF;AAMA,SAASsI,UAAUhF,MAAwBxD,MAA8B;CACvE,MAAMiK,WAAWzG,KAAKhD,MAAMyD,SAASiG,QAAQzG,YAC3CwC,UAAUzC,KAAK/D,SAASgE,OAAO,CACjC;CACA,MAAMwB,KAAKgF,SAASE,WAAW1G,YAAYA,QAAQzD,SAASA,IAAI;CAChE,MAAMoK,MAAMC,OAAeC,iBAA8B;EACvD,MAAM7G,UAAU4G,QAAQ,IAAIjG,KAAAA,IAAY6F,SAAShF,GAAGoF,KAAK;EACzD,IAAI5G,YAAYW,KAAAA,GACdkG,SAAS;OAETpE,QAAQ1C,MAAMC,QAAQzD,IAAI;CAE9B;CAEA,OAAO;EACLa,MAAMuJ,GAAGnF,KAAK,IAAIA,KAAK,IAAIA,KAAK,CAAC;EACjCnE,MAAMsJ,GAAGnF,KAAK,GAAGzB,KAAKnD,SAAS;EAC/BU,UAAUqJ,GAAGnF,KAAK,GAAGzB,KAAKvD,aAAa;CACzC;AACF;AAIA,SAASsK,OACPvK,MAIA;CACA,OAAOA,SAAS,YAAY,QAAQA;AACtC;AAIA,SAASwK,OAAO,EAAE5I,SAA2B5B,MAAuB;CAClE,QAAQ8J,SAA8B;EACpC,IAAIA,SAAS,MACX;EAGFlI,MAAMmC,QAAQkF,IAAIjJ,MAAM8J,IAAI;EAC5B,aAAa;GACXlI,MAAMmC,QAAQ0G,OAAOzK,IAAI;EAC3B;CACF;AACF;AAKA,SAAS0K,QAAQlH,MAAwBxD,MAAuB;CAC9D,aAAa;EACXkG,QAAQ1C,MAAMxD,MAAMwD,KAAK/D,SAAS4B,kBAAkB,IAAI;CAC1D;AACF;AAGA,SAASsJ,gBAAgBjH,OAAyB;CAChD,OAAO,OAAOA,UAAU,YAAYA,UAAU,QAAQ,mBAAmBA,QACrEA,MAAMkH,gBACNxG,KAAAA;AACN;AAGA,SAAAyG,YAAArH,MAAA;CAAA,MAAA6B,IAAAC,EAAA,EAAA;CACE,MAAA,EAAA9D,QAAAhC,WAAAC,SAAAG,WAAAC,OAAAC,QAAAU,UAAwEgD;CACxE,MAAAsH,KAAW9M,MAAM;CACjB,MAAA+M,QAAc5L,SAAS;CACvB,MAAA6L,MAAY1L,gBAAgByL,KAAK;CACjC,MAAAE,OAAa5L,YAAY,WAAW;CACpC,MAAA6L,QAAcjM,YAAYa,MAAM,CAAC,CAAAmE;CAAS,IAAAmB;CAAA,IAAAC,EAAA,OAAA5F,WAAA4F,EAAA,OAAA7E,MAAAyD,UAAA;EAAA,IAAAuB;EAAA,IAAAH,EAAA,OAAA5F,SAAA;GACR+F,MAAA/B,YAAawC,UAAUxG,SAASgE,OAAO;GAAC4B,EAAA,KAAA5F;GAAA4F,EAAA,KAAAG;EAAA,OAAAA,KAAAH,EAAA;EAA5DD,KAAA5E,MAAKyD,SAASC,KAAMsB,EAAwC;EAACH,EAAA,KAAA5F;EAAA4F,EAAA,KAAA7E,MAAAyD;EAAAoB,EAAA,KAAAD;CAAA,OAAAA,KAAAC,EAAA;CAA3E,MAAAL,QAAcI;CACd,MAAA8B,QAAc1D,KAAI7D,WAAYwL,QAAQ3K,OAAO0K,KAAK;CAClD,MAAAE,UAAgB,GAAGN,GAAE;CACrB,MAAA3J,QACE+F,UAAU,KAAV1H,YAAA,CAA4B;EAAAsL,IAAMM;EAAO9J,MAAQ4F;CAAM,GAAC,GAAK1H,SAAS;CACxE,MAAA6L,UAAgB,CAAC7K,MAAKkH,cAAN,CAAsBlH,MAAKmH;CAGxC,MAAA2D,KAAAtM;CACE,MAAAwG,KAAAhF,MAAKyD,SAAS+E,KAAK5C,WAAAiE,UAAA;EAClB,IAAI,CAAClD,MAAM1H,SAASgE,SAAO,GAAC,OACnB;EAGT,IAAI,CAACA,UAAO8H,YAAW,OAEnB,oBAACmD,MAAD;GACe,eAAAjL,UAAOzD,SAAU;GAM5B,OAAAP,YAAY2E,KAAAA,IACRhF,cACE6L,MACAxH,UAAOzD,SAAU,YAAjBoE,KAAAA,IAAyC4G,IAAGvH,SAC5CjD,MAAKkH,aACDsD,IAAGQ,eACH/H,UAAOzD,SAAU,YACfgL,IAAGS,YACHT,IAAG1J,IAEG,IAAd7B,QAAOyB;GAGZuC,UAAAA,UAAOnC;EApBC,GAKJ,GAAGmC,UAAOzD,KAAK,GAAIqK,OALf;EAyBf,MAAAqB,UAAgBjI,UAAOzD,SAAUwB;EAGjC,MAAAmK,YAAkB/L,aAAa6D,UAAOzD,SAAUgF,OAAKhF;EAAM,OAGzD,8BAAC,WAAD;GAAU,GACHzB,SAAQgL,OAAQ,QAAQqC,WAAWpI,MAAMC,SAAmB,IAA5DW,KAAAA;GAA6D,GAC7DuH,YAAY5M,cAAcoC,KAAiB,IAA3CiD,KAAAA;GAA4C,GAC7CyH,WAAWjM,WAAWY,KAAK;GACT,sBAAA6K,UAAAjJ,aAAAgC,KAAAA;GACH,mBAAA7F,SAAQgL,OAAQ,QAAhBnF,KAAAA,IAAA;GACJ,iBAAA5D,MAAKkH;GACR,cAAA,GAAGwD,MAAMX,OAAO9G,UAAOzD,IAAK,GAAE,IAAKH;GAChC,iBAAA4D,UAAOqI;GACP,iBAAArI,UAAOsI;GACP,iBAAAtI,UAAOyD,SAAP9C,KAAAA;GACC,kBAAA4H,YAAYvI,WAASjD,OAAOV,QAAQoL,MAAKe,KAAM;GACrD,UAAAzL,MAAKkH;GACV,KAAAjE,UAAOzD;GACW,uBAAAuD,SAASC,MAAMC,SAAO;GAE3C,SAAAlF,SAAQgL,OAAQ,QAAhBnF,KAAAA,IAAoCsG,QAAQlH,MAAMC,UAAOzD,IAAK;GAE3D,KAAAwK,OAAOhH,MAAMC,UAAOzD,IAAK;GACxB,MAAAzB,SAAQgL,OAAQ,QAAhB,eAAAnF,KAAAA;GAEJ,OAAA3E,YAAY2E,KAAAA,IACRhF,cACE4L,IAAGvH,SACHiI,UAAUV,IAAGkB,iBAAb9H,KAAAA,CAE+B,IAAjC3E,QAAOuB,IAAKyC,UAAOzD,MAAO0L,OAAO;EA1B/B,GA6BR,oBAACgD,MAAD;GAEI,OAAAjP,YAAY2E,KAAAA,IACRhF,cACE6L,MACAkB,YAAYnB,KAAKvH,WAASiI,SAASlL,MAAKkH,UAAW,CAEnB,IAAlCjI,QAAO6B,KAAMmC,UAAOzD,MAAO0L,OAAO;GAGvCjI,UAAAA,UAAOnC;EAVC,CAAA,CA7BH;CAyCE,CAEf;CAAC,IAAAqE;CAAA,IAAAN,EAAA,OAAA7D,UAAA6D,EAAA,OAAAgG,WAAAhG,EAAA,OAAA7B,QAAA6B,EAAA,OAAA6B,SAAA7B,EAAA,OAAA+F,SAAA;EACDzF,KAAApH,SAAQgL,OAAQ,QACfrC,UAAU,KAAV,OACE,oBAACwH,MAAD;GAAgBtD,IAAAA;GAAgB,OAAAtI,OAAMO;GACnC6D,UAAAA;EADQ,CAAA,IAKb,oBAAC,WAAD;GACE,eAAA;GACe,gBAAA;GACF,cAAA;GACA,aAAA;GACb,aAAA;GACA,mBAAA;GACUmE,UAAAA;GACW,sBAAA;GAEnB,cAAA7J,WAAW,QAAQoB,QAAOyE,IAAK7F,MAAM,IAArC,eAAA;GAEM,QAAAuI,OAAOvG,IAAI;GACL,cAAAQ,UAAUR,IAAI;GACnB,SAAAoG,eAAepG,IAAI;GACvB,KAAAqG,QAAQrG,IAAI;GACNhB,WAAAA;GACC,YAAA;GACL,OAAAM,OAAMpB;GACNa,OAAAA;EAAQ,CAAA;EAElB8C,EAAA,KAAA7D;EAAA6D,EAAA,KAAAgG;EAAAhG,EAAA,KAAA7B;EAAA6B,EAAA,KAAA6B;EAAA7B,EAAA,KAAA+F;EAAA/F,EAAA,MAAAM;CAAA,OAAAA,KAAAN,EAAA;CAAA,IAAAQ;CAAA,IAAAR,EAAA,QAAAiG,MAAAjG,EAAA,QAAAG,MAAAH,EAAA,QAAAM,IAAA;EA/GHE,KAAA,qBAAC,IAAD,EAAA,UAAA,CACGL,IAkFAG,EAnFW,EAAA,CAAA;EAgHEN,EAAA,MAAAiG;EAAAjG,EAAA,MAAAG;EAAAH,EAAA,MAAAM;EAAAN,EAAA,MAAAQ;CAAA,OAAAA,KAAAR,EAAA;CAAA,OAhHhBQ;AAgHgB;AAMpB,SAASuG,OACP5L,OACAiD,SACA4I,IACA5K,SACS;CACT,IAAIjB,MAAMkH,cAAclH,MAAMmH,YAC5B,OAAO;CAGTlG,QAAQsC,UAAU;CAClBvD,MAAM6L,GAAG,CAAC5I,QAAQzD,IAAI;CACtB,OAAO;AACT;AAEA,SAAS6D,QAAQL,MAAwBC,SAAsB4I,IAAU;CACvE,MAAM9E,UAAU6E,OAAO5I,KAAKhD,OAAOiD,SAAS4I,IAAI7I,KAAK/B,OAAO;CAM5D,IACE8F,WACA9D,QAAQzD,SAAS,SACjBwD,KAAKhC,WAAW,SAChBkI,SAASlG,KAAKhD,OAAO,IAAI,GAEzBgI,UAAUhF,MAAM,KAAK,CAAC,CAAC3C,KAAK;CAE9ByG,OAAO9D,MAAM+D,OAAO;AACtB;AAEA,SAAS4E,YACPnB,KACAvH,SACAiI,SACAhE,YACA;CACA,IAAIA,YACF,OAAOsD,IAAIQ;CAGb,IAAIE,SACF,OAAOV,IAAIuB;CAGb,OAAO9I,QAAQuE,gBAAgBgD,IAAIS,YAAYT,IAAI1J;AACrD;AAIA,SAAS2E,UAAUxG,SAAqCgE,SAAsB;CAC5E,OAAOA,QAAQ8H,cAAcpE,MAAM1H,SAASgE,OAAO;AACrD;AAKA,SAAS+I,SACPhM,OACAiD,SACAgJ,KACA3M,QACA2B,SACAgG,OACS;CACT,IAAIjH,MAAMkH,cAAclH,MAAMmH,YAC5B,OAAO;CAGT,MAAM+E,aAAa5N,aAAagB,MAAM;CAEtC,QAAQ2D,QAAQzD,MAAhB;EACE,KAAK;EACL,KAAK;EACL,KAAK;EACL,KAAK;EACL,KAAK;EACL,KAAK,QAAQ;GACX,MAAM6H,SAAS,IAAI3I,aAAaY,QAAQ,EAAEgI,uBAAuB,EAAE,CAAC;GACpE,MAAM6E,QAAQlL,QAAQsC,UAAU0I;GAEhC,IAAI,CAAC5E,OAAOE,qBAAqB4E,KAAK,GACpC,OAAO;GAGT,MAAMC,SAAS/E,OAAOO,MAAMuE,KAAK;GAEjC,IAAIE,OAAOC,MAAMF,MAAM,GACrB,OAAO;GAGT,MAAM,EAAEd,aAAarI;GACrB,MAAMsJ,OAAOjB,aAAa1H,KAAAA,KAAawI,SAASd;GAIhDtL,MAAM+H,WAAW9E,QAAQzD,MAAM+M,OAAOlF,OAAOO,MAAMqE,GAAG,IAAIG,MAAM;GAEhE,IACEd,aAAa1H,KAAAA,MACZyI,OAAO,GAAGD,OAAM,EAAG,IAAId,YACtBa,MAAMjK,UAAUgC,OAAOoH,QAAQ,CAAC,CAACpJ,SACnC;IACAjB,QAAQsC,UAAU;IAClB0D,MAAM3G,KAAK;GACb,OACEW,QAAQsC,UAAU4I;GAEpB,OAAO;EACT;EACA,KAAK,aAAa;GAChB,MAAM,CAACK,IAAIC,MAAM1G,aAAazG,MAAM;GAEpC,IAAI4M,WAAWM,IAAIP,GAAG,GACpBjM,MAAM+H,WAAW,aAAa,CAAC;QAC1B,IAAImE,WAAWO,IAAIR,GAAG,GAC3BjM,MAAM+H,WAAW,aAAa,CAAC;QAE/B,OAAO;GAETd,MAAM3G,KAAK;GACX,OAAO;EACT;EACA,KAAK,OAAO;GACV,MAAMoM,UAAUzE,OAAOjI,MAAMkI,UAAU5I,MAAM,CAAC,CAACoE,MAAMyE,QACnD+D,WAAW/D,IAAIU,WAAWoD,GAAG,CAC/B;GAEA,IAAIS,YAAY9I,KAAAA,GACd,OAAO;GAET5D,MAAM+H,WAAW,OAAO2E,QAAQvE,GAAG;GAEnC,IAAIe,SAASlJ,OAAO0M,QAAQvE,GAAG,GAC7BlB,MAAM5G,KAAK;QAEX4G,MAAM3G,KAAK;GAEb,OAAO;EACT;CAKF;CAIA,OAAO;AACT;AAEA,SAAS2D,QAAQjB,MAAwBC,SAAsBgJ,KAAa;CAC1EnF,OACE9D,MACAgJ,SACEhJ,KAAKhD,OACLiD,SACAgJ,KACAjJ,KAAK1D,QACL0D,KAAK/B,SACL+G,UAAUhF,MAAMC,QAAQzD,IAAI,CAC9B,CACF;AACF;AAKA,SAASmL,QAAQ3K,OAAuB0K,OAAoC;CAC1E,IAAI1K,MAAM0G,UAAU,MAClB,OAAO;CAGT,MAAMiG,UAAU3M,MAAM4M,YAAY,EAAEjE,OAAO,OAAO,CAAC;CAEnD,OAAO3I,MAAM6M,mBAAmB,SAC5BnC,MAAMoC,aAAa/I,QAAQ,UAAU4I,OAAO,IAC5CjC,MAAMqC,aAAahJ,QAAQ,UAAU4I,OAAO;AAClD;AAKA,SAASnB,YACPvI,SACAjD,OACAV,QACAmM,OACA;CACA,IAAIxI,QAAQuE,eACV,OAAOiE;CAGT,MAAM,EAAEvF,QAAQkC,aAAapI,MAAMgN,cAAcC,gBAAgB;CAEjE,IAAIhK,QAAQzD,SAAS,SAAS;EAC5B,MAAMmJ,QAAQ,IAAIvL,cAAckC,QAAQ;GAAEqJ,OAAO;GAAQP;EAAS,CAAC,CAAC,CAAC8E,OACnElN,MAAMmN,SACR;EACA,OAAOxE,UAAU1F,QAAQnC,OAAO6H,QAAQ,GAAG1F,QAAQnC,KAAI,KAAM6H;CAC/D;CAEA,IAAI1F,QAAQzD,SAAS,QACnB,OAAO,IAAIpC,cAAckC,QAAQ;EAC/B2G,MAAM;EACNC;EACAkC;CACF,CAAC,CAAC,CAAC8E,OAAOlN,MAAMmN,SAAS;CAG3B,OAAOlK,QAAQnC;AACjB;AAIA,SAASsK,WACPpI,MACAC,SACiB;CACjB,MAAMgE,QAAQe,UAAUhF,MAAMC,QAAQzD,IAAI;CAC1C,MAAM4N,QAAQvB,aAAmB;EAC/BxI,QAAQL,MAAMC,SAAS4I,EAAE;CAC3B;CACA,MAAMwB,cAAc;EAClBxJ,SAASb,MAAMC,OAAO;CACxB;CAGA,MAAMqK,uBAAO,IAAIjM,IAAwB;EACvC,CAAC,aAAa+L,KAAK,WAAW,CAAC;EAC/B,CAAC,aAAaxP,YAAY2P,QAAQtG,MAAM3G,OAAO2G,MAAM1G,QAAQ;EAC7D,CAAC,cAAc3C,YAAY2P,QAAQtG,MAAM1G,WAAW0G,MAAM3G,IAAI;EAC9D,CAAC,WAAW8M,KAAK,WAAW,CAAC;EAC7B,CAAC,aAAaC,KAAK;EACnB,CAAC,UAAUA,KAAK;EAChB,CAAC,OAAOD,KAAK,gBAAgB,CAAC;EAC9B,CAAC,QAAQA,KAAK,gBAAgB,CAAC;EAC/B,CAAC,YAAYA,KAAK,eAAe,CAAC;EAClC,CAAC,UAAUA,KAAK,eAAe,CAAC;CAAC,CAClC;CAED,OAAO;EAGL1N,SAASwD,UAAU;GACjB,MAAM0G,KAAKO,gBAAgBjH,MAAME,WAAW;GAC5C,IAAI,CAAC,CAAC,GAAGJ,KAAK5B,MAAMmC,QAAQiK,OAAO,CAAC,CAAC,CAACC,MAAMnE,SAASA,SAASM,EAAE,GAC9DL,OAAOvG,IAAI,CAAC,CAAC;EAEjB;EACApD,eAAe;GACboD,KAAK/B,QAAQsC,UAAU;GACvBP,KAAK1B,UAAU2B,QAAQzD,IAAI;GAC3B8D,UAAUN,IAAI;EAChB;EACA0K,YAAYxK,UAAU;GACpB,MAAM,EAAEyK,QAAQC,SAAS3B,KAAK4B,YAAY3K,MAAME;GAChD,MAAM0K,UAAUR,KAAKtE,IAAIiD,GAAG;GAE5B,IAAI6B,YAAYlK,KAAAA,GAAW;IACzBV,MAAM6K,eAAe;IACrBD,QAAQ;IACR;GACF;GAIA,MAAMhK,QAAQmI,IAAIjI,YAAY,CAAC;GAE/B,IACEF,UAAUF,KAAAA,KACVM,OAAOC,cAAcL,KAAK,MAAMmI,OAChC,CAAC0B,UACD,CAACC,WACD,CAACC,SACD;IACA3K,MAAM6K,eAAe;IACrB9J,QAAQjB,MAAMC,SAASgJ,GAAG;GAC5B;EACF;CACF;AACF;AAGA,SAASZ,WAAWjM,WAAoBY,OAAuB;CAC7D,IAAIjC,SAASgL,OAAO,OAClB;CAGF,OAAO;EACL,GAAI3J,YAAY,EAAE,gBAAgB,KAAK,IAAIwE,KAAAA;EAC3C,GAAI5D,MAAMmH,aAAa,EAAE,iBAAiB,KAAK,IAAIvD,KAAAA;EACnD,GAAI5D,MAAMgO,aAAa,EAAE,iBAAiB,KAAK,IAAIpK,KAAAA;CACrD;AACF"}
1
+ {"version":3,"file":"index.js","names":["Calendar","ComponentRef","Dispatch","Ref","RefObject","SetStateAction","AccessibilityActionEvent","AccessibilityActionInfo","HostInstance","PressableProps","StyleProp","TextStyle","ViewStyle","DateFieldState","DateSegment","DateSegmentType","CalendarDate","DateFormatter","toCalendar","useEffect","useEffectEvent","useId","useImperativeHandle","useRef","useState","I18nManager","Text","NativeText","Platform","Pressable","StyleSheet","TextInput","FieldDescriptionPart","Focusable","LibraryMessages","startsWithIn","descriptionOf","FieldSegments","messagesFor","NumberParser","useTheme","composeStyles","useTypeRole","segmentStylesOf","DateSegmentsProps","described","drawing","SegmentDrawing","holding","isInvalid","label","locale","onActiveChange","type","onBeforeStart","onBlur","onEdit","onFocus","onPastEnd","ref","SegmentsHandle","state","Focusing","Pick","SegmentLineProps","Moves","away","next","previous","box","isActive","literal","parts","ReadonlySet","raisesKeyboard","text","Omit","active","entered","input","inside","nodes","Map","setActive","focusLast","focusOn","keyboard","Step","WebSegmentProps","ADJUSTABLE","name","INVISIBLE","SENTINEL","AFTER_SENTINEL","end","length","start","NUMERIC","Set","styles","create","height","opacity","position","top","width","notDrawn","display","actionOf","line","segment","event","actionName","nativeEvent","stepKey","arrivedIn","current","changedOf","segments","find","each","undefined","eraseKey","point","replace","codePointAt","typeKey","String","fromCodePoint","commonPrefixLength","texts","sorted","sort","first","at","last","DateSegments","t0","$","_c","props","t1","Symbol","for","t2","reportActive","t3","t4","t5","focus","typedInto","focusTo","findLast","segment_0","type_0","t6","dayPeriodsOf","formatter","hour","hour12","periodAt","hours","date","Date","setHours","formatToParts","part","value","drawn","replaceAll","has","edited","changed","eraseFrom","moves","isDisabled","isReadOnly","placeholder","parser","maximumFractionDigits","isValidPartialNumber","isPlaceholder","shortened","slice","parsed","parse","kept","clearSegment","setSegment","movesFrom","erasOf","calendar","era","timeZone","year","eras","getEras","map","set","day","month","toDate","formatted","prefix","OS","get","blur","hidesEra","identifier","inputFocusedOf","inputOf","node","leftOf","confirmPlaceholder","editable","filter","findIndex","to","index","beyond","nameOf","nodeOf","delete","pressOf","relatedTargetOf","relatedTarget","SegmentLine","id","theme","own","role","words","valueOf","valueId","canEdit","T0","isEditable","textDisabled","textMuted","focused","describes","webPropsOf","webStateOf","maxValue","minValue","valueTextOf","empty","segmentFocused","textStyleOf","stepBy","by","ReturnType","textFocused","typeInto","key","startsWith","typed","number","Number","isNaN","over","am","pm","matched","written","formatValue","maxGranularity","selectedTime","selectedDate","dateFormatter","resolvedOptions","format","dateValue","step","erase","keys","isRTL","values","some","onKeyDown","altKey","ctrlKey","metaKey","handler","preventDefault","isRequired","_c","NativeText"],"sources":["../../src/segments/index.tsx"],"sourcesContent":["import type { Calendar } from '@internationalized/date'\nimport type {\n ComponentRef,\n Dispatch,\n Ref,\n RefObject,\n SetStateAction,\n} from 'react'\nimport type {\n AccessibilityActionEvent,\n AccessibilityActionInfo,\n HostInstance,\n PressableProps,\n StyleProp,\n TextStyle,\n ViewStyle,\n} from 'react-native'\nimport type {\n DateFieldState,\n DateSegment,\n DateSegmentType,\n} from 'react-stately/useDateFieldState'\n\nimport {\n CalendarDate,\n DateFormatter,\n toCalendar,\n} from '@internationalized/date'\nimport {\n useEffect,\n useEffectEvent,\n useId,\n useImperativeHandle,\n useRef,\n useState,\n} from 'react'\nimport {\n I18nManager,\n Text as NativeText,\n Platform,\n Pressable,\n StyleSheet,\n TextInput,\n} from 'react-native'\n\nimport type { FieldDescriptionPart } from '../field'\nimport type { Focusable } from '../form'\nimport type { LibraryMessages } from '../i18n/messages'\n\nimport { startsWithIn } from '../autocomplete'\nimport { descriptionOf, FieldSegments } from '../field'\nimport { messagesFor } from '../i18n'\nimport { NumberParser } from '../number/parser'\nimport { useTheme } from '../theme/scope'\nimport { composeStyles } from '../theme/styles'\nimport { useTypeRole } from '../typography/roles'\nimport { segmentStylesOf } from './styles'\n\n// The segments a date or a time is typed into, one part of the value each, as\n// web's src/segments draws them. React Stately's date field state decides\n// what the parts are, how many, in what order and what each may hold, from\n// the locale and the granularity, so a field built on it draws them from that\n// state rather than writing any of them out. What is here is how a person\n// types into them and how a screen reader reads them, which is React Aria's\n// useDateSegment ported, since React Aria does not run on native.\n//\n// **Typing is React Aria's, digit for digit.** A digit goes into the segment\n// after the ones typed before it, and moves on to the next segment once no\n// further digit could fit, so `9` in a month moves on and `1` waits for a\n// second. A letter picks a day period or an era by the start of its name in\n// the locale, backspace takes a digit off the end, and on an empty segment\n// moves back to the one before it.\n//\n// **On iOS and Android one hidden input takes the keys.** A view cannot raise\n// the keyboard, so a press on a segment makes it the one being typed and\n// focuses a text input no one sees or reads, which holds one space and hands\n// over each key typed after it. Its keyboard is a number pad for a segment of\n// digits and the full one for a day period or an era. A screen reader reaches\n// each segment as an adjustable element instead, which a swipe steps up or\n// down, and which opens the keyboard when activated.\n//\n// **Under React Native Web each segment is its own focus stop**, as web's\n// are, read as a spin button and typed into with the keys a browser hands\n// it: digits and letters, backspace, the arrow keys up and down to step, and\n// left and right to move between segments, which follow the direction the\n// page reads in.\n//\n// **A drawing of their own replaces a field's line**, for segments that are\n// not a field's: a box per part, the text inside it and the punctuation\n// between them, each the caller's, as a time picker's modal draws its hour\n// and minute. It names the parts it draws, and focus passes the others by,\n// so a day period a selector beside the boxes stands for is never typed into.\n// Punctuation is drawn only where it holds something to see, since a\n// locale's literals carry bidirectional marks and spaces beside it.\n\ntype DateSegmentsProps = {\n /** What describes the field after the value it holds: the line under it. */\n readonly described: readonly FieldDescriptionPart[]\n /** How the segments are drawn where they are not a field's line. */\n readonly drawing?: SegmentDrawing\n /**\n * What the segments are read as holding, after their own names: the date\n * or the time written out, unless a range picker around them reads its\n * whole range here instead. `''` reads nothing.\n */\n readonly holding?: string\n /** Whether the field shows an error, which every segment then says. */\n readonly isInvalid: boolean\n /** The field's label, which each segment's name ends in. */\n readonly label: string\n /** The locale the field writes in: its `useLocaleOf`. */\n readonly locale: string\n /**\n * Called with the segment in focus as it changes, and with `null` as focus\n * leaves them.\n */\n readonly onActiveChange?: (type: DateSegmentType | null) => void\n /**\n * Called where focus would move back from the first segment, as a\n * backspace on it does, which a range picker sends on to the start's last.\n */\n readonly onBeforeStart?: () => void\n /** Called as focus leaves the segments, once they fill in what they can. */\n readonly onBlur?: () => void\n /** Called after each edit a person makes, typed or stepped. */\n readonly onEdit?: () => void\n /** Called as focus arrives in the segments from outside them. */\n readonly onFocus?: () => void\n /**\n * Called where focus would move on from the last segment, as a full one\n * does, which a range picker sends on to the end's first.\n */\n readonly onPastEnd?: () => void\n /** What focuses the segments: the first, or the last. */\n readonly ref?: Ref<SegmentsHandle>\n readonly state: DateFieldState\n}\n\n// What moving focus to a segment reaches for.\ntype Focusing = Pick<\n SegmentLineProps,\n 'entered' | 'input' | 'nodes' | 'setActive' | 'state'\n>\n\ntype Moves = {\n // Where focus goes from a segment that stops being drawn, as React Aria's\n // goes from one it removes: the one before it, or the one after it where it\n // was the first.\n readonly away: () => void\n readonly next: () => void\n readonly previous: () => void\n}\n\n/**\n * How segments are drawn in place of a field's line of body large text, each\n * style chosen for whether its part is the one in focus.\n */\ntype SegmentDrawing = {\n /** The box a part a person types into is drawn in. */\n readonly box: (\n type: DateSegmentType,\n isActive: boolean,\n ) => StyleProp<ViewStyle>\n /** The punctuation between two parts. */\n readonly literal: StyleProp<TextStyle>\n /** The parts drawn. The rest are left out, and focus passes them by. */\n readonly parts: ReadonlySet<DateSegmentType>\n /**\n * Whether a press on a part raises the keyboard on iOS and Android, as a\n * field's does, rather than only making it the one in focus.\n */\n readonly raisesKeyboard: boolean\n /** The text inside a part's box. */\n readonly text: (\n type: DateSegmentType,\n isActive: boolean,\n ) => StyleProp<TextStyle>\n}\n\n// The segments' own props, with what the component around them keeps for\n// them: which one is being typed, what has been typed into it, whether focus\n// is among them, the hidden input and each segment's element.\ntype SegmentLineProps = Omit<DateSegmentsProps, 'ref'> & {\n readonly active: DateSegmentType | null\n readonly entered: RefObject<string>\n readonly input: RefObject<ComponentRef<typeof TextInput> | null>\n readonly inside: RefObject<boolean>\n readonly nodes: RefObject<Map<DateSegmentType, HostInstance>>\n readonly setActive: Dispatch<SetStateAction<DateSegmentType | null>>\n}\n\n/**\n * What focuses a field's segments: `focus` the first, unless focus is among\n * them already, `focusLast` the last, and `focusOn` the one of `type`, with\n * the keyboard raised on iOS and Android or put away.\n */\ntype SegmentsHandle = Focusable & {\n readonly focusLast: () => void\n readonly focusOn: (type: DateSegmentType, keyboard: boolean) => void\n}\n\n// A step a spin button takes, each one a method of the field's state.\ntype Step =\n | 'decrement'\n | 'decrementPage'\n | 'decrementToMin'\n | 'increment'\n | 'incrementPage'\n | 'incrementToMax'\n\n// What a segment is handed under React Native Web, which takes keys and focus\n// on any element.\ntype WebSegmentProps = Pick<PressableProps, 'onBlur' | 'onFocus' | 'onKeyDown'>\n\n// What a screen reader can ask of a segment: a step up, or a step down.\nconst ADJUSTABLE: readonly AccessibilityActionInfo[] = [\n { name: 'increment' },\n { name: 'decrement' },\n]\n\n// What a literal holds besides what it is drawn for: the spaces, and the\n// marks a locale sets a direction with.\nconst INVISIBLE = /[\\s\\u061C\\u200E\\u200F\\u202A-\\u202E\\u2066-\\u2069]/gu\n\n// The text the hidden input holds, which a backspace has something to take\n// from and which every key typed lands after.\nconst SENTINEL = ' '\n\n// Where the hidden input's caret stays: after the space.\nconst AFTER_SENTINEL = { end: SENTINEL.length, start: SENTINEL.length }\n\n// The segments a number is typed into, which the number pad serves.\nconst NUMERIC = new Set<DateSegmentType>([\n 'day',\n 'hour',\n 'minute',\n 'month',\n 'second',\n 'year',\n])\n\nconst styles = StyleSheet.create({\n // The input no one sees, which is there to raise the keyboard and take its\n // keys. Still laid out, since an input with no size takes no focus.\n input: {\n height: 1,\n opacity: 0,\n position: 'absolute',\n start: 0,\n top: 0,\n width: 1,\n },\n // The date written out, in the document under React Native Web for the\n // first segment to point at, and drawn nowhere.\n notDrawn: {\n display: 'none',\n },\n})\n\n// What a screen reader's swipe up or down does to a segment.\nfunction actionOf(line: SegmentLineProps, segment: DateSegment) {\n return (event: AccessibilityActionEvent) => {\n const { actionName } = event.nativeEvent\n if (actionName === 'increment' || actionName === 'decrement') {\n stepKey(line, segment, actionName)\n }\n }\n}\n\n// Where focus goes once a person is in the segments: what the field calls on\n// arriving, which it hears once however many segments focus passes through.\nfunction arrivedIn({ inside, onFocus }: SegmentLineProps) {\n if (!inside.current) {\n inside.current = true\n onFocus?.()\n }\n}\n\n// What the hidden input does with each change to its text: a shorter text is\n// a backspace, and a longer one a key typed after the space.\nfunction changedOf(line: SegmentLineProps) {\n return (text: string) => {\n const segment = line.state.segments.find(\n (each) => each.type === line.active,\n )\n\n if (segment === undefined) {\n return\n }\n\n if (text.length < SENTINEL.length) {\n eraseKey(line, segment)\n return\n }\n\n // One key at a time, the first typed after the space: a second handed\n // over in the same change would be written over by the first, since\n // both are set from the value this render holds.\n const point = text.replace(SENTINEL, '').codePointAt(0)\n\n if (point !== undefined) {\n typeKey(line, segment, String.fromCodePoint(point))\n }\n }\n}\n\n// The number of characters at the start of every one of `texts` that they\n// share, which an era's name is typed after, as React Aria finds it.\nfunction commonPrefixLength(texts: readonly string[]) {\n const sorted = [...texts].sort()\n const first = sorted.at(0) ?? ''\n const last = sorted.at(-1) ?? ''\n let length = 0\n\n while (length < first.length && first[length] === last[length]) {\n length++\n }\n\n return length\n}\n\n/**\n * A date or a time's segments, inside a field's box, from React Stately's\n * date field state: each part of the value typed or stepped on its own, the\n * one being typed drawn as a filled shape and the empty ones in their\n * placeholders, muted.\n */\nfunction DateSegments({ onActiveChange, ref, ...props }: DateSegmentsProps) {\n const [active, setActive] = useState<DateSegmentType | null>(null)\n // What has been typed into the segment in focus since it took focus, which\n // the next digit is read after.\n const entered = useRef('')\n // Whether focus is in the segments, which a press on the box around them\n // leaves where it is.\n const inside = useRef(false)\n const input = useRef<ComponentRef<typeof TextInput>>(null)\n // Each segment's element under React Native Web, which focus moves to.\n const nodes = useRef(new Map<DateSegmentType, HostInstance>())\n const { drawing, state } = props\n const reportActive = useEffectEvent((type: DateSegmentType | null) => {\n onActiveChange?.(type)\n })\n\n useEffect(() => {\n reportActive(active)\n }, [active])\n\n useImperativeHandle(ref, () => ({\n focus: () => {\n const first = state.segments.find((segment) =>\n typedInto(drawing, segment),\n )\n if (!inside.current && first !== undefined) {\n focusTo({ entered, input, nodes, setActive, state }, first.type)\n }\n },\n focusLast: () => {\n const last = state.segments.findLast((segment) =>\n typedInto(drawing, segment),\n )\n if (last !== undefined) {\n focusTo({ entered, input, nodes, setActive, state }, last.type)\n }\n },\n focusOn: (type, keyboard) => {\n focusTo({ entered, input, nodes, setActive, state }, type, keyboard)\n },\n }))\n\n return (\n <SegmentLine\n {...props}\n active={active}\n entered={entered}\n input={input}\n inside={inside}\n nodes={nodes}\n setActive={setActive}\n />\n )\n}\n\n// What the locale calls the morning and the afternoon, which a key picks\n// between by the start of each.\nfunction dayPeriodsOf(locale: string): readonly [string, string] {\n const formatter = new DateFormatter(locale, { hour: 'numeric', hour12: true })\n const periodAt = (hours: number) => {\n const date = new Date()\n date.setHours(hours)\n return (\n formatter.formatToParts(date).find((part) => part.type === 'dayPeriod')\n ?.value ?? ''\n )\n }\n\n return [periodAt(0), periodAt(12)]\n}\n\n// Whether a segment is drawn: every one on a field's line, and in a drawing\n// of its own the parts it names and the punctuation that holds something to\n// see.\nfunction drawn(drawing: SegmentDrawing | undefined, segment: DateSegment) {\n if (drawing === undefined) {\n return true\n }\n\n return segment.type === 'literal'\n ? segment.text.replaceAll(INVISIBLE, '') !== ''\n : drawing.parts.has(segment.type)\n}\n\nfunction edited({ onEdit }: SegmentLineProps, changed: boolean) {\n if (changed) {\n onEdit?.()\n }\n}\n\n// Takes a digit off the end of a segment, as backspace does in React Aria's,\n// and clears a day period or an era outright. On a segment already empty it\n// moves to the one before. Whether it changed the value.\nfunction eraseFrom(\n state: DateFieldState,\n segment: DateSegment,\n locale: string,\n entered: RefObject<string>,\n moves: Moves,\n): boolean {\n if (state.isDisabled || state.isReadOnly) {\n return false\n }\n\n if (segment.text === segment.placeholder) {\n moves.previous()\n }\n\n const parser = new NumberParser(locale, { maximumFractionDigits: 0 })\n\n if (parser.isValidPartialNumber(segment.text) && !segment.isPlaceholder) {\n const shortened = segment.text.slice(0, -1)\n const parsed = parser.parse(shortened)\n const kept = parsed === 0 ? '' : shortened\n\n if (kept === '') {\n state.clearSegment(segment.type)\n } else {\n state.setSegment(segment.type, parsed)\n }\n entered.current = kept\n return true\n }\n\n if (segment.type === 'dayPeriod' || segment.type === 'era') {\n state.clearSegment(segment.type)\n return true\n }\n\n return false\n}\n\nfunction eraseKey(line: SegmentLineProps, segment: DateSegment) {\n edited(\n line,\n eraseFrom(\n line.state,\n segment,\n line.locale,\n line.entered,\n movesFrom(line, segment.type),\n ),\n )\n}\n\n// The calendar's eras with the names a key picks them by: each era's name in\n// the locale, less what every name begins with, so a calendar whose eras are\n// ERA0 and ERA1 is typed with 0 and 1, as React Aria's is.\nfunction erasOf(calendar: Calendar, locale: string) {\n const formatter = new DateFormatter(locale, {\n era: 'narrow',\n timeZone: 'UTC',\n year: 'numeric',\n })\n const first = toCalendar(new CalendarDate(1, 1, 1), calendar)\n const eras = calendar.getEras().map((era) => {\n const date = first.set({ day: 1, era, month: 1, year: 1 }).toDate('UTC')\n\n return {\n era,\n // An era with no name in the locale is typed by its identifier.\n formatted:\n formatter.formatToParts(date).find((part) => part.type === 'era')\n ?.value ?? era,\n }\n })\n const prefix = commonPrefixLength(eras.map((era) => era.formatted))\n\n return eras.map(({ era, formatted }) => ({\n era,\n formatted: formatted.slice(prefix),\n }))\n}\n\n// Moves focus to the segment of `type`: the segment's own element under React\n// Native Web, and on iOS and Android the hidden input, with the segment made\n// the one it types into. A read-only field raises no keyboard, and nor does a\n// move that puts the keyboard away, which makes the segment the one in focus\n// and takes focus off the input.\nfunction focusTo(\n { entered, input, nodes, setActive, state }: Focusing,\n type: DateSegmentType,\n keyboard = true,\n) {\n entered.current = ''\n\n if (Platform.OS === 'web') {\n nodes.current.get(type)?.focus()\n return\n }\n\n if (!keyboard) {\n setActive(type)\n input.current?.blur()\n return\n }\n\n if (state.isReadOnly) {\n return\n }\n\n setActive(type)\n input.current?.focus()\n}\n\n// Whether setting the era to `era` stops the era segment being drawn, which\n// React Stately draws in a Gregorian calendar only while the date is BC.\nfunction hidesEra(state: DateFieldState, era: string) {\n return state.calendar.identifier === 'gregory' && era !== 'BC'\n}\n\n// What the hidden input does on taking focus: types into the segment it was\n// focused for, or the first where it was focused some other way.\nfunction inputFocusedOf(line: SegmentLineProps) {\n return () => {\n const first =\n line.state.segments.find((segment) => typedInto(line.drawing, segment))\n ?.type ?? null\n line.setActive((current) => current ?? first)\n arrivedIn(line)\n }\n}\n\n// Keeps the hidden input, which focus is moved to on iOS and Android.\nfunction inputOf({ input }: SegmentLineProps) {\n return (node: ComponentRef<typeof TextInput> | null) => {\n input.current = node\n }\n}\n\n// What focus leaving the segments does: fills in what the placeholder can,\n// as React Aria's field does on blur, then tells the field.\nfunction leftOf({\n entered,\n inside,\n onBlur,\n setActive,\n state,\n}: SegmentLineProps) {\n return () => {\n inside.current = false\n entered.current = ''\n setActive(null)\n state.confirmPlaceholder()\n onBlur?.()\n }\n}\n\n// The segments on either side of the one of `type`, among those a person\n// types into, which a full segment moves on to and a backspace back to. Past\n// either end it is the field's to say, as a range picker's focus moves on\n// from one date's segments to the other's.\nfunction movesFrom(line: SegmentLineProps, type: DateSegmentType): Moves {\n const editable = line.state.segments.filter((segment) =>\n typedInto(line.drawing, segment),\n )\n const at = editable.findIndex((segment) => segment.type === type)\n const to = (index: number, beyond?: () => void) => () => {\n const segment = index < 0 ? undefined : editable.at(index)\n if (segment === undefined) {\n beyond?.()\n } else {\n focusTo(line, segment.type)\n }\n }\n\n return {\n away: to(at > 0 ? at - 1 : at + 1),\n next: to(at + 1, line.onPastEnd),\n previous: to(at - 1, line.onBeforeStart),\n }\n}\n\n// The name a segment of `type` is read by. A literal is never read, and is\n// named as a day only to keep the lookup total.\nfunction nameOf(\n type: DateSegmentType,\n): keyof Omit<\n LibraryMessages['segments'],\n 'empty' | 'selectedDate' | 'selectedTime'\n> {\n return type === 'literal' ? 'day' : type\n}\n\n// Keeps each segment's element, which focus is moved to under React Native\n// Web, for as long as it is drawn.\nfunction nodeOf({ nodes }: SegmentLineProps, type: DateSegmentType) {\n return (node: HostInstance | null) => {\n if (node === null) {\n return undefined\n }\n\n nodes.current.set(type, node)\n return () => {\n nodes.current.delete(type)\n }\n }\n}\n\n// What a press on a segment does on iOS and Android: makes it the one typed\n// into, and raises the keyboard, unless the drawing says a press only makes\n// it the one in focus.\nfunction pressOf(line: SegmentLineProps, type: DateSegmentType) {\n return () => {\n focusTo(line, type, line.drawing?.raisesKeyboard ?? true)\n }\n}\n\n// The element focus moved to, off a browser's blur event.\nfunction relatedTargetOf(event: unknown): unknown {\n return typeof event === 'object' && event !== null && 'relatedTarget' in event\n ? event.relatedTarget\n : undefined\n}\n\n// The segments themselves, drawn from the field's state.\nfunction SegmentLine(line: SegmentLineProps) {\n const { active, described, drawing, isInvalid, label, locale, state } = line\n const id = useId()\n const theme = useTheme()\n const own = segmentStylesOf(theme)\n const role = useTypeRole('bodyLarge')\n const words = messagesFor(locale).segments\n const first = state.segments.find((segment) => typedInto(drawing, segment))\n const value = line.holding ?? valueOf(state, words)\n const valueId = `${id}-value`\n const parts =\n value === '' ? described : [{ id: valueId, text: value }, ...described]\n const canEdit = !state.isDisabled && !state.isReadOnly\n\n return (\n <FieldSegments>\n {state.segments.map((segment, index) => {\n if (!drawn(drawing, segment)) {\n return null\n }\n\n if (!segment.isEditable) {\n return (\n <NativeText\n aria-hidden={segment.type === 'literal'}\n // A segment's place is its key, and a literal's its index, since\n // a locale can put the same punctuation between several.\n // oxlint-disable-next-line react/no-array-index-key -- see above\n key={`${segment.type}-${index}`}\n style={\n drawing === undefined\n ? composeStyles<TextStyle>(\n role,\n segment.type === 'literal' ? undefined : own.segment,\n state.isDisabled\n ? own.textDisabled\n : segment.type === 'literal'\n ? own.textMuted\n : own.text,\n )\n : drawing.literal\n }\n >\n {segment.text}\n </NativeText>\n )\n }\n\n const focused = segment.type === active\n // The field's description is said on the first segment alone, so it\n // is not heard again at every step, unless the field has an error.\n const describes = isInvalid || segment.type === first?.type\n\n return (\n <Pressable\n {...(Platform.OS === 'web' ? webPropsOf(line, segment) : undefined)}\n {...(describes ? descriptionOf(parts) : undefined)}\n {...webStateOf(isInvalid, state)}\n accessibilityActions={canEdit ? ADJUSTABLE : undefined}\n accessibilityRole={Platform.OS === 'web' ? undefined : 'adjustable'}\n aria-disabled={state.isDisabled}\n aria-label={`${words[nameOf(segment.type)]}, ${label}`}\n aria-valuemax={segment.maxValue}\n aria-valuemin={segment.minValue}\n aria-valuenow={segment.value ?? undefined}\n aria-valuetext={valueTextOf(segment, state, locale, words.empty)}\n disabled={state.isDisabled}\n key={segment.type}\n onAccessibilityAction={actionOf(line, segment)}\n onPress={\n Platform.OS === 'web' ? undefined : pressOf(line, segment.type)\n }\n ref={nodeOf(line, segment.type)}\n role={Platform.OS === 'web' ? 'spinbutton' : undefined}\n style={\n drawing === undefined\n ? composeStyles<ViewStyle>(\n own.segment,\n focused ? own.segmentFocused : undefined,\n )\n : drawing.box(segment.type, focused)\n }\n >\n <NativeText\n style={\n drawing === undefined\n ? composeStyles<TextStyle>(\n role,\n textStyleOf(own, segment, focused, state.isDisabled),\n )\n : drawing.text(segment.type, focused)\n }\n >\n {segment.text}\n </NativeText>\n </Pressable>\n )\n })}\n {Platform.OS === 'web' ? (\n value === '' ? null : (\n <NativeText id={valueId} style={styles.notDrawn}>\n {value}\n </NativeText>\n )\n ) : (\n <TextInput\n aria-hidden\n autoCapitalize=\"none\"\n autoComplete=\"off\"\n autoCorrect={false}\n caretHidden\n contextMenuHidden\n editable={canEdit}\n importantForAutofill=\"no\"\n keyboardType={\n active === null || NUMERIC.has(active) ? 'number-pad' : 'default'\n }\n onBlur={leftOf(line)}\n onChangeText={changedOf(line)}\n onFocus={inputFocusedOf(line)}\n ref={inputOf(line)}\n selection={AFTER_SENTINEL}\n spellCheck={false}\n style={styles.input}\n value={SENTINEL}\n />\n )}\n </FieldSegments>\n )\n}\n\n// Steps a segment, as an arrow key or a swipe does, which starts what is\n// typed into it again. Whether it changed the value.\nfunction stepBy(\n state: DateFieldState,\n segment: DateSegment,\n by: Step,\n entered: RefObject<string>,\n): boolean {\n if (state.isDisabled || state.isReadOnly) {\n return false\n }\n\n entered.current = ''\n state[by](segment.type)\n return true\n}\n\nfunction stepKey(line: SegmentLineProps, segment: DateSegment, by: Step) {\n const changed = stepBy(line.state, segment, by, line.entered)\n\n // A Gregorian era is drawn only while it is BC, so a step, which can only\n // take it to AD, takes the segment away, and focus with it where it is the\n // segment in focus. A screen reader's swipe moves no focus of ours, and\n // raises no keyboard.\n if (\n changed &&\n segment.type === 'era' &&\n line.active === 'era' &&\n hidesEra(line.state, 'AD')\n ) {\n movesFrom(line, 'era').away()\n }\n edited(line, changed)\n}\n\nfunction textStyleOf(\n own: ReturnType<typeof segmentStylesOf>,\n segment: DateSegment,\n focused: boolean,\n isDisabled: boolean,\n) {\n if (isDisabled) {\n return own.textDisabled\n }\n\n if (focused) {\n return own.textFocused\n }\n\n return segment.isPlaceholder ? own.textMuted : own.text\n}\n\n// Whether a person types into `segment`: one they can edit, which the\n// drawing, where there is one, draws.\nfunction typedInto(drawing: SegmentDrawing | undefined, segment: DateSegment) {\n return segment.isEditable && drawn(drawing, segment)\n}\n\n// Types `key` into a segment, as React Aria's segment takes a key typed into\n// it, and moves on once the segment can take no more. Whether it changed the\n// value.\nfunction typeInto(\n state: DateFieldState,\n segment: DateSegment,\n key: string,\n locale: string,\n entered: RefObject<string>,\n moves: Moves,\n): boolean {\n if (state.isDisabled || state.isReadOnly) {\n return false\n }\n\n const startsWith = startsWithIn(locale)\n\n switch (segment.type) {\n case 'day':\n case 'hour':\n case 'minute':\n case 'month':\n case 'second':\n case 'year': {\n const parser = new NumberParser(locale, { maximumFractionDigits: 0 })\n const typed = entered.current + key\n\n if (!parser.isValidPartialNumber(typed)) {\n return false\n }\n\n const number = parser.parse(typed)\n\n if (Number.isNaN(number)) {\n return false\n }\n\n const { maxValue } = segment\n const over = maxValue !== undefined && number > maxValue\n\n // A number past the segment's largest starts again from the key alone,\n // so 13 in a month is a 3.\n state.setSegment(segment.type, over ? parser.parse(key) : number)\n\n if (\n maxValue !== undefined &&\n (Number(`${number}0`) > maxValue ||\n typed.length >= String(maxValue).length)\n ) {\n entered.current = ''\n moves.next()\n } else {\n entered.current = typed\n }\n return true\n }\n case 'dayPeriod': {\n const [am, pm] = dayPeriodsOf(locale)\n\n if (startsWith(am, key)) {\n state.setSegment('dayPeriod', 0)\n } else if (startsWith(pm, key)) {\n state.setSegment('dayPeriod', 1)\n } else {\n return false\n }\n moves.next()\n return true\n }\n case 'era': {\n const matched = erasOf(state.calendar, locale).find((era) =>\n startsWith(era.formatted, key),\n )\n\n if (matched === undefined) {\n return false\n }\n state.setSegment('era', matched.era)\n\n if (hidesEra(state, matched.era)) {\n moves.away()\n } else {\n moves.next()\n }\n return true\n }\n case 'literal':\n case 'timeZoneName': {\n break\n }\n }\n\n // A literal and a time zone are written by the locale and the value, and\n // nothing typed reaches them.\n return false\n}\n\nfunction typeKey(line: SegmentLineProps, segment: DateSegment, key: string) {\n edited(\n line,\n typeInto(\n line.state,\n segment,\n key,\n line.locale,\n line.entered,\n movesFrom(line, segment.type),\n ),\n )\n}\n\n// The date or the time a field holds, written out, which describes the\n// field after its segments, as React Aria describes it. Nothing while the\n// field is empty.\nfunction valueOf(state: DateFieldState, words: LibraryMessages['segments']) {\n if (state.value === null) {\n return ''\n }\n\n const written = state.formatValue({ month: 'long' })\n\n return state.maxGranularity === 'hour'\n ? words.selectedTime.replace('{time}', written)\n : words.selectedDate.replace('{date}', written)\n}\n\n// What a segment's value reads as, as React Aria writes it: a month with its\n// name beside its number, an hour with its day period, and an empty segment\n// as empty.\nfunction valueTextOf(\n segment: DateSegment,\n state: DateFieldState,\n locale: string,\n empty: string,\n) {\n if (segment.isPlaceholder) {\n return empty\n }\n\n const { hour12, timeZone } = state.dateFormatter.resolvedOptions()\n\n if (segment.type === 'month') {\n const month = new DateFormatter(locale, { month: 'long', timeZone }).format(\n state.dateValue,\n )\n return month === segment.text ? month : `${segment.text} – ${month}`\n }\n\n if (segment.type === 'hour') {\n return new DateFormatter(locale, {\n hour: 'numeric',\n hour12,\n timeZone,\n }).format(state.dateValue)\n }\n\n return segment.text\n}\n\n// What a segment takes under React Native Web: focus, and the keys a browser\n// hands it.\nfunction webPropsOf(\n line: SegmentLineProps,\n segment: DateSegment,\n): WebSegmentProps {\n const moves = movesFrom(line, segment.type)\n const step = (by: Step) => () => {\n stepKey(line, segment, by)\n }\n const erase = () => {\n eraseKey(line, segment)\n }\n // The arrow keys move along the line as it reads, so left is the next\n // segment in a right-to-left page.\n const keys = new Map<string, () => void>([\n ['ArrowDown', step('decrement')],\n ['ArrowLeft', I18nManager.isRTL ? moves.next : moves.previous],\n ['ArrowRight', I18nManager.isRTL ? moves.previous : moves.next],\n ['ArrowUp', step('increment')],\n ['Backspace', erase],\n ['Delete', erase],\n ['End', step('incrementToMax')],\n ['Home', step('decrementToMin')],\n ['PageDown', step('decrementPage')],\n ['PageUp', step('incrementPage')],\n ])\n\n return {\n // Focus moving to another segment stays in the field, and only focus\n // leaving the segments altogether is the field's blur.\n onBlur: (event) => {\n const to = relatedTargetOf(event.nativeEvent)\n if (![...line.nodes.current.values()].some((node) => node === to)) {\n leftOf(line)()\n }\n },\n onFocus: () => {\n line.entered.current = ''\n line.setActive(segment.type)\n arrivedIn(line)\n },\n onKeyDown: (event) => {\n const { altKey, ctrlKey, key, metaKey } = event.nativeEvent\n const handler = keys.get(key)\n\n if (handler !== undefined) {\n event.preventDefault()\n handler()\n return\n }\n\n // A key that types one character, rather than one held with a key that\n // makes it a shortcut, is typed into the segment.\n const point = key.codePointAt(0)\n\n if (\n point !== undefined &&\n String.fromCodePoint(point) === key &&\n !altKey &&\n !ctrlKey &&\n !metaKey\n ) {\n event.preventDefault()\n typeKey(line, segment, key)\n }\n },\n }\n}\n\n// What a browser reads off a segment that React Native has no prop for.\nfunction webStateOf(isInvalid: boolean, state: DateFieldState) {\n if (Platform.OS !== 'web') {\n return undefined\n }\n\n return {\n ...(isInvalid ? { 'aria-invalid': true } : undefined),\n ...(state.isReadOnly ? { 'aria-readonly': true } : undefined),\n ...(state.isRequired ? { 'aria-required': true } : undefined),\n }\n}\n\nexport { DateSegments }\nexport type { DateSegmentsProps, SegmentDrawing, SegmentsHandle }\n"],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@kanso-labs/react-native-kanso-ui",
3
- "version": "0.11.25",
3
+ "version": "0.11.26",
4
4
  "description": "Kanso UI's Material Design components for React Native, themed through the same --kui-* design tokens as the web library",
5
5
  "keywords": [
6
6
  "react-native",
@@ -114,6 +114,7 @@
114
114
  "react": ">=19.2.0",
115
115
  "react-native": ">=0.86.0",
116
116
  "react-native-gesture-handler": "^2.32.0 || ^3.0.0",
117
+ "react-native-keyboard-controller": ">=1.22.0",
117
118
  "react-native-reanimated": "^4.5.0",
118
119
  "react-native-safe-area-context": "^5.0.0",
119
120
  "react-native-svg": "^15.15.0",
@@ -131,6 +132,9 @@
131
132
  },
132
133
  "expo-image-picker": {
133
134
  "optional": true
135
+ },
136
+ "react-native-keyboard-controller": {
137
+ "optional": true
134
138
  }
135
139
  },
136
140
  "overrides": {