@mmstack/primitives 20.0.3 → 20.0.4
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/README.md +40 -3
- package/fesm2022/mmstack-primitives.mjs +58 -96
- package/fesm2022/mmstack-primitives.mjs.map +1 -1
- package/index.d.ts +58 -67
- package/package.json +1 -1
package/index.d.ts
CHANGED
|
@@ -420,65 +420,51 @@ type ElementVisibilitySignal = Signal<IntersectionObserverEntry | undefined> & {
|
|
|
420
420
|
declare function elementVisibility(target?: ElementRef<Element> | Element | Signal<ElementRef<Element> | Element | null>, opt?: ElementVisibilityOptions): ElementVisibilitySignal;
|
|
421
421
|
|
|
422
422
|
/**
|
|
423
|
-
* Reactively maps items from a source array
|
|
423
|
+
* Reactively maps items from a source array to a new array, creating stable signals for each item.
|
|
424
424
|
*
|
|
425
|
-
* This function
|
|
426
|
-
*
|
|
427
|
-
*
|
|
425
|
+
* This function is highly optimized for performance, similar to SolidJS's `mapArray`.
|
|
426
|
+
* For each item in the source array, it creates a stable signal that is passed to the mapping function.
|
|
427
|
+
* This ensures that downstream consumers only re-evaluate for items that have actually changed,
|
|
428
|
+
* or when items are added or removed from the list.
|
|
428
429
|
*
|
|
429
|
-
*
|
|
430
|
-
*
|
|
431
|
-
*
|
|
432
|
-
*
|
|
433
|
-
* that have changed, or when items are added/removed, rather than re-evaluating everything
|
|
434
|
-
* when the source array reference changes but items remain the same.
|
|
435
|
-
*
|
|
436
|
-
* It efficiently handles changes in the source array's length by reusing existing mapped
|
|
437
|
-
* results when possible, slicing when the array shrinks, and appending new mapped items
|
|
438
|
-
* when it grows.
|
|
430
|
+
* The type of signal passed to the `map` function depends on the source:
|
|
431
|
+
* - **Readonly `Signal`**: `map` receives a readonly `Signal<T>`.
|
|
432
|
+
* - **`WritableSignal`**: `map` receives a `WritableSignal<T>`, allowing two-way binding.
|
|
433
|
+
* - **`MutableSignal`**: `map` receives a `MutableSignal<T>`, allowing in-place mutation for performance.
|
|
439
434
|
*
|
|
440
435
|
* @template T The type of items in the source array.
|
|
441
436
|
* @template U The type of items in the resulting mapped array.
|
|
442
437
|
*
|
|
443
|
-
* @param source A
|
|
444
|
-
* The
|
|
445
|
-
* @param
|
|
446
|
-
*
|
|
447
|
-
*
|
|
448
|
-
* Use this signal within your mapping logic if you need reactivity
|
|
449
|
-
* tied to the specific item's value changes.
|
|
450
|
-
* - `index`: The number index of the item in the array.
|
|
451
|
-
* It should return the mapped value `U`.
|
|
452
|
-
* @param [opt] Optional `CreateSignalOptions<T>`. These options are passed directly
|
|
453
|
-
* to the `computed` signal created for each individual item (`Signal<T>`).
|
|
454
|
-
* This allows specifying options like a custom `equal` function for item comparison.
|
|
455
|
-
*
|
|
456
|
-
* @returns A `Signal<U[]>` containing the mapped array. This signal updates whenever
|
|
457
|
-
* the source array changes (either length or the values of its items).
|
|
438
|
+
* @param source A `Signal<T[]>` or a function returning `T[]`.
|
|
439
|
+
* @param map The mapping function. It receives a stable signal for the item and its index.
|
|
440
|
+
* @param options Optional configuration, including `CreateSignalOptions` for the item signals
|
|
441
|
+
* (e.g., a custom `equal` function) and an `onDestroy` callback for cleanup.
|
|
442
|
+
* @returns A `Signal<U[]>` containing the mapped array.
|
|
458
443
|
*
|
|
459
444
|
* @example
|
|
460
|
-
*
|
|
445
|
+
* // Writable example
|
|
461
446
|
* const sourceItems = signal([
|
|
462
447
|
* { id: 1, name: 'Apple' },
|
|
463
448
|
* { id: 2, name: 'Banana' }
|
|
464
449
|
* ]);
|
|
465
450
|
*
|
|
466
|
-
*
|
|
467
|
-
* sourceItems,
|
|
468
|
-
* (
|
|
469
|
-
*
|
|
470
|
-
*
|
|
471
|
-
*
|
|
472
|
-
*
|
|
473
|
-
*
|
|
474
|
-
* {
|
|
475
|
-
* );
|
|
476
|
-
* ```
|
|
477
|
-
* @remarks
|
|
478
|
-
* This function achieves its high performance by leveraging the new `linkedSignal`
|
|
479
|
-
* API from Angular, which allows for efficient memoization and reuse of array items.
|
|
451
|
+
* // The `itemSignal` is writable because `sourceItems` is a WritableSignal.
|
|
452
|
+
* const mappedItems = mapArray(sourceItems, (itemSignal, index) => ({
|
|
453
|
+
* label: computed(() => `${index}: ${itemSignal().name.toUpperCase()}`),
|
|
454
|
+
* setName: (newName: string) => itemSignal.update(item => ({ ...item, name: newName }))
|
|
455
|
+
* }));
|
|
456
|
+
*
|
|
457
|
+
* // This will update the original source signal.
|
|
458
|
+
* mappedItems()[0].setName('Avocado');
|
|
459
|
+
* // sourceItems() is now: [{ id: 1, name: 'Avocado' }, { id: 2, name: 'Banana' }]
|
|
480
460
|
*/
|
|
481
|
-
declare function mapArray<T, U>(source:
|
|
461
|
+
declare function mapArray<T, U>(source: MutableSignal<T[]>, map: (value: MutableSignal<T>, index: number) => U, options?: CreateSignalOptions<T> & {
|
|
462
|
+
onDestroy?: (value: U) => void;
|
|
463
|
+
}): Signal<U[]>;
|
|
464
|
+
declare function mapArray<T, U>(source: WritableSignal<T[]>, map: (value: WritableSignal<T>, index: number) => U, options?: CreateSignalOptions<T> & {
|
|
465
|
+
onDestroy?: (value: U) => void;
|
|
466
|
+
}): Signal<U[]>;
|
|
467
|
+
declare function mapArray<T, U>(source: Signal<T[]> | (() => T[]), map: (value: Signal<T>, index: number) => U, options?: CreateSignalOptions<T> & {
|
|
482
468
|
onDestroy?: (value: U) => void;
|
|
483
469
|
}): Signal<U[]>;
|
|
484
470
|
|
|
@@ -1196,6 +1182,33 @@ type UntilOptions = {
|
|
|
1196
1182
|
destroyRef?: DestroyRef;
|
|
1197
1183
|
injector?: Injector;
|
|
1198
1184
|
};
|
|
1185
|
+
/**
|
|
1186
|
+
* Creates a Promise that resolves when a signal's value satisfies a type predicate.
|
|
1187
|
+
*
|
|
1188
|
+
* This overload is used when the predicate function is a type guard (e.g., `(v): v is MyType`).
|
|
1189
|
+
* The returned promise will resolve with the narrowed type.
|
|
1190
|
+
*
|
|
1191
|
+
* @template T The base type of the signal's value.
|
|
1192
|
+
* @template U The narrowed type asserted by the predicate.
|
|
1193
|
+
* @param sourceSignal The signal to observe.
|
|
1194
|
+
* @param predicate A type guard function that returns `true` if the value is of type `U`.
|
|
1195
|
+
* @param options Optional configuration for timeout and explicit destruction.
|
|
1196
|
+
* @returns A Promise that resolves with the signal's value, narrowed to type `U`.
|
|
1197
|
+
*
|
|
1198
|
+
* @example
|
|
1199
|
+
* ```ts
|
|
1200
|
+
* const event = signal<Event | null>(null);
|
|
1201
|
+
*
|
|
1202
|
+
* // The returned promise is `Promise<MouseEvent>`
|
|
1203
|
+
* const mouseEventPromise = until(event, (e): e is MouseEvent => e instanceof MouseEvent);
|
|
1204
|
+
*
|
|
1205
|
+
* async function logMouseEvent() {
|
|
1206
|
+
* const me = await mouseEventPromise;
|
|
1207
|
+
* console.log(me.clientX); // `me` is correctly typed as MouseEvent
|
|
1208
|
+
* }
|
|
1209
|
+
* ```
|
|
1210
|
+
*/
|
|
1211
|
+
declare function until<T, U extends T>(sourceSignal: Signal<T>, predicate: (value: T) => value is U, options?: UntilOptions): Promise<U>;
|
|
1199
1212
|
/**
|
|
1200
1213
|
* Creates a Promise that resolves when a signal's value satisfies a given predicate.
|
|
1201
1214
|
*
|
|
@@ -1208,28 +1221,6 @@ type UntilOptions = {
|
|
|
1208
1221
|
* @param options Optional configuration for timeout and explicit destruction.
|
|
1209
1222
|
* @returns A Promise that resolves with the signal's value when the predicate is true,
|
|
1210
1223
|
* or rejects on timeout or context destruction.
|
|
1211
|
-
*
|
|
1212
|
-
* @example
|
|
1213
|
-
* ```ts
|
|
1214
|
-
* const count = signal(0);
|
|
1215
|
-
*
|
|
1216
|
-
* async function waitForCount() {
|
|
1217
|
-
* console.log('Waiting for count to be >= 3...');
|
|
1218
|
-
* try {
|
|
1219
|
-
* const finalCount = await until(count, c => c >= 3, { timeout: 5000 });
|
|
1220
|
-
* console.log(`Count reached: ${finalCount}`);
|
|
1221
|
-
* } catch (e: any) { // Ensure 'e' is typed if you access properties like e.message
|
|
1222
|
-
* console.error(e.message); // e.g., "until: Timeout after 5000ms."
|
|
1223
|
-
* }
|
|
1224
|
-
* }
|
|
1225
|
-
*
|
|
1226
|
-
* // Simulate updates
|
|
1227
|
-
* setTimeout(() => count.set(1), 500);
|
|
1228
|
-
* setTimeout(() => count.set(2), 1000);
|
|
1229
|
-
* setTimeout(() => count.set(3), 1500);
|
|
1230
|
-
*
|
|
1231
|
-
* waitForCount();
|
|
1232
|
-
* ```
|
|
1233
1224
|
*/
|
|
1234
1225
|
declare function until<T>(sourceSignal: Signal<T>, predicate: (value: T) => boolean, options?: UntilOptions): Promise<T>;
|
|
1235
1226
|
|