1 | import { useEffect, useReducer, useMemo } from 'react';
|
2 |
|
3 | import ExpoLocalization, {
|
4 | addCalendarListener,
|
5 | addLocaleListener,
|
6 | removeSubscription,
|
7 | } from './ExpoLocalization';
|
8 | import { Localization } from './Localization.types';
|
9 | export * from './Localization.types';
|
10 |
|
11 | // @needsAudit
|
12 | /**
|
13 | * @hidden
|
14 | * @deprecated Use Localization.getLocales() instead.
|
15 | * Three-character ISO 4217 currency code. Returns `null` on web.
|
16 | *
|
17 | * @example
|
18 | * `'USD'`, `'EUR'`, `'CNY'`, `null`
|
19 | */
|
20 | export const currency = ExpoLocalization.currency;
|
21 |
|
22 | // @needsAudit
|
23 | /**
|
24 | * @hidden
|
25 | * @deprecated Use Localization.getLocales() instead.
|
26 | * Decimal separator used for formatting numbers.
|
27 | *
|
28 | * @example
|
29 | * `','`, `'.'`
|
30 | */
|
31 | export const decimalSeparator = ExpoLocalization.decimalSeparator;
|
32 |
|
33 | // @needsAudit
|
34 | /**
|
35 | * @hidden
|
36 | * @deprecated Use Localization.getLocales() instead.
|
37 | * Digit grouping separator used when formatting numbers larger than 1000.
|
38 | *
|
39 | * @example
|
40 | * `'.'`, `''`, `','`
|
41 | */
|
42 | export const digitGroupingSeparator = ExpoLocalization.digitGroupingSeparator;
|
43 |
|
44 | // @needsAudit
|
45 | /**
|
46 | * @hidden
|
47 | * @deprecated Use Localization.getLocales() instead.
|
48 | * A list of all the supported language ISO codes.
|
49 | */
|
50 | export const isoCurrencyCodes = ExpoLocalization.isoCurrencyCodes;
|
51 |
|
52 | // @needsAudit
|
53 | /**
|
54 | * @hidden
|
55 | * @deprecated Use Localization.getLocales() instead.
|
56 | * Boolean value that indicates whether the system uses the metric system.
|
57 | * On Android and web, this is inferred from the current region.
|
58 | */
|
59 | export const isMetric = ExpoLocalization.isMetric;
|
60 |
|
61 | // @needsAudit
|
62 | /**
|
63 | * @hidden
|
64 | * @deprecated Use Localization.getLocales() instead.
|
65 | * Returns if the system's language is written from Right-to-Left.
|
66 | * This can be used to build features like [bidirectional icons](https://material.io/design/usability/bidirectionality.html).
|
67 | *
|
68 | * Returns `false` in Server Side Rendering (SSR) environments.
|
69 | */
|
70 | export const isRTL = ExpoLocalization.isRTL;
|
71 |
|
72 | // @needsAudit
|
73 | /**
|
74 | * @deprecated Use [`Localization.getLocales()`](#localizationgetlocales) instead.
|
75 | * An [IETF BCP 47 language tag](https://en.wikipedia.org/wiki/IETF_language_tag),
|
76 | * consisting of a two-character language code and optional script, region and variant codes.
|
77 | *
|
78 | * @example
|
79 | * `'en'`, `'en-US'`, `'zh-Hans'`, `'zh-Hans-CN'`, `'en-emodeng'`
|
80 | */
|
81 | export const locale = ExpoLocalization.locale;
|
82 |
|
83 | // @needsAudit
|
84 | /**
|
85 | * @hidden
|
86 | * @deprecated Use Localization.getLocales() instead.
|
87 | * List of all the native languages provided by the user settings.
|
88 | * These are returned in the order the user defines in their device settings.
|
89 | *
|
90 | * @example
|
91 | * `['en', 'en-US', 'zh-Hans', 'zh-Hans-CN', 'en-emodeng']`
|
92 | */
|
93 | export const locales = ExpoLocalization.locales;
|
94 |
|
95 | // @needsAudit
|
96 | /**
|
97 | * @hidden
|
98 | * @deprecated Use Localization.getCalendars() instead.
|
99 | * The current time zone in display format.
|
100 | * On Web time zone is calculated with Intl.DateTimeFormat().resolvedOptions().timeZone. For a
|
101 | * better estimation you could use the moment-timezone package but it will add significant bloat to
|
102 | * your website's bundle size.
|
103 | *
|
104 | * @example
|
105 | * `'America/Los_Angeles'`
|
106 | */
|
107 | export const timezone = ExpoLocalization.timezone;
|
108 |
|
109 | // @needsAudit
|
110 | /**
|
111 | * @hidden
|
112 | * @deprecated Use Localization.getLocales() instead.
|
113 | * The region code for your device that comes from the Region setting under Language & Region on iOS.
|
114 | * This value is always available on iOS, but might return `null` on Android or web.
|
115 | *
|
116 | * @example
|
117 | * `'US'`, `'NZ'`, `null`
|
118 | */
|
119 | export const region = ExpoLocalization.region;
|
120 |
|
121 | /**
|
122 | * List of user's locales, returned as an array of objects of type `Locale`.
|
123 | * Guaranteed to contain at least 1 element.
|
124 | * These are returned in the order the user defines in their device settings.
|
125 | * On the web currency and measurements systems are not provided, instead returned as null.
|
126 | * If needed, you can infer them from the current region using a lookup table.
|
127 | * @example
|
128 | * ```js
|
129 | * [{
|
130 | * "languageTag": "pl-PL",
|
131 | * "languageCode": "pl",
|
132 | * "textDirection": "ltr",
|
133 | * "digitGroupingSeparator": " ",
|
134 | * "decimalSeparator": ",",
|
135 | * "measurementSystem": "metric",
|
136 | * "currencyCode": "PLN",
|
137 | * "currencySymbol": "zł",
|
138 | * "regionCode": "PL",
|
139 | * "temperatureUnit": "celsius"
|
140 | * }]
|
141 | * ```
|
142 | */
|
143 | export const getLocales = ExpoLocalization.getLocales;
|
144 |
|
145 | /**
|
146 | * List of user's preferred calendars, returned as an array of objects of type `Calendar`.
|
147 | * Guaranteed to contain at least 1 element.
|
148 | * For now always returns a single element, but it's likely to return a user preference list on some platforms in the future.
|
149 | * @example
|
150 | * ```js
|
151 | * [{
|
152 | * "calendar": "gregory",
|
153 | * "timeZone": "Europe/Warsaw",
|
154 | * "uses24hourClock": true,
|
155 | * "firstWeekday": 1
|
156 | * }]
|
157 | * ```
|
158 | */
|
159 | export const getCalendars = ExpoLocalization.getCalendars;
|
160 |
|
161 | /**
|
162 | * A hook providing a list of user's locales, returned as an array of objects of type `Locale`.
|
163 | * Guaranteed to contain at least 1 element.
|
164 | * These are returned in the order the user defines in their device settings.
|
165 | * On the web currency and measurements systems are not provided, instead returned as null.
|
166 | * If needed, you can infer them from the current region using a lookup table.
|
167 | * If the OS settings change, the hook will rerender with a new list of locales.
|
168 | * @example
|
169 | * ```js
|
170 | * [{
|
171 | * "languageTag": "pl-PL",
|
172 | * "languageCode": "pl",
|
173 | * "textDirection": "ltr",
|
174 | * "digitGroupingSeparator": " ",
|
175 | * "decimalSeparator": ",",
|
176 | * "measurementSystem": "metric",
|
177 | * "currencyCode": "PLN",
|
178 | * "currencySymbol": "zł",
|
179 | * "regionCode": "PL",
|
180 | * "temperatureUnit": "celsius"
|
181 | * }]
|
182 | * ```
|
183 | */
|
184 | export function useLocales() {
|
185 | const [key, invalidate] = useReducer((k) => k + 1, 0);
|
186 | const locales = useMemo(() => getLocales(), [key]);
|
187 | useEffect(() => {
|
188 | const subscription = addLocaleListener(invalidate);
|
189 | return () => {
|
190 | removeSubscription(subscription);
|
191 | };
|
192 | }, []);
|
193 | return locales;
|
194 | }
|
195 |
|
196 | /**
|
197 | * A hook providing a list of user's preferred calendars, returned as an array of objects of type `Calendar`.
|
198 | * Guaranteed to contain at least 1 element.
|
199 | * For now always returns a single element, but it's likely to return a user preference list on some platforms in the future.
|
200 | * If the OS settings change, the hook will rerender with a new list of calendars.
|
201 | * @example
|
202 | * ```js
|
203 | * [{
|
204 | * "calendar": "gregory",
|
205 | * "timeZone": "Europe/Warsaw",
|
206 | * "uses24hourClock": true,
|
207 | * "firstWeekday": 1
|
208 | * }]
|
209 | * ```
|
210 | */
|
211 | export function useCalendars() {
|
212 | const [key, invalidate] = useReducer((k) => k + 1, 0);
|
213 | const calendars = useMemo(() => getCalendars(), [key]);
|
214 | useEffect(() => {
|
215 | const subscription = addCalendarListener(invalidate);
|
216 | return () => {
|
217 | removeSubscription(subscription);
|
218 | };
|
219 | }, []);
|
220 | return calendars;
|
221 | }
|
222 |
|
223 | // @needsAudit
|
224 | /**
|
225 | * @hidden
|
226 | * Get the latest native values from the device. Locale can be changed on some Android devices
|
227 | * without resetting the app.
|
228 | * > On iOS, changing the locale will cause the device to reset meaning the constants will always be
|
229 | * correct.
|
230 | *
|
231 | * @example
|
232 | * ```ts
|
233 | * // When the app returns from the background on Android...
|
234 | *
|
235 | * const { locale } = await Localization.getLocalizationAsync();
|
236 | * ```
|
237 | * @deprecated
|
238 | * Use Localization.getLocales() or Localization.getCalendars() instead.
|
239 | */
|
240 | export async function getLocalizationAsync(): Promise<Localization> {
|
241 | return await ExpoLocalization.getLocalizationAsync();
|
242 | }
|