domma-js 0.56.0 → 0.58.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (121) hide show
  1. package/README.md +2 -2
  2. package/assets/types/generated/public/assets/flags/africa.d.ts +6 -0
  3. package/assets/types/generated/public/assets/flags/americas.d.ts +6 -0
  4. package/assets/types/generated/public/assets/flags/asia.d.ts +6 -0
  5. package/assets/types/generated/public/assets/flags/europe.d.ts +9 -0
  6. package/assets/types/generated/public/assets/flags/index.d.ts +11 -0
  7. package/assets/types/generated/public/assets/flags/oceania.d.ts +2 -0
  8. package/assets/types/generated/public/assets/icons/buildings.d.ts +6 -0
  9. package/assets/types/generated/public/assets/icons/code.d.ts +2 -0
  10. package/assets/types/generated/public/assets/icons/commerce.d.ts +7 -0
  11. package/assets/types/generated/public/assets/icons/communication.d.ts +7 -0
  12. package/assets/types/generated/public/assets/icons/devices.d.ts +6 -0
  13. package/assets/types/generated/public/assets/icons/emojis.d.ts +6 -0
  14. package/assets/types/generated/public/assets/icons/files.d.ts +7 -0
  15. package/assets/types/generated/public/assets/icons/finance.d.ts +6 -0
  16. package/assets/types/generated/public/assets/icons/forms.d.ts +5 -0
  17. package/assets/types/generated/public/assets/icons/health.d.ts +6 -0
  18. package/assets/types/generated/public/assets/icons/index.d.ts +24 -0
  19. package/assets/types/generated/public/assets/icons/media.d.ts +7 -0
  20. package/assets/types/generated/public/assets/icons/navigation.d.ts +7 -0
  21. package/assets/types/generated/public/assets/icons/seasonal.d.ts +6 -0
  22. package/assets/types/generated/public/assets/icons/social.d.ts +7 -0
  23. package/assets/types/generated/public/assets/icons/sport.d.ts +6 -0
  24. package/assets/types/generated/public/assets/icons/status.d.ts +7 -0
  25. package/assets/types/generated/public/assets/icons/transport.d.ts +7 -0
  26. package/assets/types/generated/public/assets/icons/ui.d.ts +7 -0
  27. package/assets/types/generated/public/assets/icons/weather.d.ts +6 -0
  28. package/assets/types/generated/src/auth.d.ts +424 -0
  29. package/assets/types/generated/src/avatar.d.ts +270 -0
  30. package/assets/types/generated/src/binding-source.d.ts +58 -0
  31. package/assets/types/generated/src/butterfly-drawing.d.ts +2 -0
  32. package/assets/types/generated/src/component-factory.d.ts +150 -0
  33. package/assets/types/generated/src/component.d.ts +162 -0
  34. package/assets/types/generated/src/components/back-to-top.d.ts +150 -0
  35. package/assets/types/generated/src/components/badge.d.ts +208 -0
  36. package/assets/types/generated/src/components/card.d.ts +189 -0
  37. package/assets/types/generated/src/components/command-palette.d.ts +352 -0
  38. package/assets/types/generated/src/components/dropzone.d.ts +342 -0
  39. package/assets/types/generated/src/components/focus-trap.d.ts +238 -0
  40. package/assets/types/generated/src/components/loader.d.ts +133 -0
  41. package/assets/types/generated/src/components/modal.d.ts +339 -0
  42. package/assets/types/generated/src/components/range-slider.d.ts +267 -0
  43. package/assets/types/generated/src/components/shared.d.ts +91 -0
  44. package/assets/types/generated/src/components/split-pane.d.ts +239 -0
  45. package/assets/types/generated/src/components/toast.d.ts +284 -0
  46. package/assets/types/generated/src/components/tooltip.d.ts +200 -0
  47. package/assets/types/generated/src/components/virtual-list.d.ts +340 -0
  48. package/assets/types/generated/src/config.d.ts +193 -0
  49. package/assets/types/generated/src/context-cursor.d.ts +69 -0
  50. package/assets/types/generated/src/context-menu.d.ts +596 -0
  51. package/assets/types/generated/src/dates.d.ts +367 -0
  52. package/assets/types/generated/src/dom.d.ts +1221 -0
  53. package/assets/types/generated/src/effects.d.ts +1281 -0
  54. package/assets/types/generated/src/elements.d.ts +4994 -0
  55. package/assets/types/generated/src/escape.d.ts +5 -0
  56. package/assets/types/generated/src/flags-bundle.d.ts +4 -0
  57. package/assets/types/generated/src/flags.d.ts +338 -0
  58. package/assets/types/generated/src/forms.d.ts +1060 -0
  59. package/assets/types/generated/src/globals.d.ts +45 -0
  60. package/assets/types/generated/src/http.d.ts +131 -0
  61. package/assets/types/generated/src/i18n.d.ts +261 -0
  62. package/assets/types/generated/src/icons.d.ts +213 -0
  63. package/assets/types/generated/src/index.d.ts +249 -0
  64. package/assets/types/generated/src/input-group.d.ts +135 -0
  65. package/assets/types/generated/src/models.d.ts +968 -0
  66. package/assets/types/generated/src/popover.d.ts +413 -0
  67. package/assets/types/generated/src/router.d.ts +344 -0
  68. package/assets/types/generated/src/safe-url.d.ts +10 -0
  69. package/assets/types/generated/src/sanitize.d.ts +97 -0
  70. package/assets/types/generated/src/schema-builder.d.ts +420 -0
  71. package/assets/types/generated/src/skeleton.d.ts +135 -0
  72. package/assets/types/generated/src/smooth-caret.d.ts +61 -0
  73. package/assets/types/generated/src/sortable.d.ts +368 -0
  74. package/assets/types/generated/src/storage.d.ts +93 -0
  75. package/assets/types/generated/src/tables.d.ts +901 -0
  76. package/assets/types/generated/src/theme.d.ts +262 -0
  77. package/assets/types/generated/src/ticker-tape-drawing.d.ts +2 -0
  78. package/assets/types/generated/src/treeview.d.ts +504 -0
  79. package/assets/types/generated/src/utils.d.ts +1667 -0
  80. package/assets/types/generated/src/web-components/base/domma-element.d.ts +134 -0
  81. package/assets/types/generated/src/web-components/index.d.ts +14 -0
  82. package/assets/types/generated/vendor/domma-reactive.d.ts +587 -0
  83. package/assets/types/index.d.ts +104 -226
  84. package/package.json +5 -2
  85. package/public/dist/bundles/domma-complete.css +20 -14
  86. package/public/dist/bundles/domma-data-focused.css +20 -14
  87. package/public/dist/bundles/domma-essentials.css +20 -14
  88. package/public/dist/bundles/domma-full.css +20 -14
  89. package/public/dist/bundles/domma-minimal.css +8 -8
  90. package/public/dist/domma-flags.esm.js +3 -3
  91. package/public/dist/domma-flags.esm.js.map +1 -1
  92. package/public/dist/domma-flags.min.js +3 -3
  93. package/public/dist/domma-flags.min.js.map +1 -1
  94. package/public/dist/domma-syntax.min.js +3 -3
  95. package/public/dist/domma.css +3 -3
  96. package/public/dist/domma.esm.js +5 -5
  97. package/public/dist/domma.esm.js.map +1 -1
  98. package/public/dist/domma.min.js +5 -5
  99. package/public/dist/domma.min.js.map +1 -1
  100. package/public/dist/elements.css +9 -3
  101. package/public/dist/grid.css +3 -3
  102. package/public/dist/syntax.css +3 -3
  103. package/public/dist/themes/domma-themes.css +3 -3
  104. package/templates/kickstart/.claude/snippets.md +1 -1
  105. package/templates/kickstart/CLAUDE.md +1 -1
  106. package/templates/kickstart/frontend/types/domma.d.ts +7 -4
  107. package/templates/kickstart-spa/.claude/snippets.md +1 -1
  108. package/assets/types/config.d.ts +0 -136
  109. package/assets/types/dates.d.ts +0 -209
  110. package/assets/types/dom.d.ts +0 -448
  111. package/assets/types/elements.d.ts +0 -1168
  112. package/assets/types/flags.d.ts +0 -130
  113. package/assets/types/http.d.ts +0 -97
  114. package/assets/types/i18n.d.ts +0 -99
  115. package/assets/types/icons.d.ts +0 -147
  116. package/assets/types/models.d.ts +0 -260
  117. package/assets/types/smooth-caret.d.ts +0 -12
  118. package/assets/types/storage.d.ts +0 -93
  119. package/assets/types/tables.d.ts +0 -327
  120. package/assets/types/theme.d.ts +0 -137
  121. package/assets/types/utils.d.ts +0 -675
@@ -0,0 +1,424 @@
1
+ /**
2
+ * Options for `A.init()`.
3
+ * @typedef {object} AuthOptions
4
+ * @property {string} [apiUrl] - Backend API URL (default: `http://<host>:3000/api` on localhost, else `<origin>/api`)
5
+ * @property {string} [storageKey='auth_token'] - Storage key for the token
6
+ * @property {string} [userStorageKey='auth_user'] - Storage key for the user object
7
+ * @property {boolean} [autoCheck=true] - Verify a stored token with `GET <apiUrl>/auth/me` on init
8
+ */
9
+ /**
10
+ * The signed-in user, as the backend returned it (`response.user` from login, register or
11
+ * `/auth/me`). Domma reads `email` and `role`; anything else is the backend's.
12
+ * @typedef {{email?: string, name?: string, role?: string, [key: string]: any}} AuthUser
13
+ */
14
+ /**
15
+ * Events `A.on()` can listen for: `login` / `register` (data: the user), `logout` (null),
16
+ * `error` (the message string) and `tokenExpired` (null - a stored token the server refused on init).
17
+ * @typedef {'login'|'register'|'logout'|'error'|'tokenExpired'} AuthEventName
18
+ */
19
+ /**
20
+ * An auth event handler. Gets the event's data (see AuthEventName).
21
+ * @callback AuthEventHandler
22
+ * @param {any} data
23
+ * @returns {void}
24
+ */
25
+ /**
26
+ * The auth module (`A`, `Domma.auth`).
27
+ * @typedef {object} Auth
28
+ * @property {string|null} apiUrl - Backend API URL (set by init)
29
+ * @property {string|null} token - Current JWT, or null
30
+ * @property {AuthUser|null} user - Current user, or null
31
+ * @property {AuthOptions} config - Resolved configuration (set by init)
32
+ * @property {Record<string, AuthEventHandler[]>} eventHandlers - Registered handlers by event name
33
+ * @property {boolean} initialized - Whether init() has run
34
+ * @property {(config?: AuthOptions) => void} init - Initialise the module: load the stored token and user, and (autoCheck) verify the token
35
+ * @property {(email: string, password: string) => Promise<AuthUser>} login - Log in (`POST <apiUrl>/auth/login`); stores the token and user and emits `login`. Rejects on failure (and emits `error`)
36
+ * @property {(email: string, password: string, name: string) => Promise<AuthUser>} register - Register (`POST <apiUrl>/auth/register`); stores the token and user and emits `register`. Rejects on failure (and emits `error`)
37
+ * @property {() => void} logout - Clear the token and user and emit `logout`
38
+ * @property {() => AuthUser|null} getUser - Current user or null
39
+ * @property {() => boolean} isAuthenticated - True when there is both a token and a user
40
+ * @property {() => {Authorization?: string}} getHeaders - `{Authorization: 'Bearer <token>'}`, or `{}` without a token
41
+ * @property {() => string|null} getApiUrl - The backend API URL
42
+ * @property {() => string|null} getRole - Current user's role ('admin', 'subscriber', 'guest') or null
43
+ * @property {(role: string) => boolean} hasRole - Whether the user has this role
44
+ * @property {(roles: string[]) => boolean} hasAnyRole - Whether the user has any of these roles
45
+ * @property {() => boolean} isAdmin - Role is 'admin'
46
+ * @property {() => boolean} isSubscriber - Role is 'subscriber'
47
+ * @property {() => boolean} isGuest - Role is 'guest'
48
+ * @property {(event: AuthEventName|(string & {}), callback: AuthEventHandler) => void} on - Subscribe to an event
49
+ * @property {(event: AuthEventName|(string & {}), callback?: AuthEventHandler) => void} off - Unsubscribe one handler, or every handler of the event when none is given
50
+ * @property {typeof LoginForm} LoginForm - Login form component class
51
+ * @property {typeof RegisterForm} RegisterForm - Registration form component class
52
+ * @property {typeof AuthTabs} AuthTabs - Login/Register tab switcher component class
53
+ * @property {typeof UserInfo} UserInfo - Signed-in user display with a logout button
54
+ * @property {(selector: string|HTMLElement, options?: LoginFormOptions) => LoginForm} createLoginForm - Create a LoginForm
55
+ * @property {(selector: string|HTMLElement, options?: RegisterFormOptions) => RegisterForm} createRegisterForm - Create a RegisterForm
56
+ * @property {(selector: string|HTMLElement, options?: AuthTabsOptions) => AuthTabs} createAuthTabs - Create an AuthTabs
57
+ * @property {(selector: string|HTMLElement, options?: UserInfoOptions) => UserInfo} createUserInfo - Create a UserInfo
58
+ */
59
+ /**
60
+ * Options for `A.createLoginForm()` / `new A.LoginForm()`.
61
+ * @typedef {object} LoginFormOptions
62
+ * @property {string} [emailPlaceholder='your@email.com']
63
+ * @property {string} [passwordPlaceholder='Enter your password']
64
+ * @property {string} [buttonText='Login']
65
+ * @property {boolean} [showLabels=true]
66
+ * @property {((email: string, password: string) => void)|null} [onSubmit] - Called before the login request
67
+ * @property {((user: AuthUser|null) => void)|null} [onSuccess] - Called after a successful login
68
+ * @property {((error: Error) => void)|null} [onError] - Called when the login fails
69
+ */
70
+ /**
71
+ * Options for `A.createRegisterForm()` / `new A.RegisterForm()`.
72
+ * @typedef {object} RegisterFormOptions
73
+ * @property {string} [namePlaceholder='Your name']
74
+ * @property {string} [emailPlaceholder='your@email.com']
75
+ * @property {string} [passwordPlaceholder='Create a password']
76
+ * @property {string} [buttonText='Register']
77
+ * @property {number} [minPasswordLength=6]
78
+ * @property {boolean} [showLabels=true]
79
+ * @property {((email: string, password: string, name: string) => void)|null} [onSubmit] - Called before the register request
80
+ * @property {((user: AuthUser|null) => void)|null} [onSuccess] - Called after a successful registration
81
+ * @property {((error: Error) => void)|null} [onError] - Called when registration fails (also for mismatched passwords)
82
+ */
83
+ /**
84
+ * Options for `A.createAuthTabs()` / `new A.AuthTabs()`.
85
+ * @typedef {object} AuthTabsOptions
86
+ * @property {'login'|'register'} [activeTab='login']
87
+ * @property {string} [loginText='Login']
88
+ * @property {string} [registerText='Register']
89
+ * @property {((tab: string) => void)|null} [onChange] - Called with the tab switched to
90
+ */
91
+ /**
92
+ * Options for `A.createUserInfo()` / `new A.UserInfo()`.
93
+ * @typedef {object} UserInfoOptions
94
+ * @property {boolean} [showIcon=true]
95
+ * @property {boolean} [showRole=true]
96
+ * @property {string} [logoutText='Logout']
97
+ * @property {(() => void)|null} [onLogout] - Called after the logout button logs out
98
+ */
99
+ /** @type {Auth} */
100
+ export const auth: Auth;
101
+ /**
102
+ * LoginForm Component
103
+ */
104
+ export class LoginForm extends Component {
105
+ static defaults: {
106
+ emailPlaceholder: string;
107
+ passwordPlaceholder: string;
108
+ buttonText: string;
109
+ showLabels: boolean;
110
+ onSubmit: any;
111
+ onSuccess: any;
112
+ onError: any;
113
+ };
114
+ /**
115
+ * @param {string|HTMLElement} selector - Container element or selector
116
+ * @param {LoginFormOptions} [options]
117
+ */
118
+ constructor(selector: string | HTMLElement, options?: LoginFormOptions);
119
+ _init(): void;
120
+ render(): void;
121
+ handleSubmit(): Promise<void>;
122
+ }
123
+ /**
124
+ * RegisterForm Component
125
+ */
126
+ export class RegisterForm extends Component {
127
+ static defaults: {
128
+ namePlaceholder: string;
129
+ emailPlaceholder: string;
130
+ passwordPlaceholder: string;
131
+ buttonText: string;
132
+ minPasswordLength: number;
133
+ showLabels: boolean;
134
+ onSubmit: any;
135
+ onSuccess: any;
136
+ onError: any;
137
+ };
138
+ /**
139
+ * @param {string|HTMLElement} selector - Container element or selector
140
+ * @param {RegisterFormOptions} [options]
141
+ */
142
+ constructor(selector: string | HTMLElement, options?: RegisterFormOptions);
143
+ _init(): void;
144
+ render(): void;
145
+ handleSubmit(): Promise<void>;
146
+ }
147
+ /**
148
+ * AuthTabs Component
149
+ */
150
+ export class AuthTabs extends Component {
151
+ static defaults: {
152
+ activeTab: string;
153
+ loginText: string;
154
+ registerText: string;
155
+ onChange: any;
156
+ };
157
+ /**
158
+ * @param {string|HTMLElement} selector - Container element or selector
159
+ * @param {AuthTabsOptions} [options]
160
+ */
161
+ constructor(selector: string | HTMLElement, options?: AuthTabsOptions);
162
+ _init(): void;
163
+ render(): void;
164
+ /**
165
+ * @param {string} tab - 'login' or 'register'
166
+ */
167
+ switchTab(tab: string): void;
168
+ }
169
+ /**
170
+ * UserInfo Component
171
+ */
172
+ export class UserInfo extends Component {
173
+ static defaults: {
174
+ showIcon: boolean;
175
+ showRole: boolean;
176
+ logoutText: string;
177
+ onLogout: any;
178
+ };
179
+ /**
180
+ * @param {string|HTMLElement} selector
181
+ * @param {Object} [options]
182
+ */
183
+ constructor(selector: string | HTMLElement, options?: any);
184
+ _init(): void;
185
+ _onAuthChange: () => void;
186
+ render(): void;
187
+ handleLogout(): void;
188
+ }
189
+ /**
190
+ * Options for `A.init()`.
191
+ */
192
+ export type AuthOptions = {
193
+ /**
194
+ * - Backend API URL (default: `http://<host>:3000/api` on localhost, else `<origin>/api`)
195
+ */
196
+ apiUrl?: string;
197
+ /**
198
+ * - Storage key for the token
199
+ */
200
+ storageKey?: string;
201
+ /**
202
+ * - Storage key for the user object
203
+ */
204
+ userStorageKey?: string;
205
+ /**
206
+ * - Verify a stored token with `GET <apiUrl>/auth/me` on init
207
+ */
208
+ autoCheck?: boolean;
209
+ };
210
+ /**
211
+ * The signed-in user, as the backend returned it (`response.user` from login, register or
212
+ * `/auth/me`). Domma reads `email` and `role`; anything else is the backend's.
213
+ */
214
+ export type AuthUser = {
215
+ email?: string;
216
+ name?: string;
217
+ role?: string;
218
+ [key: string]: any;
219
+ };
220
+ /**
221
+ * Events `A.on()` can listen for: `login` / `register` (data: the user), `logout` (null),
222
+ * `error` (the message string) and `tokenExpired` (null - a stored token the server refused on init).
223
+ */
224
+ export type AuthEventName = "login" | "register" | "logout" | "error" | "tokenExpired";
225
+ /**
226
+ * An auth event handler. Gets the event's data (see AuthEventName).
227
+ */
228
+ export type AuthEventHandler = (data: any) => void;
229
+ /**
230
+ * The auth module (`A`, `Domma.auth`).
231
+ */
232
+ export type Auth = {
233
+ /**
234
+ * - Backend API URL (set by init)
235
+ */
236
+ apiUrl: string | null;
237
+ /**
238
+ * - Current JWT, or null
239
+ */
240
+ token: string | null;
241
+ /**
242
+ * - Current user, or null
243
+ */
244
+ user: AuthUser | null;
245
+ /**
246
+ * - Resolved configuration (set by init)
247
+ */
248
+ config: AuthOptions;
249
+ /**
250
+ * - Registered handlers by event name
251
+ */
252
+ eventHandlers: Record<string, AuthEventHandler[]>;
253
+ /**
254
+ * - Whether init() has run
255
+ */
256
+ initialized: boolean;
257
+ /**
258
+ * - Initialise the module: load the stored token and user, and (autoCheck) verify the token
259
+ */
260
+ init: (config?: AuthOptions) => void;
261
+ /**
262
+ * - Log in (`POST <apiUrl>/auth/login`); stores the token and user and emits `login`. Rejects on failure (and emits `error`)
263
+ */
264
+ login: (email: string, password: string) => Promise<AuthUser>;
265
+ /**
266
+ * - Register (`POST <apiUrl>/auth/register`); stores the token and user and emits `register`. Rejects on failure (and emits `error`)
267
+ */
268
+ register: (email: string, password: string, name: string) => Promise<AuthUser>;
269
+ /**
270
+ * - Clear the token and user and emit `logout`
271
+ */
272
+ logout: () => void;
273
+ /**
274
+ * - Current user or null
275
+ */
276
+ getUser: () => AuthUser | null;
277
+ /**
278
+ * - True when there is both a token and a user
279
+ */
280
+ isAuthenticated: () => boolean;
281
+ /**
282
+ * - `{Authorization: 'Bearer <token>'}`, or `{}` without a token
283
+ */
284
+ getHeaders: () => {
285
+ Authorization?: string;
286
+ };
287
+ /**
288
+ * - The backend API URL
289
+ */
290
+ getApiUrl: () => string | null;
291
+ /**
292
+ * - Current user's role ('admin', 'subscriber', 'guest') or null
293
+ */
294
+ getRole: () => string | null;
295
+ /**
296
+ * - Whether the user has this role
297
+ */
298
+ hasRole: (role: string) => boolean;
299
+ /**
300
+ * - Whether the user has any of these roles
301
+ */
302
+ hasAnyRole: (roles: string[]) => boolean;
303
+ /**
304
+ * - Role is 'admin'
305
+ */
306
+ isAdmin: () => boolean;
307
+ /**
308
+ * - Role is 'subscriber'
309
+ */
310
+ isSubscriber: () => boolean;
311
+ /**
312
+ * - Role is 'guest'
313
+ */
314
+ isGuest: () => boolean;
315
+ /**
316
+ * - Subscribe to an event
317
+ */
318
+ on: (event: AuthEventName | (string & {}), callback: AuthEventHandler) => void;
319
+ /**
320
+ * - Unsubscribe one handler, or every handler of the event when none is given
321
+ */
322
+ off: (event: AuthEventName | (string & {}), callback?: AuthEventHandler) => void;
323
+ /**
324
+ * - Login form component class
325
+ */
326
+ LoginForm: typeof LoginForm;
327
+ /**
328
+ * - Registration form component class
329
+ */
330
+ RegisterForm: typeof RegisterForm;
331
+ /**
332
+ * - Login/Register tab switcher component class
333
+ */
334
+ AuthTabs: typeof AuthTabs;
335
+ /**
336
+ * - Signed-in user display with a logout button
337
+ */
338
+ UserInfo: typeof UserInfo;
339
+ /**
340
+ * - Create a LoginForm
341
+ */
342
+ createLoginForm: (selector: string | HTMLElement, options?: LoginFormOptions) => LoginForm;
343
+ /**
344
+ * - Create a RegisterForm
345
+ */
346
+ createRegisterForm: (selector: string | HTMLElement, options?: RegisterFormOptions) => RegisterForm;
347
+ /**
348
+ * - Create an AuthTabs
349
+ */
350
+ createAuthTabs: (selector: string | HTMLElement, options?: AuthTabsOptions) => AuthTabs;
351
+ /**
352
+ * - Create a UserInfo
353
+ */
354
+ createUserInfo: (selector: string | HTMLElement, options?: UserInfoOptions) => UserInfo;
355
+ };
356
+ /**
357
+ * Options for `A.createLoginForm()` / `new A.LoginForm()`.
358
+ */
359
+ export type LoginFormOptions = {
360
+ emailPlaceholder?: string;
361
+ passwordPlaceholder?: string;
362
+ buttonText?: string;
363
+ showLabels?: boolean;
364
+ /**
365
+ * - Called before the login request
366
+ */
367
+ onSubmit?: ((email: string, password: string) => void) | null;
368
+ /**
369
+ * - Called after a successful login
370
+ */
371
+ onSuccess?: ((user: AuthUser | null) => void) | null;
372
+ /**
373
+ * - Called when the login fails
374
+ */
375
+ onError?: ((error: Error) => void) | null;
376
+ };
377
+ /**
378
+ * Options for `A.createRegisterForm()` / `new A.RegisterForm()`.
379
+ */
380
+ export type RegisterFormOptions = {
381
+ namePlaceholder?: string;
382
+ emailPlaceholder?: string;
383
+ passwordPlaceholder?: string;
384
+ buttonText?: string;
385
+ minPasswordLength?: number;
386
+ showLabels?: boolean;
387
+ /**
388
+ * - Called before the register request
389
+ */
390
+ onSubmit?: ((email: string, password: string, name: string) => void) | null;
391
+ /**
392
+ * - Called after a successful registration
393
+ */
394
+ onSuccess?: ((user: AuthUser | null) => void) | null;
395
+ /**
396
+ * - Called when registration fails (also for mismatched passwords)
397
+ */
398
+ onError?: ((error: Error) => void) | null;
399
+ };
400
+ /**
401
+ * Options for `A.createAuthTabs()` / `new A.AuthTabs()`.
402
+ */
403
+ export type AuthTabsOptions = {
404
+ activeTab?: "login" | "register";
405
+ loginText?: string;
406
+ registerText?: string;
407
+ /**
408
+ * - Called with the tab switched to
409
+ */
410
+ onChange?: ((tab: string) => void) | null;
411
+ };
412
+ /**
413
+ * Options for `A.createUserInfo()` / `new A.UserInfo()`.
414
+ */
415
+ export type UserInfoOptions = {
416
+ showIcon?: boolean;
417
+ showRole?: boolean;
418
+ logoutText?: string;
419
+ /**
420
+ * - Called after the logout button logs out
421
+ */
422
+ onLogout?: (() => void) | null;
423
+ };
424
+ import Component from './component.js';
@@ -0,0 +1,270 @@
1
+ /**
2
+ * Initials for a name.
3
+ *
4
+ * 'Jane Smith' -> 'JS' first and last word
5
+ * 'Jane Q. Public' -> 'JP'
6
+ * 'Madonna' -> 'M' one word, one letter
7
+ * 'jane.smith@example.com' -> 'JS' the part before the @, split on . _ - +
8
+ * 'Jean-Luc Picard' -> 'JP'
9
+ * 'Łukasz Żuk' -> 'ŁŻ'
10
+ * '王小明' -> '王'
11
+ * '', null, ' !! ' -> '' nothing to go on: callers show an icon
12
+ *
13
+ * Words are split on spaces, dots, underscores, hyphens and plus signs;
14
+ * anything that is not a letter or digit at the start of a word (quotes,
15
+ * brackets, emoji) is skipped, and bracketed notes like "(Admin)" are dropped.
16
+ * @param {string|null|undefined} name
17
+ * @returns {string}
18
+ */
19
+ export function avatarInitials(name: string | null | undefined): string;
20
+ /**
21
+ * The tone (0-7) for a name: FNV-1a over the trimmed, lower-cased, single-spaced
22
+ * name. Stable across pages, sessions and machines; case and spacing do not
23
+ * change it, so 'jane smith' and 'Jane Smith' match.
24
+ * @param {string} key
25
+ * @returns {number}
26
+ */
27
+ export function avatarTone(key: string): number;
28
+ /**
29
+ * Render one avatar.
30
+ * @overload
31
+ * @param {string|Element|ArrayLike<Element>|null} target
32
+ * @param {AvatarOptions} [options]
33
+ * @returns {AvatarHandle|null}
34
+ */
35
+ export function avatar(target: string | Element | ArrayLike<Element> | null, options?: AvatarOptions): AvatarHandle | null;
36
+ /**
37
+ * Render one avatar into a detached <span> for you to insert.
38
+ * @overload
39
+ * @param {AvatarOptions} options
40
+ * @returns {AvatarHandle}
41
+ */
42
+ export function avatar(options: AvatarOptions): AvatarHandle;
43
+ export namespace avatar {
44
+ export { avatarInitials as initials };
45
+ export { avatarTone as tone };
46
+ /**
47
+ * The live handle on an element, if any - the same answer as E.get(target, 'avatar').
48
+ * @param {string|Element|ArrayLike<Element>} target
49
+ * @returns {AvatarHandle|null}
50
+ */
51
+ export function get(target: string | Element | ArrayLike<Element>): AvatarHandle | null;
52
+ /**
53
+ * Turn every `[data-avatar]` under `root` (and `root` itself) into an avatar,
54
+ * once. Options come from `data-avatar-*`. Returns the new handles.
55
+ * @param {string|Element|Document} [root]
56
+ * @returns {AvatarHandle[]}
57
+ */
58
+ export function scan(root?: string | Element | Document): AvatarHandle[];
59
+ }
60
+ /**
61
+ * Render a stack of avatars with a "+N" overflow bubble.
62
+ *
63
+ * @param {string|Element|ArrayLike<Element>} target - a <ul>/<ol> to fill, or any element
64
+ * to put a new <ul> into (its content comes back on destroy())
65
+ * @param {AvatarGroupOptions} [options] - see GROUP_DEFAULTS
66
+ * @returns {AvatarGroupHandle|null} null if nothing matched
67
+ */
68
+ export function avatarGroup(target: string | Element | ArrayLike<Element>, options?: AvatarGroupOptions): AvatarGroupHandle | null;
69
+ export namespace avatarGroup {
70
+ /**
71
+ * The live group handle on a host element (or its list), if any - the same answer as E.get(target, 'avatar-group').
72
+ * @param {string|Element|ArrayLike<Element>} target
73
+ * @returns {AvatarGroupHandle|null}
74
+ */
75
+ function get(target: string | Element | ArrayLike<Element>): AvatarGroupHandle | null;
76
+ }
77
+ /** @type {AvatarSize[]} */
78
+ export const AVATAR_SIZES: AvatarSize[];
79
+ /** @type {AvatarShape[]} */
80
+ export const AVATAR_SHAPES: AvatarShape[];
81
+ /** @type {AvatarStatus[]} */
82
+ export const AVATAR_STATUSES: AvatarStatus[];
83
+ /** How many `.avatar-tone-*` classes elements.css defines. */
84
+ export const AVATAR_TONES: 8;
85
+ export default avatar;
86
+ export type AvatarSize = "xs" | "sm" | "md" | "lg" | "xl";
87
+ export type AvatarShape = "circle" | "rounded" | "square";
88
+ export type AvatarStatus = "online" | "away" | "busy" | "offline";
89
+ export type AvatarOptions = {
90
+ /**
91
+ * - The person: initials, tone and accessible name come from it
92
+ */
93
+ name?: string | null;
94
+ /**
95
+ * - Picture URL; falls back to the initials (or icon) if it fails to load
96
+ */
97
+ src?: string | null;
98
+ /**
99
+ * - Accessible name when it should differ from name
100
+ */
101
+ alt?: string | null;
102
+ /**
103
+ * - Size (default 'md')
104
+ */
105
+ size?: AvatarSize;
106
+ /**
107
+ * - Shape (default 'circle')
108
+ */
109
+ shape?: AvatarShape;
110
+ /**
111
+ * - Status dot; the word goes into the accessible name
112
+ */
113
+ status?: AvatarStatus | null;
114
+ /**
115
+ * - Words for the statuses in the accessible name, e.g. {busy: 'in a meeting'}
116
+ */
117
+ statusLabels?: Partial<Record<AvatarStatus, string>> | null;
118
+ /**
119
+ * - Icon name shown instead of initials ('user' when there is no name)
120
+ */
121
+ icon?: string | null;
122
+ /**
123
+ * - Hover text; true = the accessible name
124
+ */
125
+ title?: string | true | null;
126
+ /**
127
+ * - A primary-coloured ring (default false)
128
+ */
129
+ ring?: boolean;
130
+ /**
131
+ * - 0-7 to choose the tint; default is a hash of the name
132
+ */
133
+ tone?: number | null;
134
+ /**
135
+ * - aria-hidden: the name is written next to it (default false)
136
+ */
137
+ decorative?: boolean;
138
+ };
139
+ /**
140
+ * The handle E.avatar() returns. `options`, `initials`, `tone` and `label` are read only.
141
+ */
142
+ export type AvatarHandle = {
143
+ /**
144
+ * - The avatar element
145
+ */
146
+ element: HTMLElement;
147
+ /**
148
+ * - The options in force
149
+ */
150
+ options: AvatarOptions;
151
+ /**
152
+ * - The initials drawn ('' when an icon is shown)
153
+ */
154
+ initials: string;
155
+ /**
156
+ * - The tone 0-7, or null with nothing to hash
157
+ */
158
+ tone: number | null;
159
+ /**
160
+ * - The accessible name, e.g. 'Jane Smith (online)'
161
+ */
162
+ label: string;
163
+ /**
164
+ * - Merge options and redraw
165
+ */
166
+ update: (options?: AvatarOptions) => AvatarHandle;
167
+ /**
168
+ * - Restore the element's previous children, classes and attributes
169
+ */
170
+ destroy: () => HTMLElement;
171
+ };
172
+ /**
173
+ * `E.avatar` - the factory with `initials`, `tone`, `get` and `scan`.
174
+ */
175
+ export type AvatarStatic = typeof avatar;
176
+ /**
177
+ * One person in an avatar group.
178
+ */
179
+ export type AvatarPerson = {
180
+ name?: string;
181
+ src?: string;
182
+ status?: AvatarStatus;
183
+ /**
184
+ * - Makes the avatar a link
185
+ */
186
+ href?: string;
187
+ alt?: string;
188
+ icon?: string;
189
+ tone?: number;
190
+ /**
191
+ * - Hover text (default: the accessible name)
192
+ */
193
+ title?: string | true;
194
+ };
195
+ export type AvatarGroupOptions = {
196
+ /**
197
+ * - People, or plain names
198
+ */
199
+ people?: Array<AvatarPerson | string>;
200
+ /**
201
+ * - Show this many, then "+N"; null = everyone
202
+ */
203
+ max?: number | null;
204
+ /**
205
+ * - Size (default 'md')
206
+ */
207
+ size?: AvatarSize;
208
+ /**
209
+ * - Shape (default 'circle')
210
+ */
211
+ shape?: AvatarShape;
212
+ /**
213
+ * - 'none' | 'sm' | 'md' | 'lg', pixels, or any CSS length; null = the stylesheet's 25%
214
+ */
215
+ overlap?: "none" | "sm" | "md" | "lg" | number | string | null;
216
+ /**
217
+ * - Accessible name for the list
218
+ */
219
+ label?: string | null;
220
+ statusLabels?: Partial<Record<AvatarStatus, string>> | null;
221
+ /**
222
+ * - Called when "+N" is pressed, instead of the popover
223
+ */
224
+ onMore?: ((hidden: AvatarPerson[], event: MouseEvent) => void) | null;
225
+ /**
226
+ * - false: no popover, the hidden names go in the button's title (default true)
227
+ */
228
+ popover?: boolean;
229
+ /**
230
+ * - The "+N" button's accessible name (default '3 more: A, B and C')
231
+ */
232
+ moreLabel?: ((count: number, names: string[]) => string) | null;
233
+ };
234
+ /**
235
+ * The handle E.avatarGroup() returns. Everything but the methods is read only.
236
+ */
237
+ export type AvatarGroupHandle = {
238
+ /**
239
+ * - The <ul>
240
+ */
241
+ element: HTMLUListElement | HTMLOListElement;
242
+ options: AvatarGroupOptions;
243
+ people: AvatarPerson[];
244
+ /**
245
+ * - Drawn as avatars
246
+ */
247
+ shown: AvatarPerson[];
248
+ /**
249
+ * - Folded into "+N"
250
+ */
251
+ hidden: AvatarPerson[];
252
+ /**
253
+ * - The "+N" button, or null
254
+ */
255
+ more: HTMLButtonElement | null;
256
+ /**
257
+ * - The "+N" popover, or null
258
+ */
259
+ popover: import("./popover.js").PopoverInstance | null;
260
+ update: (options?: AvatarGroupOptions) => AvatarGroupHandle;
261
+ setPeople: (people: Array<AvatarPerson | string>) => AvatarGroupHandle;
262
+ /**
263
+ * - Remove everything and restore the host
264
+ */
265
+ destroy: () => HTMLElement;
266
+ };
267
+ /**
268
+ * `E.avatarGroup` - the factory with `get`.
269
+ */
270
+ export type AvatarGroupStatic = typeof avatarGroup;