@datalayer/core 1.1.57 → 1.1.59

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.
@@ -37,10 +37,12 @@ export const UserAvatar = ({ avatarUrl, avatarIcon, size = 100, square = true, i
37
37
  height: size,
38
38
  borderRadius: square ? 2 : '50%',
39
39
  overflow: 'hidden',
40
- display: 'inline-flex',
40
+ display: 'flex',
41
41
  alignItems: 'center',
42
42
  justifyContent: 'center',
43
- }, children: _jsx(SelectedIcon, { size: size, colored: true }) }));
43
+ bg: fallbackBackground || 'accent.subtle',
44
+ '--datalayer-icon-fg': fallbackForeground || palette.primary,
45
+ }, children: _jsx(SelectedIcon, { size: iconSize ?? Math.round(size * 0.62), themed: true, colormode: true }) }));
44
46
  }
45
47
  if (hasRealAvatar(avatarUrl)) {
46
48
  return _jsx(DLAvatar, { className: className, square: square, src: avatarUrl, size: size });
@@ -102,6 +102,16 @@ export function LiveEditorCollaborators(props) {
102
102
  if (!faces.length) {
103
103
  return null;
104
104
  }
105
- return (_jsx(AvatarStack, { size: size, children: faces.map(face => (_jsx(PrincipalAvatar, { kind: "personal", size: size, alt: face.name, avatarUrl: face.avatarUrl, avatarIcon: face.avatarIcon, square: false }, face.id))) }));
105
+ return (
106
+ /*
107
+ * Expanding to the LEFT.
108
+ *
109
+ * A stack of faces spreads out on hover, and it spreads from where it is
110
+ * anchored: anchored on its left, it grew rightwards over whatever the
111
+ * toolbar holds next to it. `alignRight` anchors it on its right, so it
112
+ * opens back over the space it came from — empty by construction, since
113
+ * the stack was collapsed there a moment before.
114
+ */
115
+ _jsx(AvatarStack, { alignRight: true, size: size, children: faces.map(face => (_jsx(PrincipalAvatar, { kind: "personal", size: size, alt: face.name, avatarUrl: face.avatarUrl, avatarIcon: face.avatarIcon, square: false }, face.id))) }));
106
116
  }
107
117
  export default LiveEditorCollaborators;
@@ -23,11 +23,23 @@ import { SvgUsecasesHero } from '@datalayer/design/lib/svg/SvgUsecasesHero';
23
23
  export type PrincipalType = 'personal' | 'organization' | 'team';
24
24
  type AvatarComponent = ComponentType<SVGProps<SVGSVGElement> & {
25
25
  size?: number | 'small' | 'medium' | 'large';
26
+ /**
27
+ * The multi-colour variant, of the emoji the icon is drawn from.
28
+ *
29
+ * The avatars are never drawn with it — see the picker: they follow the
30
+ * colour of the theme instead, through `themed` and `colormode`.
31
+ */
26
32
  colored?: boolean;
33
+ /** Take the colour from `--datalayer-icon-fg`, or from `currentColor`. */
34
+ themed?: boolean;
35
+ /** Follow the colour mode of the page. */
36
+ colormode?: boolean | 'light' | 'dark';
27
37
  }>;
28
38
  export declare const PRINCIPAL_AVATAR_ICONS: ReadonlyArray<{
29
39
  name: string;
30
40
  label: string;
41
+ /** What the picture is of, as the emoji catalogue describes it. */
42
+ description?: string;
31
43
  Icon: AvatarComponent;
32
44
  }>;
33
45
  export declare const PRINCIPAL_BANNERS: readonly [{
@@ -1,40 +1,80 @@
1
- import { jsx as _jsx, Fragment as _Fragment, jsxs as _jsxs } from "react/jsx-runtime";
1
+ import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
2
+ /*
3
+ * Copyright (c) 2023-2025 Datalayer, Inc.
4
+ * Distributed under the terms of the Modified BSD License.
5
+ */
2
6
  /*
3
7
  * Copyright (c) 2023-2026 Datalayer, Inc.
4
8
  * Distributed under the terms of the Modified BSD License.
5
9
  */
6
10
  import { useEffect, useState } from 'react';
7
- import { Box, Button, Text } from '@primer/react';
11
+ import { Box, Button, Text, Tooltip } from '@primer/react';
8
12
  import { Dialog } from '@primer/react/experimental';
13
+ import AlienMaskIcon from '@datalayer/icons-react/data2/AlienMaskIcon';
9
14
  import AlienMonsterIcon from '@datalayer/icons-react/data2/AlienMonsterIcon';
10
15
  import AstronautIcon from '@datalayer/icons-react/data2/AstronautIcon';
16
+ import AtomSymbolIcon from '@datalayer/icons-react/data2/AtomSymbolIcon';
17
+ import BankIcon from '@datalayer/icons-react/data2/BankIcon';
18
+ import BlackNibIcon from '@datalayer/icons-react/data2/BlackNibIcon';
19
+ import BriefcaseIcon from '@datalayer/icons-react/data2/BriefcaseIcon';
20
+ import BuildingClassicIcon from '@datalayer/icons-react/data2/BuildingClassicIcon';
21
+ import BuildingConstructionIcon from '@datalayer/icons-react/data2/BuildingConstructionIcon';
22
+ import BuildingOfficeIcon from '@datalayer/icons-react/data2/BuildingOfficeIcon';
23
+ import BullseyeIcon from '@datalayer/icons-react/data2/BullseyeIcon';
24
+ import CloudGreyIcon from '@datalayer/icons-react/data2/CloudGreyIcon';
25
+ import ConstructionIcon from '@datalayer/icons-react/data2/ConstructionIcon';
11
26
  import ConstructionWorkerIcon from '@datalayer/icons-react/data2/ConstructionWorkerIcon';
12
27
  import CowboyHatFaceIcon from '@datalayer/icons-react/data2/CowboyHatFaceIcon';
28
+ import DashboardGreyIcon from '@datalayer/icons-react/data1/DashboardGreyIcon';
29
+ import DnaIcon from '@datalayer/icons-react/data2/DnaIcon';
30
+ import DraftIcon from '@datalayer/icons-react/data1/DraftIcon';
13
31
  import DragonFaceIcon from '@datalayer/icons-react/data2/DragonFaceIcon';
32
+ import DragonIcon from '@datalayer/icons-react/data2/DragonIcon';
14
33
  import ElfManIcon from '@datalayer/icons-react/data2/ElfManIcon';
34
+ import FireIcon from '@datalayer/icons-react/data2/FireIcon';
35
+ import FireworksIcon from '@datalayer/icons-react/data2/FireworksIcon';
15
36
  import FlyingSaucerIcon from '@datalayer/icons-react/data2/FlyingSaucerIcon';
37
+ import FourLeafCloverIcon from '@datalayer/icons-react/data2/FourLeafCloverIcon';
38
+ import GraduationCapIcon from '@datalayer/icons-react/data2/GraduationCapIcon';
16
39
  import GremlinIcon from '@datalayer/icons-react/data2/GremlinIcon';
17
40
  import GrinningFaceIcon from '@datalayer/icons-react/data2/GrinningFaceIcon';
41
+ import HouseIcon from '@datalayer/icons-react/data2/HouseIcon';
18
42
  import LizardIcon from '@datalayer/icons-react/data2/LizardIcon';
19
43
  import MagicWandIcon from '@datalayer/icons-react/data2/MagicWandIcon';
20
44
  import ManOfficeWorkerIcon from '@datalayer/icons-react/data2/ManOfficeWorkerIcon';
21
45
  import ManTechnologistIcon from '@datalayer/icons-react/data2/ManTechnologistIcon';
46
+ import MusicalNoteIcon from '@datalayer/icons-react/data2/MusicalNoteIcon';
22
47
  import NinjaIcon from '@datalayer/icons-react/data2/NinjaIcon';
48
+ import OpenHandsIcon from '@datalayer/icons-react/data2/OpenHandsIcon';
49
+ import PenIcon from '@datalayer/icons-react/data2/PenIcon';
23
50
  import PenguinIcon from '@datalayer/icons-react/data2/PenguinIcon';
51
+ import PictureIcon from '@datalayer/icons-react/data2/PictureIcon';
52
+ import PlaneDepartureIcon from '@datalayer/icons-react/data2/PlaneDepartureIcon';
24
53
  import PersonSurfingIcon from '@datalayer/icons-react/data2/PersonSurfingIcon';
25
54
  import PersonSwimmingIcon from '@datalayer/icons-react/data2/PersonSwimmingIcon';
55
+ import PictureFramedIcon from '@datalayer/icons-react/data2/PictureFramedIcon';
26
56
  import RingedPlanetIcon from '@datalayer/icons-react/data2/RingedPlanetIcon';
27
57
  import RobotIcon from '@datalayer/icons-react/data2/RobotIcon';
28
58
  import RocketIcon from '@datalayer/icons-react/data2/RocketIcon';
29
59
  import SantaClausIcon from '@datalayer/icons-react/data2/SantaClausIcon';
60
+ import SatelliteIcon from '@datalayer/icons-react/data2/SatelliteIcon';
30
61
  import ScientistIcon from '@datalayer/icons-react/data2/ScientistIcon';
31
62
  import SharkIcon from '@datalayer/icons-react/data2/SharkIcon';
32
63
  import SnowmanIcon from '@datalayer/icons-react/data2/SnowmanIcon';
64
+ import SpaceInvadersAlien1Icon from '@datalayer/icons-react/eggs/SpaceInvadersAlien1Icon';
65
+ import SpaceInvadersAlien2Icon from '@datalayer/icons-react/eggs/SpaceInvadersAlien2Icon';
66
+ import SpaceInvadersAlien3Icon from '@datalayer/icons-react/eggs/SpaceInvadersAlien3Icon';
67
+ import SparklerIcon from '@datalayer/icons-react/data2/SparklerIcon';
33
68
  import StarIcon from '@datalayer/icons-react/data2/StarIcon';
34
- import StudentWomanIcon from '@datalayer/icons-react/data2/StudentWomanIcon';
69
+ import StudentIcon from '@datalayer/icons-react/data2/StudentIcon';
70
+ import StudioMicrophoneIcon from '@datalayer/icons-react/data2/StudioMicrophoneIcon';
35
71
  import SunIcon from '@datalayer/icons-react/data2/SunIcon';
72
+ import WavingHandIcon from '@datalayer/icons-react/data2/WavingHandIcon';
36
73
  import WhaleSpoutingIcon from '@datalayer/icons-react/data2/WhaleSpoutingIcon';
37
74
  import WomanTechnologistIcon from '@datalayer/icons-react/data2/WomanTechnologistIcon';
75
+ import WrappedGiftIcon from '@datalayer/icons-react/data2/WrappedGiftIcon';
76
+ import WritingHandIcon from '@datalayer/icons-react/data2/WritingHandIcon';
77
+ import YinYangIcon from '@datalayer/icons-react/data2/YinYangIcon';
38
78
  import { SvgAboutHero } from '@datalayer/design/lib/svg/SvgAboutHero';
39
79
  import { SvgAgentsHero } from '@datalayer/design/lib/svg/SvgAgentsHero';
40
80
  import { SvgAgentsHomeHero } from '@datalayer/design/lib/svg/SvgAgentsHomeHero';
@@ -57,40 +97,405 @@ import { SvgTermsHero } from '@datalayer/design/lib/svg/SvgTermsHero';
57
97
  import { SvgTutorialsHero } from '@datalayer/design/lib/svg/SvgTutorialsHero';
58
98
  import { SvgUsecasesHero } from '@datalayer/design/lib/svg/SvgUsecasesHero';
59
99
  export const PRINCIPAL_AVATAR_ICONS = [
60
- { name: 'AlienMonsterIcon', label: 'Alien monster', Icon: AlienMonsterIcon },
61
- { name: 'AstronautIcon', label: 'Astronaut', Icon: AstronautIcon },
62
- { name: 'ConstructionWorkerIcon', label: 'Construction worker', Icon: ConstructionWorkerIcon },
63
- { name: 'CowboyHatFaceIcon', label: 'Cowboy', Icon: CowboyHatFaceIcon },
64
- { name: 'DragonFaceIcon', label: 'Dragon', Icon: DragonFaceIcon },
65
- { name: 'ElfManIcon', label: 'Elf', Icon: ElfManIcon },
66
- { name: 'FlyingSaucerIcon', label: 'Flying saucer', Icon: FlyingSaucerIcon },
67
- { name: 'GremlinIcon', label: 'Gremlin', Icon: GremlinIcon },
68
- { name: 'GrinningFaceIcon', label: 'Grinning face', Icon: GrinningFaceIcon },
69
- { name: 'LizardIcon', label: 'Lizard', Icon: LizardIcon },
70
- { name: 'MagicWandIcon', label: 'Magic wand', Icon: MagicWandIcon },
71
- { name: 'ManOfficeWorkerIcon', label: 'Office worker', Icon: ManOfficeWorkerIcon },
72
- { name: 'ManTechnologistIcon', label: 'Man technologist', Icon: ManTechnologistIcon },
73
- { name: 'NinjaIcon', label: 'Ninja', Icon: NinjaIcon },
74
- { name: 'PenguinIcon', label: 'Penguin', Icon: PenguinIcon },
75
- { name: 'PersonSurfingIcon', label: 'Surfer', Icon: PersonSurfingIcon },
76
- { name: 'PersonSwimmingIcon', label: 'Swimmer', Icon: PersonSwimmingIcon },
77
- { name: 'RingedPlanetIcon', label: 'Planet', Icon: RingedPlanetIcon },
78
- { name: 'RobotIcon', label: 'Robot', Icon: RobotIcon },
79
- { name: 'RocketIcon', label: 'Rocket', Icon: RocketIcon },
80
- { name: 'SantaClausIcon', label: 'Santa', Icon: SantaClausIcon },
81
- { name: 'ScientistIcon', label: 'Scientist', Icon: ScientistIcon },
82
- { name: 'SharkIcon', label: 'Shark', Icon: SharkIcon },
83
- { name: 'SnowmanIcon', label: 'Snowman', Icon: SnowmanIcon },
84
- { name: 'StarIcon', label: 'Star', Icon: StarIcon },
85
- { name: 'StudentWomanIcon', label: 'Student', Icon: StudentWomanIcon },
86
- { name: 'SunIcon', label: 'Sun', Icon: SunIcon },
87
- { name: 'WhaleSpoutingIcon', label: 'Whale', Icon: WhaleSpoutingIcon },
88
- { name: 'WomanTechnologistIcon', label: 'Woman technologist', Icon: WomanTechnologistIcon },
100
+ {
101
+ name: 'AlienMaskIcon',
102
+ label: 'Alien mask',
103
+ description: 'A mask of an alien face, worn for disguise.',
104
+ Icon: AlienMaskIcon,
105
+ },
106
+ {
107
+ name: 'AlienMonsterIcon',
108
+ label: 'Alien monster',
109
+ description: 'The pixelated alien of the arcade cabinets.',
110
+ Icon: AlienMonsterIcon,
111
+ },
112
+ {
113
+ name: 'AstronautIcon',
114
+ label: 'Astronaut',
115
+ description: 'A person in a spacesuit, ready for orbit.',
116
+ Icon: AstronautIcon,
117
+ },
118
+ {
119
+ name: 'AtomSymbolIcon',
120
+ label: 'Atom',
121
+ description: 'A nucleus circled by electrons, the mark of physics.',
122
+ Icon: AtomSymbolIcon,
123
+ },
124
+ {
125
+ name: 'BankIcon',
126
+ label: 'Bank',
127
+ description: 'A columned building where money is kept.',
128
+ Icon: BankIcon,
129
+ },
130
+ {
131
+ name: 'BlackNibIcon',
132
+ label: 'Black nib',
133
+ description: 'The nib of a fountain pen, poised to write.',
134
+ Icon: BlackNibIcon,
135
+ },
136
+ {
137
+ name: 'BriefcaseIcon',
138
+ label: 'Briefcase',
139
+ description: 'A case for papers, carried to work.',
140
+ Icon: BriefcaseIcon,
141
+ },
142
+ {
143
+ name: 'BuildingClassicIcon',
144
+ label: 'Classic building',
145
+ description: 'A columned building of the classical order.',
146
+ Icon: BuildingClassicIcon,
147
+ },
148
+ {
149
+ name: 'BuildingConstructionIcon',
150
+ label: 'Building construction',
151
+ description: 'A building going up, crane and all.',
152
+ Icon: BuildingConstructionIcon,
153
+ },
154
+ {
155
+ name: 'BuildingOfficeIcon',
156
+ label: 'Office building',
157
+ description: 'An office block of many identical windows.',
158
+ Icon: BuildingOfficeIcon,
159
+ },
160
+ {
161
+ name: 'BullseyeIcon',
162
+ label: 'Bullseye',
163
+ description: 'A dart in the centre of the target.',
164
+ Icon: BullseyeIcon,
165
+ },
166
+ {
167
+ name: 'CloudGreyIcon',
168
+ label: 'Cloud',
169
+ description: 'A cloud, of the sky or of the servers.',
170
+ Icon: CloudGreyIcon,
171
+ },
172
+ {
173
+ name: 'ConstructionIcon',
174
+ label: 'Construction',
175
+ description: 'A striped barrier: work in progress.',
176
+ Icon: ConstructionIcon,
177
+ },
178
+ {
179
+ name: 'ConstructionWorkerIcon',
180
+ label: 'Construction worker',
181
+ description: 'A worker in a hard hat.',
182
+ Icon: ConstructionWorkerIcon,
183
+ },
184
+ {
185
+ name: 'CowboyHatFaceIcon',
186
+ label: 'Cowboy',
187
+ description: 'A grinning face under a cowboy hat.',
188
+ Icon: CowboyHatFaceIcon,
189
+ },
190
+ {
191
+ name: 'DashboardGreyIcon',
192
+ label: 'Dashboard',
193
+ description: 'A gauge with its needle in the red.',
194
+ Icon: DashboardGreyIcon,
195
+ },
196
+ {
197
+ name: 'DnaIcon',
198
+ label: 'DNA',
199
+ description: 'The double helix that carries the code of life.',
200
+ Icon: DnaIcon,
201
+ },
202
+ {
203
+ name: 'DraftIcon',
204
+ label: 'Draft',
205
+ description: 'A sheet still being drawn up.',
206
+ Icon: DraftIcon,
207
+ },
208
+ {
209
+ name: 'DragonFaceIcon',
210
+ label: 'Dragon face',
211
+ description: 'The face of a dragon, whiskers and horns.',
212
+ Icon: DragonFaceIcon,
213
+ },
214
+ {
215
+ name: 'DragonIcon',
216
+ label: 'Dragon',
217
+ description: 'A dragon in full, coiled and winged.',
218
+ Icon: DragonIcon,
219
+ },
220
+ {
221
+ name: 'ElfManIcon',
222
+ label: 'Elf',
223
+ description: 'A pointy-eared elf of the folk tales.',
224
+ Icon: ElfManIcon,
225
+ },
226
+ {
227
+ name: 'FireIcon',
228
+ label: 'Fire',
229
+ description: 'A flame — hot, fast, or simply on fire.',
230
+ Icon: FireIcon,
231
+ },
232
+ {
233
+ name: 'FireworksIcon',
234
+ label: 'Fireworks',
235
+ description: 'Fireworks bursting over a night sky.',
236
+ Icon: FireworksIcon,
237
+ },
238
+ {
239
+ name: 'FlyingSaucerIcon',
240
+ label: 'Flying saucer',
241
+ description: 'A saucer from elsewhere, beam and all.',
242
+ Icon: FlyingSaucerIcon,
243
+ },
244
+ {
245
+ name: 'FourLeafCloverIcon',
246
+ label: 'Four-leaf clover',
247
+ description: 'The rare fourth leaf, for luck.',
248
+ Icon: FourLeafCloverIcon,
249
+ },
250
+ {
251
+ name: 'GraduationCapIcon',
252
+ label: 'Graduation cap',
253
+ description: 'The square cap thrown on graduation day.',
254
+ Icon: GraduationCapIcon,
255
+ },
256
+ {
257
+ name: 'GremlinIcon',
258
+ label: 'Gremlin',
259
+ description: 'A small mischief-maker, blamed for the bugs.',
260
+ Icon: GremlinIcon,
261
+ },
262
+ {
263
+ name: 'GrinningFaceIcon',
264
+ label: 'Grinning face',
265
+ description: 'A face grinning from ear to ear.',
266
+ Icon: GrinningFaceIcon,
267
+ },
268
+ {
269
+ name: 'HouseIcon',
270
+ label: 'House',
271
+ description: 'A house with its roof and door.',
272
+ Icon: HouseIcon,
273
+ },
274
+ {
275
+ name: 'LizardIcon',
276
+ label: 'Lizard',
277
+ description: 'A lizard, still and watchful.',
278
+ Icon: LizardIcon,
279
+ },
280
+ {
281
+ name: 'MagicWandIcon',
282
+ label: 'Magic wand',
283
+ description: 'A wand trailing sparks.',
284
+ Icon: MagicWandIcon,
285
+ },
286
+ {
287
+ name: 'ManOfficeWorkerIcon',
288
+ label: 'Office worker',
289
+ description: 'A worker at a desk in an office.',
290
+ Icon: ManOfficeWorkerIcon,
291
+ },
292
+ {
293
+ name: 'ManTechnologistIcon',
294
+ label: 'Man technologist',
295
+ description: 'A man at a laptop, writing code.',
296
+ Icon: ManTechnologistIcon,
297
+ },
298
+ {
299
+ name: 'MusicalNoteIcon',
300
+ label: 'Musical note',
301
+ description: 'A single note off a stave.',
302
+ Icon: MusicalNoteIcon,
303
+ },
304
+ {
305
+ name: 'NinjaIcon',
306
+ label: 'Ninja',
307
+ description: 'A masked figure, quick and unseen.',
308
+ Icon: NinjaIcon,
309
+ },
310
+ {
311
+ name: 'OpenHandsIcon',
312
+ label: 'Open hands',
313
+ description: 'Two open hands, offered or welcoming.',
314
+ Icon: OpenHandsIcon,
315
+ },
316
+ {
317
+ name: 'PenIcon',
318
+ label: 'Pen',
319
+ description: 'A ballpoint pen for everyday writing.',
320
+ Icon: PenIcon,
321
+ },
322
+ {
323
+ name: 'PenguinIcon',
324
+ label: 'Penguin',
325
+ description: 'A penguin in its black and white.',
326
+ Icon: PenguinIcon,
327
+ },
328
+ {
329
+ name: 'PersonSurfingIcon',
330
+ label: 'Surfer',
331
+ description: 'A surfer riding the face of a wave.',
332
+ Icon: PersonSurfingIcon,
333
+ },
334
+ {
335
+ name: 'PersonSwimmingIcon',
336
+ label: 'Swimmer',
337
+ description: 'A swimmer mid-stroke.',
338
+ Icon: PersonSwimmingIcon,
339
+ },
340
+ {
341
+ name: 'PictureFramedIcon',
342
+ label: 'Framed picture',
343
+ description: 'A painting hung in its frame.',
344
+ Icon: PictureFramedIcon,
345
+ },
346
+ {
347
+ name: 'PictureIcon',
348
+ label: 'Picture',
349
+ description: 'A photograph of mountains and sun.',
350
+ Icon: PictureIcon,
351
+ },
352
+ {
353
+ name: 'PlaneDepartureIcon',
354
+ label: 'Plane',
355
+ description: 'An aeroplane lifting off the runway.',
356
+ Icon: PlaneDepartureIcon,
357
+ },
358
+ {
359
+ name: 'RingedPlanetIcon',
360
+ label: 'Planet',
361
+ description: 'A planet circled by its rings.',
362
+ Icon: RingedPlanetIcon,
363
+ },
364
+ {
365
+ name: 'RobotIcon',
366
+ label: 'Robot',
367
+ description: 'The square face of a robot.',
368
+ Icon: RobotIcon,
369
+ },
370
+ {
371
+ name: 'RocketIcon',
372
+ label: 'Rocket',
373
+ description: 'A rocket climbing on its exhaust.',
374
+ Icon: RocketIcon,
375
+ },
376
+ {
377
+ name: 'SantaClausIcon',
378
+ label: 'Santa',
379
+ description: 'Santa Claus, red hat and white beard.',
380
+ Icon: SantaClausIcon,
381
+ },
382
+ {
383
+ name: 'SatelliteIcon',
384
+ label: 'Satellite',
385
+ description: 'A satellite with its panels spread.',
386
+ Icon: SatelliteIcon,
387
+ },
388
+ {
389
+ name: 'ScientistIcon',
390
+ label: 'Scientist',
391
+ description: 'A scientist at the microscope.',
392
+ Icon: ScientistIcon,
393
+ },
394
+ {
395
+ name: 'SharkIcon',
396
+ label: 'Shark',
397
+ description: 'A shark, fin first.',
398
+ Icon: SharkIcon,
399
+ },
400
+ {
401
+ name: 'SnowmanIcon',
402
+ label: 'Snowman',
403
+ description: 'A snowman built up in the cold.',
404
+ Icon: SnowmanIcon,
405
+ },
406
+ {
407
+ name: 'SpaceInvadersAlien1Icon',
408
+ label: 'Space invader 1',
409
+ description: 'The first invader of the arcade fleet.',
410
+ Icon: SpaceInvadersAlien1Icon,
411
+ },
412
+ {
413
+ name: 'SpaceInvadersAlien2Icon',
414
+ label: 'Space invader 2',
415
+ description: 'The second invader of the arcade fleet.',
416
+ Icon: SpaceInvadersAlien2Icon,
417
+ },
418
+ {
419
+ name: 'SpaceInvadersAlien3Icon',
420
+ label: 'Space invader 3',
421
+ description: 'The third invader of the arcade fleet.',
422
+ Icon: SpaceInvadersAlien3Icon,
423
+ },
424
+ {
425
+ name: 'SparklerIcon',
426
+ label: 'Sparkler',
427
+ description: 'A hand-held sparkler throwing light.',
428
+ Icon: SparklerIcon,
429
+ },
430
+ {
431
+ name: 'StarIcon',
432
+ label: 'Star',
433
+ description: 'A five-pointed star.',
434
+ Icon: StarIcon,
435
+ },
436
+ {
437
+ name: 'StudentIcon',
438
+ label: 'Student',
439
+ description: 'A student with book and cap.',
440
+ Icon: StudentIcon,
441
+ },
442
+ {
443
+ name: 'StudioMicrophoneIcon',
444
+ label: 'Studio microphone',
445
+ description: 'The microphone of a recording studio.',
446
+ Icon: StudioMicrophoneIcon,
447
+ },
448
+ {
449
+ name: 'SunIcon',
450
+ label: 'Sun',
451
+ description: 'The sun at full strength.',
452
+ Icon: SunIcon,
453
+ },
454
+ {
455
+ name: 'WavingHandIcon',
456
+ label: 'Waving hand',
457
+ description: 'A hand raised in hello.',
458
+ Icon: WavingHandIcon,
459
+ },
460
+ {
461
+ name: 'WhaleSpoutingIcon',
462
+ label: 'Whale',
463
+ description: 'A whale blowing a spout of water.',
464
+ Icon: WhaleSpoutingIcon,
465
+ },
466
+ {
467
+ name: 'WomanTechnologistIcon',
468
+ label: 'Woman technologist',
469
+ description: 'A woman at a laptop, writing code.',
470
+ Icon: WomanTechnologistIcon,
471
+ },
472
+ {
473
+ name: 'WrappedGiftIcon',
474
+ label: 'Wrapped gift',
475
+ description: 'A present tied with a ribbon.',
476
+ Icon: WrappedGiftIcon,
477
+ },
478
+ {
479
+ name: 'WritingHandIcon',
480
+ label: 'Writing hand',
481
+ description: 'A hand writing with a pen.',
482
+ Icon: WritingHandIcon,
483
+ },
484
+ {
485
+ name: 'YinYangIcon',
486
+ label: 'Yin yang',
487
+ description: 'The two halves that make a whole.',
488
+ Icon: YinYangIcon,
489
+ },
89
490
  ];
90
491
  export const PRINCIPAL_BANNERS = [
91
492
  { name: 'SvgAboutHero', label: 'About', Component: SvgAboutHero },
92
493
  { name: 'SvgAgentsHero', label: 'Agents', Component: SvgAgentsHero },
93
- { name: 'SvgAgentsHomeHero', label: 'Agents home', Component: SvgAgentsHomeHero },
494
+ {
495
+ name: 'SvgAgentsHomeHero',
496
+ label: 'Agents home',
497
+ Component: SvgAgentsHomeHero,
498
+ },
94
499
  { name: 'SvgBlogHero', label: 'Blog', Component: SvgBlogHero },
95
500
  { name: 'SvgCareersHero', label: 'Careers', Component: SvgCareersHero },
96
501
  { name: 'SvgChangelogHero', label: 'Changelog', Component: SvgChangelogHero },
@@ -99,7 +504,11 @@ export const PRINCIPAL_BANNERS = [
99
504
  { name: 'SvgEarthHero', label: 'Earth', Component: SvgEarthHero },
100
505
  { name: 'SvgEvalsHero', label: 'Evaluations', Component: SvgEvalsHero },
101
506
  { name: 'SvgEventsHero', label: 'Events', Component: SvgEventsHero },
102
- { name: 'SvgIntegrationsHero', label: 'Integrations', Component: SvgIntegrationsHero },
507
+ {
508
+ name: 'SvgIntegrationsHero',
509
+ label: 'Integrations',
510
+ Component: SvgIntegrationsHero,
511
+ },
103
512
  { name: 'SvgLoginHero', label: 'Login', Component: SvgLoginHero },
104
513
  { name: 'SvgPartnersHero', label: 'Partners', Component: SvgPartnersHero },
105
514
  { name: 'SvgPricingHero', label: 'Pricing', Component: SvgPricingHero },
@@ -145,28 +554,95 @@ export function PrincipalBannerImage({ banner, height = 180, }) {
145
554
  export function PrincipalAvatarPicker({ value, onChange, disabled = false, }) {
146
555
  const [open, setOpen] = useState(false);
147
556
  const selected = PRINCIPAL_AVATAR_ICONS.find(option => option.name === value);
148
- return (_jsxs(_Fragment, { children: [_jsx(Button, { type: "button", disabled: disabled, onClick: () => setOpen(true), children: selected ? `Change Avatar (${selected.label})` : 'Choose Avatar' }), open ? (_jsx(Dialog, { title: "Choose an Avatar", onClose: () => setOpen(false), width: "large", sx: { width: 'min(720px, calc(100vw - 32px))', maxWidth: 'none' }, children: _jsx(Box, { sx: {
557
+ return (_jsxs(_Fragment, { children: [_jsx(Button, { type: "button", disabled: disabled, onClick: () => setOpen(true), children: selected ? `Change Avatar (${selected.label})` : 'Choose Avatar' }), open ? (_jsx(Dialog, { title: "Choose an Avatar", onClose: () => setOpen(false),
558
+ // The widest the dialog names — 640px — which is what it falls
559
+ // back to should the width below ever stop applying.
560
+ width: "xlarge",
561
+ /*
562
+ * Wider than any name of the scale, for the twelve avatars of a
563
+ * line to have room, and bounded by the window.
564
+ *
565
+ * Under `&&`, which doubles the specificity of the class it
566
+ * generates: the width of a named size is written
567
+ * `.prc-Dialog-Dialog:where([data-width=xlarge])`, whose `:where`
568
+ * weighs nothing, so the rule and a plain `sx` are of the very
569
+ * same specificity and the one applied is whichever the
570
+ * stylesheets happen to order last.
571
+ */
572
+ sx: {
573
+ '&&': {
574
+ width: 'min(1080px, calc(100vw - 32px))',
575
+ maxWidth: 'none',
576
+ },
577
+ }, children: _jsx(Box, { sx: {
149
578
  display: 'grid',
150
- gridTemplateColumns: 'repeat(auto-fill, minmax(72px, 1fr))',
579
+ // Twelve to a line, whatever the dialog is wide: the columns
580
+ // share it evenly and `minmax(0, …)` lets them shrink under
581
+ // their content, which a long name would otherwise widen.
582
+ gridTemplateColumns: [
583
+ 'repeat(6, minmax(0, 1fr))',
584
+ 'repeat(12, minmax(0, 1fr))',
585
+ ],
151
586
  gap: 2,
152
- }, children: PRINCIPAL_AVATAR_ICONS.map(({ name, label, Icon }) => (_jsx(Button, { type: "button", "aria-label": label, "aria-pressed": value === name, onClick: () => {
153
- onChange(name);
154
- setOpen(false);
155
- }, sx: {
156
- height: 72,
157
- p: 1,
158
- borderColor: value === name ? 'accent.emphasis' : 'border.default',
159
- bg: value === name ? 'accent.subtle' : 'canvas.default',
160
- }, children: _jsx(Icon, { size: 52, colored: true }) }, name))) }) })) : null] }));
587
+ }, children: PRINCIPAL_AVATAR_ICONS.map(({ name, label, description, Icon }) => (
588
+ // A button drawn as a card rather than a Primer `Button`: the
589
+ // avatar is named under it, as the banners are under theirs.
590
+ // The name under a card is clipped when it is long, and a
591
+ // picture says only so much: the tooltip gives the whole name
592
+ // and what the picture is of.
593
+ _jsx(Tooltip, { text: description ? `${label} — ${description}` : label, direction: "n", children: _jsxs(Box, { as: "button", type: "button", "aria-label": description ? `${label} — ${description}` : label, "aria-pressed": value === name, onClick: () => {
594
+ onChange(name);
595
+ setOpen(false);
596
+ }, sx: {
597
+ display: 'block',
598
+ width: '100%',
599
+ p: 0,
600
+ overflow: 'hidden',
601
+ appearance: 'none',
602
+ color: 'fg.default',
603
+ cursor: 'pointer',
604
+ border: '1px solid',
605
+ borderRadius: 2,
606
+ borderColor: value === name ? 'accent.emphasis' : 'border.default',
607
+ bg: value === name ? 'accent.subtle' : 'canvas.default',
608
+ ':hover': { borderColor: 'accent.emphasis' },
609
+ }, children: [_jsx(Box, { sx: {
610
+ height: 72,
611
+ display: 'flex',
612
+ alignItems: 'center',
613
+ justifyContent: 'center',
614
+ }, children: _jsx(Icon, { size: 52, themed: true, colormode: true }) }), _jsx(Text, { sx: {
615
+ display: 'block',
616
+ px: 2,
617
+ py: 1,
618
+ fontSize: 0,
619
+ textAlign: 'center',
620
+ // A name too long for the card is cut rather than
621
+ // stretching the grid it sits in.
622
+ overflow: 'hidden',
623
+ textOverflow: 'ellipsis',
624
+ whiteSpace: 'nowrap',
625
+ }, children: label })] }) }, name))) }) })) : null] }));
161
626
  }
162
627
  export function PrincipalBannerPicker({ value, onChange, disabled = false, showPreview = true, }) {
163
628
  const [open, setOpen] = useState(false);
164
629
  const [selectedName, setSelectedName] = useState(value);
165
630
  useEffect(() => setSelectedName(value), [value]);
166
631
  const selected = PRINCIPAL_BANNERS.find(option => option.name === selectedName);
167
- return (_jsxs(_Fragment, { children: [showPreview && selected ? (_jsx(Box, { sx: { mb: 2 }, children: _jsx(PrincipalBannerImage, { banner: selected.name, height: 120 }) })) : null, _jsx(Button, { type: "button", disabled: disabled, onClick: () => setOpen(true), children: selected ? `Change Banner (${selected.label})` : 'Choose Banner' }), open ? (_jsx(Dialog, { title: "Choose a Banner", onClose: () => setOpen(false), width: "xlarge", sx: { width: 'min(960px, calc(100vw - 32px))', maxWidth: 'none' }, children: _jsx(Box, { sx: {
632
+ return (_jsxs(_Fragment, { children: [showPreview && selected ? (_jsx(Box, { sx: { mb: 2 }, children: _jsx(PrincipalBannerImage, { banner: selected.name, height: 120 }) })) : null, _jsx(Button, { type: "button", disabled: disabled, onClick: () => setOpen(true), children: selected ? `Change Banner (${selected.label})` : 'Choose Banner' }), open ? (_jsx(Dialog, { title: "Choose a Banner", onClose: () => setOpen(false), width: "xlarge",
633
+ // Under `&&` for the reason given on the avatar picker: a plain
634
+ // `sx` ties with the named width and may lose to it.
635
+ sx: {
636
+ '&&': {
637
+ width: 'min(960px, calc(100vw - 32px))',
638
+ maxWidth: 'none',
639
+ },
640
+ }, children: _jsx(Box, { sx: {
168
641
  display: 'grid',
169
- gridTemplateColumns: ['1fr', 'repeat(3, minmax(0, 1fr))'],
642
+ // Four to a row, so a banner is seen against its neighbours
643
+ // rather than one at a time; one column on a narrow overlay,
644
+ // where four would be four slivers.
645
+ gridTemplateColumns: ['1fr', 'repeat(4, minmax(0, 1fr))'],
170
646
  gap: 3,
171
647
  }, children: PRINCIPAL_BANNERS.map(({ name, label, Component }) => (_jsxs(Box, { as: "button", type: "button", "aria-label": label, "aria-pressed": selectedName === name, onClick: () => {
172
648
  setSelectedName(name);
@@ -182,7 +658,9 @@ export function PrincipalBannerPicker({ value, onChange, disabled = false, showP
182
658
  cursor: 'pointer',
183
659
  border: '1px solid',
184
660
  borderRadius: 2,
185
- borderColor: selectedName === name ? 'accent.emphasis' : 'border.default',
661
+ borderColor: selectedName === name
662
+ ? 'accent.emphasis'
663
+ : 'border.default',
186
664
  bg: selectedName === name ? 'accent.subtle' : 'canvas.default',
187
665
  textAlign: 'left',
188
666
  ':hover': { borderColor: 'accent.emphasis' },
@@ -21,7 +21,7 @@ export function PrincipalAvatar({ kind, avatarUrl, avatarIcon, alt, size = 20, s
21
21
  justifyContent: 'center',
22
22
  overflow: 'hidden',
23
23
  borderRadius: square ? 2 : '50%',
24
- }, "aria-label": alt || `${kind} avatar`, children: _jsx(SelectedIcon, { size: size, colored: true }) }));
24
+ }, "aria-label": alt || `${kind} avatar`, children: _jsx(SelectedIcon, { size: size, themed: true, colormode: true }) }));
25
25
  }
26
26
  if (kind === 'personal') {
27
27
  return (_jsx(UserAvatar, { avatarUrl: avatarUrl, avatarIcon: avatarIcon, size: size, square: square, iconSize: getFallbackIconSize(size), className: className }));
@@ -2021,8 +2021,17 @@ export const useCache = ({ loginRoute = '/login' } = {}) => {
2021
2021
  onSuccess: (resp, _variables) => {
2022
2022
  if (resp.success && resp.document) {
2023
2023
  const document = toDocument(resp.document);
2024
- // Set detail cache
2025
- queryClient.setQueryData(queryKeys.documents.detail(document.id), document);
2024
+ /*
2025
+ * The creation answer carries no model — the spacer keeps the
2026
+ * model with the content, and only the GET of a document answers
2027
+ * with it. Seeding the detail cache here would hand the editor a
2028
+ * document without a model, shown as a blank page: the cache is
2029
+ * invalidated instead, so an editor opening on the creation reads
2030
+ * the document from the server, model included.
2031
+ */
2032
+ queryClient.invalidateQueries({
2033
+ queryKey: queryKeys.documents.detail(document.id),
2034
+ });
2026
2035
  // Refetch all document queries immediately (including bySpace)
2027
2036
  queryClient.refetchQueries({
2028
2037
  queryKey: queryKeys.documents.all(),
@@ -1,3 +1,7 @@
1
+ /*
2
+ * Copyright (c) 2023-2025 Datalayer, Inc.
3
+ * Distributed under the terms of the Modified BSD License.
4
+ */
1
5
  /*
2
6
  * Copyright (c) 2023-2026 Datalayer, Inc.
3
7
  * Distributed under the terms of the Modified BSD License.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@datalayer/core",
3
- "version": "1.1.57",
3
+ "version": "1.1.59",
4
4
  "type": "module",
5
5
  "workspaces": [
6
6
  ".",