@nebulahome/package-sdk 1.3.0 → 1.4.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.
package/CHANGELOG.md CHANGED
@@ -3,6 +3,12 @@
3
3
  The SDK's version is the version of the package API the platform implements: a minor version adds
4
4
  to it, a major one breaks it, and a patch leaves it as it is.
5
5
 
6
+ ## 1.4.0
7
+
8
+ - **Toasts.** `useToast()` from `@nebulahome/package-sdk/ui` shows the interface's own toasts -
9
+ `success`, `warning`, `error`, `info`, each with a title, a line or two and at most one action -
10
+ for the outcome of something the viewer just did.
11
+
6
12
  ## 1.3.0
7
13
 
8
14
  - **The page's actions in its header.** `<PageActions>` from `@nebulahome/package-sdk/ui` draws
package/README.md CHANGED
@@ -140,6 +140,22 @@ import { sunPosition } from '@nebulahome/package-sdk/sun';
140
140
  const { elevation, azimuth } = sunPosition(at, { latitude, longitude });
141
141
  ```
142
142
 
143
+ ## Toasts
144
+
145
+ The interface's own toasts, for the outcome of something the viewer just did (since 1.4):
146
+
147
+ ```tsx
148
+ const toast = useToast();
149
+ const save = usePackageMutation('rules.save');
150
+
151
+ try {
152
+ await save.mutate(rules);
153
+ toast.success({ title: t('save.done', 'Saved') });
154
+ } catch (error) {
155
+ toast.error({ title: t('save.failed', "Couldn't save"), message: String(error) });
156
+ }
157
+ ```
158
+
143
159
  ## Entry points
144
160
 
145
161
  | Import | What |
@@ -189,8 +205,9 @@ git tag package-sdk@<version> && git push origin package-sdk@<version>
189
205
  ```
190
206
 
191
207
  `.github/workflows/release-package-sdk.yml` checks the tag says the package's version, runs the
192
- SDK's gates and publishes a GitHub release with the archive npm will receive. The maintainer
193
- publishes that archive, signed in to npm:
208
+ SDK's gates and keeps the archive npm will receive as the run's artifact; it makes no GitHub
209
+ release, npm is where the SDK is published. The maintainer downloads that artifact from the run
210
+ and publishes it, signed in to npm:
194
211
 
195
212
  ```sh
196
213
  npm publish nebulahome-package-sdk-<version>.tgz
@@ -6850,7 +6850,7 @@ function composeFileProblems(text, settingKeys) {
6850
6850
  * the two are compared before a package is installed or started (PACKAGES_DOCS.md 11).
6851
6851
  */
6852
6852
  /** The SDK's own version, `1.0.0`. */
6853
- const SDK_VERSION = "1.3.0";
6853
+ const SDK_VERSION = "1.4.0";
6854
6854
  //#endregion
6855
6855
  //#region src/vite/catalogues.ts
6856
6856
  /**
@@ -7,6 +7,6 @@
7
7
  * the two are compared before a package is installed or started (PACKAGES_DOCS.md 11).
8
8
  */
9
9
  /** The SDK's own version, `1.0.0`. */
10
- const SDK_VERSION = "1.3.0";
10
+ const SDK_VERSION = "1.4.0";
11
11
  //#endregion
12
12
  export { SDK_VERSION as t };
package/dist/styles.css CHANGED
@@ -276,6 +276,11 @@
276
276
  --text-display--line-height: 1.15;
277
277
  --text-display--letter-spacing: -0.03em;
278
278
 
279
+ /** The title of the screen every page shows while Nebula Home restarts or updates. */
280
+ --text-display-lg: 40px;
281
+ --text-display-lg--line-height: 1.1;
282
+ --text-display-lg--letter-spacing: -0.035em;
283
+
279
284
  /** The number an entity card is about; its unit follows at half size in `foreground-subtle`. */
280
285
  --text-reading: 32px;
281
286
  --text-reading--line-height: 1;
@@ -384,6 +389,92 @@
384
389
  * the dashes go by `animation-direction`.
385
390
  */
386
391
  --animate-energy-flow: energy-flow 1.6s linear infinite;
392
+
393
+ /*
394
+ * Nebula Home restarting or updating itself (boards N-Restart, N-Update, N-Transition-Flow): the
395
+ * ring turns slowly and unevenly while the core breathes out of phase, rings ripple out from the
396
+ * mark, its glow swells, a bar sweeps or shimmers, and the screen arrives out of a blur.
397
+ */
398
+ --animate-orbit-work: orbit 2.4s cubic-bezier(0.55, 0.1, 0.35, 0.9) infinite;
399
+ --animate-breathe: breathe 2.4s ease-in-out infinite;
400
+ --animate-ripple: ripple 2.4s cubic-bezier(0.2, 0.6, 0.3, 1) infinite;
401
+ --animate-glow: glow 3.6s ease-in-out infinite;
402
+ --animate-sweep: sweep 1.6s cubic-bezier(0.4, 0, 0.2, 1) infinite;
403
+ --animate-shimmer: shimmer 2s linear infinite;
404
+ --animate-enter: enter 0.8s cubic-bezier(0.2, 0.7, 0.2, 1) both;
405
+ --animate-arrive: arrive 0.6s cubic-bezier(0.2, 0.7, 0.2, 1) both;
406
+ }
407
+
408
+ /* The core of the mark breathing while Nebula Home works on itself. */
409
+ @keyframes breathe {
410
+ 0%,
411
+ 100% {
412
+ transform: scale(1);
413
+ opacity: 1;
414
+ }
415
+ 50% {
416
+ transform: scale(0.86);
417
+ opacity: 0.75;
418
+ }
419
+ }
420
+
421
+ /* A ring leaving the mark and fading as it widens. */
422
+ @keyframes ripple {
423
+ from {
424
+ transform: scale(0.55);
425
+ opacity: 0.55;
426
+ }
427
+ to {
428
+ transform: scale(1.9);
429
+ opacity: 0;
430
+ }
431
+ }
432
+
433
+ @keyframes glow {
434
+ 0%,
435
+ 100% {
436
+ opacity: 0.45;
437
+ }
438
+ 50% {
439
+ opacity: 0.8;
440
+ }
441
+ }
442
+
443
+ /* A bar that cannot say how far it is: a highlight crossing it again and again. */
444
+ @keyframes sweep {
445
+ from {
446
+ left: -40%;
447
+ }
448
+ to {
449
+ left: 100%;
450
+ }
451
+ }
452
+
453
+ /* A light passing along a bar that is moving. */
454
+ @keyframes shimmer {
455
+ from {
456
+ background-position: -200% 0;
457
+ }
458
+ to {
459
+ background-position: 200% 0;
460
+ }
461
+ }
462
+
463
+ /* A screen arriving out of a blur, a little small. */
464
+ @keyframes enter {
465
+ from {
466
+ opacity: 0;
467
+ transform: scale(0.96);
468
+ filter: blur(10px);
469
+ }
470
+ }
471
+
472
+ /* A note rising into place. */
473
+ @keyframes arrive {
474
+ from {
475
+ opacity: 0;
476
+ transform: translateY(10px);
477
+ }
387
478
  }
388
479
 
389
480
  /* One period of a wire's dash pattern, which is 12 units long: 2 drawn, 10 gap. */
@@ -566,6 +657,47 @@
566
657
  * The Matter mark's square, lit violet from its top-left corner: the broker's hero and its
567
658
  * dialogs' lead. Over the square's own ground, so it sits on `bg-surface-raised`.
568
659
  */
660
+ @utility modbus-glow {
661
+ background-image: radial-gradient(
662
+ 120% 120% at 0% 0%,
663
+ color-mix(in srgb, var(--color-cyan) 18%, transparent),
664
+ transparent 60%
665
+ );
666
+ }
667
+
668
+ /* The newer brokers' squares, each lit in its own mark's colour the same way. */
669
+ @utility thread-glow {
670
+ background-image: radial-gradient(
671
+ 120% 120% at 0% 0%,
672
+ color-mix(in srgb, var(--color-thread) 20%, transparent),
673
+ transparent 60%
674
+ );
675
+ }
676
+
677
+ @utility bluetooth-glow {
678
+ background-image: radial-gradient(
679
+ 120% 120% at 0% 0%,
680
+ color-mix(in srgb, #5b9dff 20%, transparent),
681
+ transparent 60%
682
+ );
683
+ }
684
+
685
+ @utility serial-glow {
686
+ background-image: radial-gradient(
687
+ 120% 120% at 0% 0%,
688
+ color-mix(in srgb, #f0c27b 18%, transparent),
689
+ transparent 60%
690
+ );
691
+ }
692
+
693
+ @utility infrared-glow {
694
+ background-image: radial-gradient(
695
+ 120% 120% at 0% 0%,
696
+ color-mix(in srgb, #f7895c 18%, transparent),
697
+ transparent 60%
698
+ );
699
+ }
700
+
569
701
  @utility matter-glow {
570
702
  background-image: radial-gradient(
571
703
  120% 120% at 0% 0%,
package/dist/ui.d.ts CHANGED
@@ -298,6 +298,32 @@ type PlatformLinkProps = LinkAttributes & {
298
298
  type PageActionsProps = {
299
299
  readonly children?: ReactNode;
300
300
  };
301
+ /** What a toast says. Since 1.4. */
302
+ type ToastMessage = {
303
+ /** A few words, no full stop. */
304
+ readonly title: string;
305
+ /** One or two lines. */
306
+ readonly message?: string;
307
+ /** The one thing to do about it; doing it closes the toast. */
308
+ readonly action?: {
309
+ readonly label: string;
310
+ readonly onSelect: () => void;
311
+ };
312
+ };
313
+ /**
314
+ * Shows one of the interface's toasts, one function per kind: bottom right, three at a time, the
315
+ * rest waiting their turn; the same toast twice is shown once. Since 1.4.
316
+ */
317
+ type Toasts = {
318
+ /** Confirms what was just done; stays 4 s. */
319
+ readonly success: (message: ToastMessage) => void;
320
+ /** Something that needs a look, not right now; stays 8 s. */
321
+ readonly warning: (message: ToastMessage) => void;
322
+ /** Something that failed; stays 10 s. */
323
+ readonly error: (message: ToastMessage) => void;
324
+ /** Something that started or changed; stays 6 s. */
325
+ readonly info: (message: ToastMessage) => void;
326
+ };
301
327
  /** What the interface lends to implement `/ui`. */
302
328
  type UiHost = {
303
329
  readonly usePackage: () => PackageInfo;
@@ -332,6 +358,8 @@ type UiHost = {
332
358
  readonly PageActions: ComponentType<PageActionsProps>;
333
359
  /** Since 1.3. */
334
360
  readonly useAreaActions: () => AreaActions;
361
+ /** Since 1.4. */
362
+ readonly useToast: () => Toasts;
335
363
  };
336
364
  //#endregion
337
365
  //#region src/ui/index.d.ts
@@ -454,6 +482,13 @@ export declare function useAreas(): readonly AreaView[];
454
482
  * @returns What changes the areas.
455
483
  */
456
484
  export declare function useAreaActions(): AreaActions;
485
+ /**
486
+ * Shows the interface's toasts: the outcome of something the viewer just did - "Saved", "Couldn't
487
+ * reach the printer" - from a handler, a mutation's `onError`, wherever. Since 1.4.
488
+ *
489
+ * @returns One function per kind: `success`, `warning`, `error`, `info`.
490
+ */
491
+ export declare function useToast(): Toasts;
457
492
  /**
458
493
  * A camera's latest still, fetched again every so often, or an image entity's picture, fetched
459
494
  * again when it changes: an address an `<img>` shows, let go of when a newer one replaces it.
@@ -516,4 +551,4 @@ export declare function PlatformLink(props: PlatformLinkProps): ReactElement;
516
551
  */
517
552
  export declare function PageActions(props: PageActionsProps): ReactElement;
518
553
  //#endregion
519
- export type { AreaActions, AreaDraft, AreaKind, AreaView, CardProps, ChangeCause, CustomEntityState, EntitiesFilter, EntityPicture, EntityView, EntityViewProps, History, HistoryQuery, HistorySeries, HistoryWindow, Locale, Mutation, MutationOptions, PackageCall, PackageInfo, PackageLinkProps, PackageNavigate, PackageRoute, PackageSettings, PageActionsProps, PageProps, PictureOptions, PlatformLinkProps, PlatformNavigate, PlatformTarget, PluralEnglish, RpcOptions, RpcState, SendCommand, SettingsPatch, StateHistoryPoint, Telemetry, TelemetryPoint, TelemetryQuery, TelemetryResolution, Theme, Translate, Translation, TranslationValues, UiHost, Viewer, VisibleSettings };
554
+ export type { AreaActions, AreaDraft, AreaKind, AreaView, CardProps, ChangeCause, CustomEntityState, EntitiesFilter, EntityPicture, EntityView, EntityViewProps, History, HistoryQuery, HistorySeries, HistoryWindow, Locale, Mutation, MutationOptions, PackageCall, PackageInfo, PackageLinkProps, PackageNavigate, PackageRoute, PackageSettings, PageActionsProps, PageProps, PictureOptions, PlatformLinkProps, PlatformNavigate, PlatformTarget, PluralEnglish, RpcOptions, RpcState, SendCommand, SettingsPatch, StateHistoryPoint, Telemetry, TelemetryPoint, TelemetryQuery, TelemetryResolution, Theme, ToastMessage, Toasts, Translate, Translation, TranslationValues, UiHost, Viewer, VisibleSettings };
package/dist/ui.js CHANGED
@@ -212,6 +212,15 @@ function useAreaActions() {
212
212
  return ui("useAreaActions", "1.3")();
213
213
  }
214
214
  /**
215
+ * Shows the interface's toasts: the outcome of something the viewer just did - "Saved", "Couldn't
216
+ * reach the printer" - from a handler, a mutation's `onError`, wherever. Since 1.4.
217
+ *
218
+ * @returns One function per kind: `success`, `warning`, `error`, `info`.
219
+ */
220
+ function useToast() {
221
+ return ui("useToast", "1.4")();
222
+ }
223
+ /**
215
224
  * A camera's latest still, fetched again every so often, or an image entity's picture, fetched
216
225
  * again when it changes: an address an `<img>` shows, let go of when a newer one replaces it.
217
226
  *
@@ -291,4 +300,4 @@ function PageActions(props) {
291
300
  return createElement(ui("PageActions", "1.3"), props);
292
301
  }
293
302
  //#endregion
294
- export { PackageLink, PageActions, PlatformLink, useAreaActions, useAreas, useCommand, useCustomEntity, useEntities, useEntity, useEntityPicture, useLocale, usePackage, usePackageCall, usePackageMutation, usePackageNavigate, usePackageRoute, usePackageRpc, usePackageSettings, usePlatformNavigate, usePortalContainer, useStateHistory, useTelemetry, useTheme, useTranslation, useViewer };
303
+ export { PackageLink, PageActions, PlatformLink, useAreaActions, useAreas, useCommand, useCustomEntity, useEntities, useEntity, useEntityPicture, useLocale, usePackage, usePackageCall, usePackageMutation, usePackageNavigate, usePackageRoute, usePackageRpc, usePackageSettings, usePlatformNavigate, usePortalContainer, useStateHistory, useTelemetry, useTheme, useToast, useTranslation, useViewer };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@nebulahome/package-sdk",
3
- "version": "1.3.0",
3
+ "version": "1.4.0",
4
4
  "description": "Write a NebulaHome package: declare it, build it, and run it on the platform.",
5
5
  "license": "MIT",
6
6
  "type": "module",
@@ -100,10 +100,10 @@
100
100
  "vitest": "^4.1.11",
101
101
  "yaml": "^2.9.0",
102
102
  "zod": "^4.5.4",
103
- "@nebulahome/contracts": "0.0.0",
104
- "@nebulahome/eslint-config": "0.0.0",
105
- "@nebulahome/tsconfig": "0.0.0",
106
- "@nebulahome/ui": "0.0.0"
103
+ "@nebulahome/contracts": "2026.10.0-alpha.23",
104
+ "@nebulahome/tsconfig": "2026.10.0-alpha.23",
105
+ "@nebulahome/eslint-config": "2026.10.0-alpha.23",
106
+ "@nebulahome/ui": "2026.10.0-alpha.23"
107
107
  },
108
108
  "scripts": {
109
109
  "build": "tsdown && node scripts/build-styles.js",