@valentin30/signal 0.0.3 → 0.0.5

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/dist/index.d.mts CHANGED
@@ -1,18 +1,42 @@
1
+ type Function = (...args: any[]) => any;
2
+
1
3
  type Maybe<T> = T | null | undefined;
2
4
 
3
- type Factory<Fn extends FactoryFunction> = Fn & {
5
+ type Factory<Fn extends Function> = Fn & {
4
6
  factory(factory: Maybe<Fn>): void;
5
7
  default(factory: Maybe<Fn>): void;
6
8
  configured(): boolean;
7
9
  };
8
- type FactoryFunction = (...args: any[]) => any;
10
+ declare function factory<Fn extends Function>(name: string): Factory<Fn>;
9
11
 
10
12
  interface Collector$1<T> {
11
13
  add(value: T): void;
14
+ collecting(): boolean;
12
15
  collect(callback: () => void): Readonly<Set<T>>;
16
+ ignore(callback: () => void): void;
17
+ }
18
+ type CollectorFactory = <T>() => Collector$1<T>;
19
+ declare const collector$1: Factory<CollectorFactory>;
20
+
21
+ type Callback = () => void;
22
+
23
+ declare function batch$1(callback: Callback): void;
24
+ declare function batch$1(callback: Callback, collector: Collector$1<Callback>): void;
25
+ declare function batch$1(callback: Callback, collector?: Collector$1<Callback>): void;
26
+ declare namespace batch$1 {
27
+ var collector: Factory<BatchCollectorFactory>;
28
+ }
29
+ type BatchCollectorFactory = () => Collector$1<Callback>;
30
+
31
+ declare function collector<T>(): Collector$1<T>;
32
+ declare class Collector<T> implements Collector$1<T> {
33
+ #private;
34
+ constructor(values: Set<T> | null);
35
+ collecting(): boolean;
36
+ add(value: T): void;
37
+ collect(callback: () => void): Set<T>;
38
+ ignore(callback: () => void): void;
13
39
  }
14
- type CollectorFactoryFunction = <T>() => Collector$1<T>;
15
- declare const collector$1: Factory<CollectorFactoryFunction>;
16
40
 
17
41
  type Equals<T> = (value: T, other: T) => boolean;
18
42
  interface Comparable<T> {
@@ -23,8 +47,6 @@ interface Reader<T> {
23
47
  read(): T;
24
48
  }
25
49
 
26
- type Callback = () => void;
27
-
28
50
  interface Subscription {
29
51
  subscribe(callback: Callback): Callback;
30
52
  unsubscribe(callback: Callback): void;
@@ -38,79 +60,70 @@ interface Signal$1<T> extends Reader<T>, Writer<T>, Comparable<T>, Subscription
38
60
  }
39
61
  interface ReadonlySignal<T> extends Reader<T>, Comparable<T>, Subscription {
40
62
  }
41
- type SignalFactoryFunction = <T>(value: T, equals?: Equals<T>) => Signal$1<T>;
42
- declare const signal$1: Factory<SignalFactoryFunction>;
43
-
44
- type ComposedFactoryFunction = <T>(compute: () => T, write: (value: T) => void, equals?: Equals<T>) => Signal$1<T>;
45
- declare const composed$1: Factory<ComposedFactoryFunction>;
46
-
47
- type ComputedFactoryFunction = <T>(compute: () => T, equals?: Equals<T>) => ReadonlySignal<T>;
48
- declare const computed$1: Factory<ComputedFactoryFunction>;
49
-
50
- type Effect = () => void;
51
- type EffectCallback = (init: boolean) => EffectCleanup | void;
52
- type EffectCleanup = (destroy: boolean) => void;
53
- type EffectFactoryFunction = (callback: EffectCallback) => Effect;
54
- declare const effect$1: Factory<EffectFactoryFunction>;
55
-
56
- declare function collector<T>(): Collector$1<T>;
57
- declare class Collector<T> implements Collector$1<T> {
58
- private values;
59
- constructor(values: Set<T> | null);
60
- add(value: T): void;
61
- collect(callback: () => void): Set<T>;
62
- }
63
+ type SignalFactory = <T>(value: T, equals?: Equals<T>) => Signal$1<T>;
64
+ declare const signal$1: Factory<SignalFactory>;
63
65
 
64
- declare function computed<T>(compute: () => T, equals?: Equals<T>): Computed<T>;
65
- declare namespace computed {
66
- var collector: Factory<ComputedCollectorFactoryFunction>;
66
+ declare function computed$1<T>(compute: () => T, equals?: Equals<T>): Computed<T>;
67
+ declare namespace computed$1 {
68
+ var collector: Factory<ComputedCollectorFactory>;
67
69
  }
68
- type ComputedCollectorFactoryFunction = () => Collector$1<ReadonlySignal<unknown>>;
70
+ type ComputedCollectorFactory = () => Collector$1<ReadonlySignal<unknown>>;
69
71
  declare class Computed<T> implements ReadonlySignal<T> {
70
- private empty;
71
- private value;
72
- private values;
73
- private dependencies;
74
- private readonly compute;
75
- private readonly equalsFn;
76
- private readonly listeners;
77
- private readonly collector;
78
- constructor(empty: boolean, value: T | undefined, values: unknown[], dependencies: Set<ReadonlySignal<unknown>>, listeners: Set<Callback>, collector: Collector$1<ReadonlySignal<unknown>>, compute: () => T, equals: Maybe<Equals<T>>);
79
- private dirty;
72
+ #private;
73
+ constructor(empty: boolean, value: T | undefined, values: [ReadonlySignal<unknown>, unknown][], dependencies: Set<ReadonlySignal<unknown>>, listeners: Set<Callback>, collector: Collector$1<ReadonlySignal<unknown>>, compute: () => T, equals: Maybe<Equals<T>>);
80
74
  read(): T;
81
75
  equals(other: T): boolean;
82
76
  subscribe(callback: Callback): Callback;
83
77
  unsubscribe(callback: Callback): void;
84
78
  }
85
79
 
86
- declare function composed<T>(compute: () => T, write: (value: T) => void, equals?: Equals<T>): Composed<T>;
87
- declare namespace composed {
88
- var collector: Factory<ComposedCollectorFactoryFunction>;
80
+ type ComposedBatcherFactory = () => Collector$1<Callback>;
81
+ type ComposedCollectorFactory = () => Collector$1<ReadonlySignal<unknown>>;
82
+ declare function composed$1<T>(compute: () => T, write: (value: T) => void, equals?: Equals<T>): Composed<T>;
83
+ declare namespace composed$1 {
84
+ var batcher: Factory<ComposedBatcherFactory>;
85
+ var collector: Factory<ComposedCollectorFactory>;
89
86
  }
90
- type ComposedCollectorFactoryFunction = () => Collector$1<ReadonlySignal<unknown>>;
91
87
  declare class Composed<T> extends Computed<T> implements Signal$1<T> {
92
- private readonly writeFn;
93
- constructor(empty: boolean, value: T | undefined, values: unknown[], dependencies: Set<ReadonlySignal<unknown>>, listeners: Set<Callback>, collector: Collector$1<ReadonlySignal<unknown>>, compute: () => T, write: (value: T) => void, equals: Maybe<Equals<T>>);
88
+ #private;
89
+ constructor(empty: boolean, value: T | undefined, values: [ReadonlySignal<unknown>, unknown][], dependencies: Set<ReadonlySignal<unknown>>, listeners: Set<Callback>, batcher: Collector$1<Callback>, collector: Collector$1<ReadonlySignal<unknown>>, compute: () => T, write: (value: T) => void, equals: Maybe<Equals<T>>);
94
90
  write(value: T): void;
95
91
  }
96
92
 
97
- type EffectCollectorFactoryFunction = () => Collector$1<ReadonlySignal<unknown>>;
93
+ type Effect = (callback: EffectCallback) => Callback;
94
+ type EffectCallback = (init: boolean) => EffectCleanup | void;
95
+ type EffectCleanup = (destroy: boolean) => void;
96
+ declare const effect$1: Factory<Effect>;
97
+
98
98
  declare function effect(cb: EffectCallback): Callback;
99
99
  declare namespace effect {
100
- var collector: Factory<EffectCollectorFactoryFunction>;
100
+ var collector: Factory<EffectCollectorFactory>;
101
101
  }
102
+ type EffectCollectorFactory = () => Collector$1<ReadonlySignal<unknown>>;
102
103
 
104
+ interface Ignore$1 {
105
+ <Value>(value: ReadonlySignal<Value>): Value;
106
+ <Value>(callback: () => Value): Value;
107
+ <Value, Args extends any[]>(callback: (...args: Args) => Value, ...args: Args): Value;
108
+ }
109
+ declare function ignore$1<Value>(value: ReadonlySignal<Value>): Value;
110
+ declare function ignore$1<Value>(callback: () => Value): Value;
111
+ declare function ignore$1<Value, Args extends any[]>(callback: (...args: Args) => Value, ...args: Args): Value;
112
+ declare namespace ignore$1 {
113
+ var collector: Factory<IgnoreCollectorFactory>;
114
+ }
115
+ type IgnoreCollectorFactory = () => Collector$1<ReadonlySignal<unknown>>;
116
+
117
+ type SignalBatcherFactory = () => Collector$1<Callback>;
118
+ type SignalCollectorFactory = () => Collector$1<ReadonlySignal<unknown>>;
103
119
  declare function signal<T>(value: T, equals?: Equals<T>): Signal$1<T>;
104
120
  declare namespace signal {
105
- var collector: Factory<SignalCollectorFactoryFunction>;
121
+ var batcher: Factory<SignalBatcherFactory>;
122
+ var collector: Factory<SignalCollectorFactory>;
106
123
  }
107
- type SignalCollectorFactoryFunction = () => Maybe<Collector$1<ReadonlySignal<unknown>>>;
108
124
  declare class Signal<T> implements Signal$1<T> {
109
- private value;
110
- private equalsFn;
111
- private listeners;
112
- private collector;
113
- constructor(value: T, equals: Maybe<Equals<T>>, listeners: Set<Callback>, collector: Maybe<Collector$1<ReadonlySignal<unknown>>>);
125
+ #private;
126
+ constructor(value: T, equals: Maybe<Equals<T>>, listeners: Set<Callback>, batcher: Collector$1<Callback>, collector: Collector$1<ReadonlySignal<unknown>>);
114
127
  read(): T;
115
128
  write(value: T): void;
116
129
  equals(other: T): boolean;
@@ -118,36 +131,60 @@ declare class Signal<T> implements Signal$1<T> {
118
131
  unsubscribe(callback: Callback): void;
119
132
  }
120
133
 
134
+ type index_BatchCollectorFactory = BatchCollectorFactory;
121
135
  type index_Collector<T> = Collector<T>;
122
136
  declare const index_Collector: typeof Collector;
123
137
  type index_Composed<T> = Composed<T>;
124
138
  declare const index_Composed: typeof Composed;
125
- type index_ComposedCollectorFactoryFunction = ComposedCollectorFactoryFunction;
139
+ type index_ComposedBatcherFactory = ComposedBatcherFactory;
140
+ type index_ComposedCollectorFactory = ComposedCollectorFactory;
126
141
  type index_Computed<T> = Computed<T>;
127
142
  declare const index_Computed: typeof Computed;
128
- type index_ComputedCollectorFactoryFunction = ComputedCollectorFactoryFunction;
129
- type index_EffectCollectorFactoryFunction = EffectCollectorFactoryFunction;
143
+ type index_ComputedCollectorFactory = ComputedCollectorFactory;
144
+ type index_EffectCollectorFactory = EffectCollectorFactory;
145
+ type index_IgnoreCollectorFactory = IgnoreCollectorFactory;
130
146
  type index_Signal<T> = Signal<T>;
131
147
  declare const index_Signal: typeof Signal;
132
- type index_SignalCollectorFactoryFunction = SignalCollectorFactoryFunction;
148
+ type index_SignalBatcherFactory = SignalBatcherFactory;
149
+ type index_SignalCollectorFactory = SignalCollectorFactory;
133
150
  declare const index_collector: typeof collector;
134
- declare const index_composed: typeof composed;
135
- declare const index_computed: typeof computed;
136
151
  declare const index_effect: typeof effect;
137
152
  declare const index_signal: typeof signal;
138
153
  declare namespace index {
139
- export { index_Collector as Collector, index_Composed as Composed, type index_ComposedCollectorFactoryFunction as ComposedCollectorFactoryFunction, index_Computed as Computed, type index_ComputedCollectorFactoryFunction as ComputedCollectorFactoryFunction, type index_EffectCollectorFactoryFunction as EffectCollectorFactoryFunction, index_Signal as Signal, type index_SignalCollectorFactoryFunction as SignalCollectorFactoryFunction, index_collector as collector, index_composed as composed, index_computed as computed, index_effect as effect, index_signal as signal };
154
+ export { type index_BatchCollectorFactory as BatchCollectorFactory, index_Collector as Collector, index_Composed as Composed, type index_ComposedBatcherFactory as ComposedBatcherFactory, type index_ComposedCollectorFactory as ComposedCollectorFactory, index_Computed as Computed, type index_ComputedCollectorFactory as ComputedCollectorFactory, type index_EffectCollectorFactory as EffectCollectorFactory, type Ignore$1 as Ignore, type index_IgnoreCollectorFactory as IgnoreCollectorFactory, index_Signal as Signal, type index_SignalBatcherFactory as SignalBatcherFactory, type index_SignalCollectorFactory as SignalCollectorFactory, batch$1 as batch, index_collector as collector, composed$1 as composed, computed$1 as computed, index_effect as effect, ignore$1 as ignore, index_signal as signal };
140
155
  }
141
156
 
142
157
  type Arguments<T> = T extends (...args: infer A) => any ? A : never;
143
158
 
159
+ interface Batch {
160
+ (callback: Callback): void;
161
+ (callback: Callback, collector: Collector$1<Callback>): void;
162
+ (callback: Callback, collector?: Collector$1<Callback>): void;
163
+ }
164
+ declare const batch: Factory<Batch>;
165
+
166
+ type ComposedFactory = <T>(read: () => T, write: (value: T) => void, equals?: Equals<T>) => Signal$1<T>;
167
+ declare const composed: Factory<ComposedFactory>;
168
+
169
+ type ComputedFactory = <T>(read: () => T, equals?: Equals<T>) => ReadonlySignal<T>;
170
+ declare const computed: Factory<ComputedFactory>;
171
+
172
+ interface Ignore {
173
+ <Value>(value: ReadonlySignal<Value>): Value;
174
+ <Value>(callback: () => Value): Value;
175
+ <Value, Args extends any[]>(callback: (...args: Args) => Value, ...args: Args): Value;
176
+ }
177
+ declare const ignore: Factory<Ignore>;
178
+
144
179
  interface Config {
145
- collector?: Maybe<CollectorFactoryFunction>;
146
- signal?: Maybe<SignalFactoryFunction>;
147
- effect?: Maybe<EffectFactoryFunction>;
148
- computed?: Maybe<ComputedFactoryFunction>;
149
- composed?: Maybe<ComposedFactoryFunction>;
180
+ collector?: Maybe<CollectorFactory>;
181
+ signal?: Maybe<SignalFactory>;
182
+ computed?: Maybe<ComputedFactory>;
183
+ composed?: Maybe<ComposedFactory>;
184
+ effect?: Maybe<Effect>;
185
+ batch?: Maybe<Batch>;
186
+ ignore?: Maybe<Ignore$1>;
150
187
  }
151
188
  declare function config(config?: Config): void;
152
189
 
153
- export { type Arguments, type Callback, type Collector$1 as Collector, type CollectorFactoryFunction, type Comparable, type ComposedFactoryFunction, type ComputedFactoryFunction, type Config, type Effect, type EffectCallback, type EffectCleanup, type EffectFactoryFunction, type Equals, type Maybe, type Reader, type ReadonlySignal, type Signal$1 as Signal, type SignalFactoryFunction, type Subscription, type Writer, collector$1 as collector, composed$1 as composed, computed$1 as computed, config, effect$1 as effect, index as internal, signal$1 as signal };
190
+ export { type Arguments, type Batch, type Callback, type Collector$1 as Collector, type CollectorFactory, type Comparable, type ComposedFactory, type ComputedFactory, type Config, type Effect, type EffectCallback, type EffectCleanup, type Equals, type Factory, type Function, type Ignore, type Maybe, type Reader, type ReadonlySignal, type Signal$1 as Signal, type SignalFactory, type Subscription, type Writer, batch, collector$1 as collector, composed, computed, config, effect$1 as effect, factory, ignore, index as internal, signal$1 as signal };
package/dist/index.d.ts CHANGED
@@ -1,18 +1,42 @@
1
+ type Function = (...args: any[]) => any;
2
+
1
3
  type Maybe<T> = T | null | undefined;
2
4
 
3
- type Factory<Fn extends FactoryFunction> = Fn & {
5
+ type Factory<Fn extends Function> = Fn & {
4
6
  factory(factory: Maybe<Fn>): void;
5
7
  default(factory: Maybe<Fn>): void;
6
8
  configured(): boolean;
7
9
  };
8
- type FactoryFunction = (...args: any[]) => any;
10
+ declare function factory<Fn extends Function>(name: string): Factory<Fn>;
9
11
 
10
12
  interface Collector$1<T> {
11
13
  add(value: T): void;
14
+ collecting(): boolean;
12
15
  collect(callback: () => void): Readonly<Set<T>>;
16
+ ignore(callback: () => void): void;
17
+ }
18
+ type CollectorFactory = <T>() => Collector$1<T>;
19
+ declare const collector$1: Factory<CollectorFactory>;
20
+
21
+ type Callback = () => void;
22
+
23
+ declare function batch$1(callback: Callback): void;
24
+ declare function batch$1(callback: Callback, collector: Collector$1<Callback>): void;
25
+ declare function batch$1(callback: Callback, collector?: Collector$1<Callback>): void;
26
+ declare namespace batch$1 {
27
+ var collector: Factory<BatchCollectorFactory>;
28
+ }
29
+ type BatchCollectorFactory = () => Collector$1<Callback>;
30
+
31
+ declare function collector<T>(): Collector$1<T>;
32
+ declare class Collector<T> implements Collector$1<T> {
33
+ #private;
34
+ constructor(values: Set<T> | null);
35
+ collecting(): boolean;
36
+ add(value: T): void;
37
+ collect(callback: () => void): Set<T>;
38
+ ignore(callback: () => void): void;
13
39
  }
14
- type CollectorFactoryFunction = <T>() => Collector$1<T>;
15
- declare const collector$1: Factory<CollectorFactoryFunction>;
16
40
 
17
41
  type Equals<T> = (value: T, other: T) => boolean;
18
42
  interface Comparable<T> {
@@ -23,8 +47,6 @@ interface Reader<T> {
23
47
  read(): T;
24
48
  }
25
49
 
26
- type Callback = () => void;
27
-
28
50
  interface Subscription {
29
51
  subscribe(callback: Callback): Callback;
30
52
  unsubscribe(callback: Callback): void;
@@ -38,79 +60,70 @@ interface Signal$1<T> extends Reader<T>, Writer<T>, Comparable<T>, Subscription
38
60
  }
39
61
  interface ReadonlySignal<T> extends Reader<T>, Comparable<T>, Subscription {
40
62
  }
41
- type SignalFactoryFunction = <T>(value: T, equals?: Equals<T>) => Signal$1<T>;
42
- declare const signal$1: Factory<SignalFactoryFunction>;
43
-
44
- type ComposedFactoryFunction = <T>(compute: () => T, write: (value: T) => void, equals?: Equals<T>) => Signal$1<T>;
45
- declare const composed$1: Factory<ComposedFactoryFunction>;
46
-
47
- type ComputedFactoryFunction = <T>(compute: () => T, equals?: Equals<T>) => ReadonlySignal<T>;
48
- declare const computed$1: Factory<ComputedFactoryFunction>;
49
-
50
- type Effect = () => void;
51
- type EffectCallback = (init: boolean) => EffectCleanup | void;
52
- type EffectCleanup = (destroy: boolean) => void;
53
- type EffectFactoryFunction = (callback: EffectCallback) => Effect;
54
- declare const effect$1: Factory<EffectFactoryFunction>;
55
-
56
- declare function collector<T>(): Collector$1<T>;
57
- declare class Collector<T> implements Collector$1<T> {
58
- private values;
59
- constructor(values: Set<T> | null);
60
- add(value: T): void;
61
- collect(callback: () => void): Set<T>;
62
- }
63
+ type SignalFactory = <T>(value: T, equals?: Equals<T>) => Signal$1<T>;
64
+ declare const signal$1: Factory<SignalFactory>;
63
65
 
64
- declare function computed<T>(compute: () => T, equals?: Equals<T>): Computed<T>;
65
- declare namespace computed {
66
- var collector: Factory<ComputedCollectorFactoryFunction>;
66
+ declare function computed$1<T>(compute: () => T, equals?: Equals<T>): Computed<T>;
67
+ declare namespace computed$1 {
68
+ var collector: Factory<ComputedCollectorFactory>;
67
69
  }
68
- type ComputedCollectorFactoryFunction = () => Collector$1<ReadonlySignal<unknown>>;
70
+ type ComputedCollectorFactory = () => Collector$1<ReadonlySignal<unknown>>;
69
71
  declare class Computed<T> implements ReadonlySignal<T> {
70
- private empty;
71
- private value;
72
- private values;
73
- private dependencies;
74
- private readonly compute;
75
- private readonly equalsFn;
76
- private readonly listeners;
77
- private readonly collector;
78
- constructor(empty: boolean, value: T | undefined, values: unknown[], dependencies: Set<ReadonlySignal<unknown>>, listeners: Set<Callback>, collector: Collector$1<ReadonlySignal<unknown>>, compute: () => T, equals: Maybe<Equals<T>>);
79
- private dirty;
72
+ #private;
73
+ constructor(empty: boolean, value: T | undefined, values: [ReadonlySignal<unknown>, unknown][], dependencies: Set<ReadonlySignal<unknown>>, listeners: Set<Callback>, collector: Collector$1<ReadonlySignal<unknown>>, compute: () => T, equals: Maybe<Equals<T>>);
80
74
  read(): T;
81
75
  equals(other: T): boolean;
82
76
  subscribe(callback: Callback): Callback;
83
77
  unsubscribe(callback: Callback): void;
84
78
  }
85
79
 
86
- declare function composed<T>(compute: () => T, write: (value: T) => void, equals?: Equals<T>): Composed<T>;
87
- declare namespace composed {
88
- var collector: Factory<ComposedCollectorFactoryFunction>;
80
+ type ComposedBatcherFactory = () => Collector$1<Callback>;
81
+ type ComposedCollectorFactory = () => Collector$1<ReadonlySignal<unknown>>;
82
+ declare function composed$1<T>(compute: () => T, write: (value: T) => void, equals?: Equals<T>): Composed<T>;
83
+ declare namespace composed$1 {
84
+ var batcher: Factory<ComposedBatcherFactory>;
85
+ var collector: Factory<ComposedCollectorFactory>;
89
86
  }
90
- type ComposedCollectorFactoryFunction = () => Collector$1<ReadonlySignal<unknown>>;
91
87
  declare class Composed<T> extends Computed<T> implements Signal$1<T> {
92
- private readonly writeFn;
93
- constructor(empty: boolean, value: T | undefined, values: unknown[], dependencies: Set<ReadonlySignal<unknown>>, listeners: Set<Callback>, collector: Collector$1<ReadonlySignal<unknown>>, compute: () => T, write: (value: T) => void, equals: Maybe<Equals<T>>);
88
+ #private;
89
+ constructor(empty: boolean, value: T | undefined, values: [ReadonlySignal<unknown>, unknown][], dependencies: Set<ReadonlySignal<unknown>>, listeners: Set<Callback>, batcher: Collector$1<Callback>, collector: Collector$1<ReadonlySignal<unknown>>, compute: () => T, write: (value: T) => void, equals: Maybe<Equals<T>>);
94
90
  write(value: T): void;
95
91
  }
96
92
 
97
- type EffectCollectorFactoryFunction = () => Collector$1<ReadonlySignal<unknown>>;
93
+ type Effect = (callback: EffectCallback) => Callback;
94
+ type EffectCallback = (init: boolean) => EffectCleanup | void;
95
+ type EffectCleanup = (destroy: boolean) => void;
96
+ declare const effect$1: Factory<Effect>;
97
+
98
98
  declare function effect(cb: EffectCallback): Callback;
99
99
  declare namespace effect {
100
- var collector: Factory<EffectCollectorFactoryFunction>;
100
+ var collector: Factory<EffectCollectorFactory>;
101
101
  }
102
+ type EffectCollectorFactory = () => Collector$1<ReadonlySignal<unknown>>;
102
103
 
104
+ interface Ignore$1 {
105
+ <Value>(value: ReadonlySignal<Value>): Value;
106
+ <Value>(callback: () => Value): Value;
107
+ <Value, Args extends any[]>(callback: (...args: Args) => Value, ...args: Args): Value;
108
+ }
109
+ declare function ignore$1<Value>(value: ReadonlySignal<Value>): Value;
110
+ declare function ignore$1<Value>(callback: () => Value): Value;
111
+ declare function ignore$1<Value, Args extends any[]>(callback: (...args: Args) => Value, ...args: Args): Value;
112
+ declare namespace ignore$1 {
113
+ var collector: Factory<IgnoreCollectorFactory>;
114
+ }
115
+ type IgnoreCollectorFactory = () => Collector$1<ReadonlySignal<unknown>>;
116
+
117
+ type SignalBatcherFactory = () => Collector$1<Callback>;
118
+ type SignalCollectorFactory = () => Collector$1<ReadonlySignal<unknown>>;
103
119
  declare function signal<T>(value: T, equals?: Equals<T>): Signal$1<T>;
104
120
  declare namespace signal {
105
- var collector: Factory<SignalCollectorFactoryFunction>;
121
+ var batcher: Factory<SignalBatcherFactory>;
122
+ var collector: Factory<SignalCollectorFactory>;
106
123
  }
107
- type SignalCollectorFactoryFunction = () => Maybe<Collector$1<ReadonlySignal<unknown>>>;
108
124
  declare class Signal<T> implements Signal$1<T> {
109
- private value;
110
- private equalsFn;
111
- private listeners;
112
- private collector;
113
- constructor(value: T, equals: Maybe<Equals<T>>, listeners: Set<Callback>, collector: Maybe<Collector$1<ReadonlySignal<unknown>>>);
125
+ #private;
126
+ constructor(value: T, equals: Maybe<Equals<T>>, listeners: Set<Callback>, batcher: Collector$1<Callback>, collector: Collector$1<ReadonlySignal<unknown>>);
114
127
  read(): T;
115
128
  write(value: T): void;
116
129
  equals(other: T): boolean;
@@ -118,36 +131,60 @@ declare class Signal<T> implements Signal$1<T> {
118
131
  unsubscribe(callback: Callback): void;
119
132
  }
120
133
 
134
+ type index_BatchCollectorFactory = BatchCollectorFactory;
121
135
  type index_Collector<T> = Collector<T>;
122
136
  declare const index_Collector: typeof Collector;
123
137
  type index_Composed<T> = Composed<T>;
124
138
  declare const index_Composed: typeof Composed;
125
- type index_ComposedCollectorFactoryFunction = ComposedCollectorFactoryFunction;
139
+ type index_ComposedBatcherFactory = ComposedBatcherFactory;
140
+ type index_ComposedCollectorFactory = ComposedCollectorFactory;
126
141
  type index_Computed<T> = Computed<T>;
127
142
  declare const index_Computed: typeof Computed;
128
- type index_ComputedCollectorFactoryFunction = ComputedCollectorFactoryFunction;
129
- type index_EffectCollectorFactoryFunction = EffectCollectorFactoryFunction;
143
+ type index_ComputedCollectorFactory = ComputedCollectorFactory;
144
+ type index_EffectCollectorFactory = EffectCollectorFactory;
145
+ type index_IgnoreCollectorFactory = IgnoreCollectorFactory;
130
146
  type index_Signal<T> = Signal<T>;
131
147
  declare const index_Signal: typeof Signal;
132
- type index_SignalCollectorFactoryFunction = SignalCollectorFactoryFunction;
148
+ type index_SignalBatcherFactory = SignalBatcherFactory;
149
+ type index_SignalCollectorFactory = SignalCollectorFactory;
133
150
  declare const index_collector: typeof collector;
134
- declare const index_composed: typeof composed;
135
- declare const index_computed: typeof computed;
136
151
  declare const index_effect: typeof effect;
137
152
  declare const index_signal: typeof signal;
138
153
  declare namespace index {
139
- export { index_Collector as Collector, index_Composed as Composed, type index_ComposedCollectorFactoryFunction as ComposedCollectorFactoryFunction, index_Computed as Computed, type index_ComputedCollectorFactoryFunction as ComputedCollectorFactoryFunction, type index_EffectCollectorFactoryFunction as EffectCollectorFactoryFunction, index_Signal as Signal, type index_SignalCollectorFactoryFunction as SignalCollectorFactoryFunction, index_collector as collector, index_composed as composed, index_computed as computed, index_effect as effect, index_signal as signal };
154
+ export { type index_BatchCollectorFactory as BatchCollectorFactory, index_Collector as Collector, index_Composed as Composed, type index_ComposedBatcherFactory as ComposedBatcherFactory, type index_ComposedCollectorFactory as ComposedCollectorFactory, index_Computed as Computed, type index_ComputedCollectorFactory as ComputedCollectorFactory, type index_EffectCollectorFactory as EffectCollectorFactory, type Ignore$1 as Ignore, type index_IgnoreCollectorFactory as IgnoreCollectorFactory, index_Signal as Signal, type index_SignalBatcherFactory as SignalBatcherFactory, type index_SignalCollectorFactory as SignalCollectorFactory, batch$1 as batch, index_collector as collector, composed$1 as composed, computed$1 as computed, index_effect as effect, ignore$1 as ignore, index_signal as signal };
140
155
  }
141
156
 
142
157
  type Arguments<T> = T extends (...args: infer A) => any ? A : never;
143
158
 
159
+ interface Batch {
160
+ (callback: Callback): void;
161
+ (callback: Callback, collector: Collector$1<Callback>): void;
162
+ (callback: Callback, collector?: Collector$1<Callback>): void;
163
+ }
164
+ declare const batch: Factory<Batch>;
165
+
166
+ type ComposedFactory = <T>(read: () => T, write: (value: T) => void, equals?: Equals<T>) => Signal$1<T>;
167
+ declare const composed: Factory<ComposedFactory>;
168
+
169
+ type ComputedFactory = <T>(read: () => T, equals?: Equals<T>) => ReadonlySignal<T>;
170
+ declare const computed: Factory<ComputedFactory>;
171
+
172
+ interface Ignore {
173
+ <Value>(value: ReadonlySignal<Value>): Value;
174
+ <Value>(callback: () => Value): Value;
175
+ <Value, Args extends any[]>(callback: (...args: Args) => Value, ...args: Args): Value;
176
+ }
177
+ declare const ignore: Factory<Ignore>;
178
+
144
179
  interface Config {
145
- collector?: Maybe<CollectorFactoryFunction>;
146
- signal?: Maybe<SignalFactoryFunction>;
147
- effect?: Maybe<EffectFactoryFunction>;
148
- computed?: Maybe<ComputedFactoryFunction>;
149
- composed?: Maybe<ComposedFactoryFunction>;
180
+ collector?: Maybe<CollectorFactory>;
181
+ signal?: Maybe<SignalFactory>;
182
+ computed?: Maybe<ComputedFactory>;
183
+ composed?: Maybe<ComposedFactory>;
184
+ effect?: Maybe<Effect>;
185
+ batch?: Maybe<Batch>;
186
+ ignore?: Maybe<Ignore$1>;
150
187
  }
151
188
  declare function config(config?: Config): void;
152
189
 
153
- export { type Arguments, type Callback, type Collector$1 as Collector, type CollectorFactoryFunction, type Comparable, type ComposedFactoryFunction, type ComputedFactoryFunction, type Config, type Effect, type EffectCallback, type EffectCleanup, type EffectFactoryFunction, type Equals, type Maybe, type Reader, type ReadonlySignal, type Signal$1 as Signal, type SignalFactoryFunction, type Subscription, type Writer, collector$1 as collector, composed$1 as composed, computed$1 as computed, config, effect$1 as effect, index as internal, signal$1 as signal };
190
+ export { type Arguments, type Batch, type Callback, type Collector$1 as Collector, type CollectorFactory, type Comparable, type ComposedFactory, type ComputedFactory, type Config, type Effect, type EffectCallback, type EffectCleanup, type Equals, type Factory, type Function, type Ignore, type Maybe, type Reader, type ReadonlySignal, type Signal$1 as Signal, type SignalFactory, type Subscription, type Writer, batch, collector$1 as collector, composed, computed, config, effect$1 as effect, factory, ignore, index as internal, signal$1 as signal };
package/dist/index.js CHANGED
@@ -20,11 +20,14 @@ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: tru
20
20
  // src/index.ts
21
21
  var index_exports = {};
22
22
  __export(index_exports, {
23
+ batch: () => batch,
23
24
  collector: () => collector,
24
25
  composed: () => composed,
25
26
  computed: () => computed,
26
27
  config: () => config,
27
28
  effect: () => effect,
29
+ factory: () => factory,
30
+ ignore: () => ignore,
28
31
  internal: () => internal_exports,
29
32
  signal: () => signal
30
33
  });
@@ -39,16 +42,15 @@ function factory(name) {
39
42
  if (__default__) return __default__(...args);
40
43
  throw new Error(`${name}.factory() not configured!`);
41
44
  }
42
- object.default = (factory2) => {
43
- __default__ = factory2;
44
- };
45
- object.factory = (factory2) => {
46
- __factory__ = factory2;
47
- };
45
+ object.default = (factory2) => __default__ = factory2;
46
+ object.factory = (factory2) => __factory__ = factory2;
48
47
  object.configured = () => __default__ !== null || __factory__ !== null;
49
48
  return object;
50
49
  }
51
50
 
51
+ // src/core/batch.ts
52
+ var batch = factory("batch");
53
+
52
54
  // src/core/collector.ts
53
55
  var collector = factory("collector");
54
56
 
@@ -61,6 +63,9 @@ var computed = factory("computed");
61
63
  // src/core/effect.ts
62
64
  var effect = factory("effect");
63
65
 
66
+ // src/core/ignore.ts
67
+ var ignore = factory("ignore");
68
+
64
69
  // src/core/signal.ts
65
70
  var signal = factory("signal");
66
71
 
@@ -71,34 +76,52 @@ __export(internal_exports, {
71
76
  Composed: () => Composed,
72
77
  Computed: () => Computed,
73
78
  Signal: () => Signal,
79
+ batch: () => batch2,
74
80
  collector: () => collector2,
75
81
  composed: () => composed2,
76
82
  computed: () => computed2,
77
83
  effect: () => effect2,
84
+ ignore: () => ignore2,
78
85
  signal: () => signal2
79
86
  });
80
87
 
88
+ // src/internal/batch.ts
89
+ function batch2(callback, collector3 = batch2.collector()) {
90
+ if (collector3.collecting()) return callback();
91
+ collector3.collect(callback).forEach((listener) => listener());
92
+ }
93
+ batch2.collector = factory("batch.collector");
94
+
81
95
  // src/internal/collector.ts
82
96
  function collector2() {
83
97
  return new Collector(null);
84
98
  }
85
99
  var Collector = class {
86
- values;
100
+ #values;
87
101
  constructor(values) {
88
- this.values = values;
102
+ this.#values = values;
103
+ }
104
+ collecting() {
105
+ return this.#values !== null;
89
106
  }
90
107
  add(value) {
91
- if (!this.values) return;
92
- this.values.add(value);
108
+ if (!this.collecting() || !this.#values) return;
109
+ this.#values.add(value);
93
110
  }
94
111
  collect(callback) {
95
- const current = this.values;
96
- this.values = /* @__PURE__ */ new Set();
112
+ const current = this.#values;
113
+ this.#values = /* @__PURE__ */ new Set();
97
114
  callback();
98
- const collected = this.values;
99
- this.values = current;
115
+ const collected = this.#values;
116
+ this.#values = current;
100
117
  return collected;
101
118
  }
119
+ ignore(callback) {
120
+ const current = this.#values;
121
+ this.#values = null;
122
+ callback();
123
+ this.#values = current;
124
+ }
102
125
  };
103
126
 
104
127
  // src/internal/computed.ts
@@ -116,54 +139,54 @@ function computed2(compute, equals) {
116
139
  }
117
140
  computed2.collector = factory("computed.collector");
118
141
  var Computed = class {
119
- empty;
120
- value;
121
- values;
122
- dependencies;
123
- compute;
124
- equalsFn;
125
- listeners;
126
- collector;
142
+ #empty;
143
+ #value;
144
+ #values;
145
+ #dependencies;
146
+ #compute;
147
+ #equals;
148
+ #listeners;
149
+ #collector;
127
150
  constructor(empty, value, values, dependencies, listeners, collector3, compute, equals) {
128
- this.empty = empty;
129
- this.value = value;
130
- this.values = values;
131
- this.dependencies = dependencies;
132
- this.listeners = listeners;
133
- this.collector = collector3;
134
- this.compute = compute;
135
- this.equalsFn = equals;
151
+ this.#empty = empty;
152
+ this.#value = value;
153
+ this.#values = values;
154
+ this.#dependencies = dependencies;
155
+ this.#listeners = listeners;
156
+ this.#collector = collector3;
157
+ this.#compute = compute;
158
+ this.#equals = equals;
136
159
  }
137
- dirty() {
138
- if (this.empty) return true;
139
- return Array.from(this.dependencies).some((dep, index) => !dep.equals(this.values[index]));
160
+ #dirty() {
161
+ if (this.#empty) return true;
162
+ return this.#values.some(([dep, value]) => !dep.equals(value));
140
163
  }
141
164
  read() {
142
- this.collector.add(this);
143
- if (!this.dirty()) return this.value;
144
- const current = this.dependencies;
145
- const next = this.collector.collect(() => this.value = this.compute());
146
- this.dependencies = next;
147
- this.values = Array.from(next).map((dep) => dep.read());
148
- this.empty = false;
149
- if (!current.size && !next.size) return this.value;
150
- if (!this.listeners.size) return this.value;
151
- current.forEach((dep) => !next.has(dep) && this.listeners.forEach((listener) => dep.unsubscribe(listener)));
152
- next.forEach((dep) => !current.has(dep) && this.listeners.forEach((listener) => dep.subscribe(listener)));
153
- return this.value;
165
+ this.#collector.add(this);
166
+ if (!this.#dirty()) return this.#value;
167
+ const current = this.#dependencies;
168
+ const next = this.#collector.collect(() => this.#value = this.#compute());
169
+ this.#dependencies = next;
170
+ this.#values = Array.from(next).map((dep) => [dep, dep.read()]);
171
+ this.#empty = false;
172
+ if (!current.size && !next.size) return this.#value;
173
+ if (!this.#listeners.size) return this.#value;
174
+ current.forEach((dep) => !next.has(dep) && this.#listeners.forEach((listener) => dep.unsubscribe(listener)));
175
+ next.forEach((dep) => !current.has(dep) && this.#listeners.forEach((listener) => dep.subscribe(listener)));
176
+ return this.#value;
154
177
  }
155
178
  equals(other) {
156
- if (this.equalsFn) return this.equalsFn(this.read(), other);
179
+ if (this.#equals) return this.#equals(this.read(), other);
157
180
  return this.read() === other;
158
181
  }
159
182
  subscribe(callback) {
160
- this.listeners.add(callback);
161
- this.dependencies.forEach((dep) => dep.subscribe(callback));
162
- return () => this.unsubscribe(callback);
183
+ this.#listeners.add(callback);
184
+ this.#dependencies.forEach((dep) => dep.subscribe(callback));
185
+ return this.unsubscribe.bind(this, callback);
163
186
  }
164
187
  unsubscribe(callback) {
165
- this.listeners.delete(callback);
166
- this.dependencies.forEach((dep) => dep.unsubscribe(callback));
188
+ this.#listeners.delete(callback);
189
+ this.#dependencies.forEach((dep) => dep.unsubscribe(callback));
167
190
  }
168
191
  };
169
192
 
@@ -175,22 +198,26 @@ function composed2(compute, write, equals) {
175
198
  [],
176
199
  /* @__PURE__ */ new Set(),
177
200
  /* @__PURE__ */ new Set(),
201
+ composed2.batcher(),
178
202
  composed2.collector(),
179
203
  compute,
180
204
  write,
181
205
  equals
182
206
  );
183
207
  }
208
+ composed2.batcher = factory("composed.batcher");
184
209
  composed2.collector = factory("composed.collector");
185
210
  var Composed = class extends Computed {
186
- writeFn;
187
- constructor(empty, value, values, dependencies, listeners, collector3, compute, write, equals) {
211
+ #batcher;
212
+ #write;
213
+ constructor(empty, value, values, dependencies, listeners, batcher, collector3, compute, write, equals) {
188
214
  super(empty, value, values, dependencies, listeners, collector3, compute, equals);
189
- this.writeFn = write;
215
+ this.#batcher = batcher;
216
+ this.#write = write;
190
217
  }
191
218
  write(value) {
192
219
  if (this.equals(value)) return;
193
- this.writeFn(value);
220
+ batch(() => this.#write(value), this.#batcher);
194
221
  }
195
222
  };
196
223
 
@@ -215,73 +242,103 @@ function effect2(cb) {
215
242
  }
216
243
  effect2.collector = factory("effect.collector");
217
244
 
245
+ // src/internal/ignore.ts
246
+ function ignore2(callback, ...args) {
247
+ let value;
248
+ ignore2.collector().ignore(() => value = typeof callback === "function" ? callback(...args) : callback.read());
249
+ return value;
250
+ }
251
+ ignore2.collector = factory("signal.collector");
252
+
218
253
  // src/internal/signal.ts
219
254
  function signal2(value, equals) {
220
- return new Signal(value, equals, /* @__PURE__ */ new Set(), signal2.collector());
255
+ return new Signal(value, equals, /* @__PURE__ */ new Set(), signal2.batcher(), signal2.collector());
221
256
  }
257
+ signal2.batcher = factory("signal.batcher");
222
258
  signal2.collector = factory("signal.collector");
223
259
  var Signal = class {
224
- value;
225
- equalsFn;
226
- listeners;
227
- collector;
228
- constructor(value, equals, listeners, collector3) {
229
- this.value = value;
230
- this.equalsFn = equals;
231
- this.listeners = listeners;
232
- this.collector = collector3;
260
+ #value;
261
+ #equals;
262
+ #listeners;
263
+ #batcher;
264
+ #collector;
265
+ constructor(value, equals, listeners, batcher, collector3) {
266
+ this.#value = value;
267
+ this.#equals = equals;
268
+ this.#listeners = listeners;
269
+ this.#batcher = batcher;
270
+ this.#collector = collector3;
233
271
  }
234
272
  read() {
235
- if (this.collector) this.collector.add(this);
236
- return this.value;
273
+ this.#collector.add(this);
274
+ return this.#value;
237
275
  }
238
276
  write(value) {
239
277
  if (this.equals(value)) return;
240
- this.value = value;
241
- this.listeners.forEach((listener) => listener());
278
+ this.#value = value;
279
+ if (this.#batcher.collecting()) this.#listeners.forEach((listener) => this.#batcher.add(listener));
280
+ else this.#listeners.forEach((listener) => listener());
242
281
  }
243
282
  equals(other) {
244
- if (this.equalsFn) return this.equalsFn(this.value, other);
245
- return this.value === other;
283
+ if (this.#equals) return this.#equals(this.#value, other);
284
+ return this.#value === other;
246
285
  }
247
286
  subscribe(callback) {
248
- this.listeners.add(callback);
249
- return () => this.unsubscribe(callback);
287
+ this.#listeners.add(callback);
288
+ return this.unsubscribe.bind(this, callback);
250
289
  }
251
290
  unsubscribe(callback) {
252
- this.listeners.delete(callback);
291
+ this.#listeners.delete(callback);
253
292
  }
254
293
  };
255
294
 
256
- // src/index.ts
295
+ // src/core/config.ts
257
296
  function config(config2 = {}) {
258
297
  collector.factory(config2.collector);
259
298
  signal.factory(config2.signal);
260
- effect.factory(config2.effect);
261
299
  computed.factory(config2.computed);
262
300
  composed.factory(config2.composed);
301
+ effect.factory(config2.effect);
302
+ batch.factory(config2.batch);
303
+ ignore.factory(config2.ignore);
304
+ }
305
+
306
+ // src/index.ts
307
+ var __collector__ = null;
308
+ function shared_collector() {
309
+ if (!__collector__) __collector__ = collector();
310
+ return __collector__;
263
311
  }
264
- var __shared__ = null;
265
- function shared() {
266
- if (!__shared__) __shared__ = collector();
267
- return __shared__;
312
+ signal2.collector.default(shared_collector);
313
+ computed2.collector.default(shared_collector);
314
+ composed2.collector.default(shared_collector);
315
+ effect2.collector.default(shared_collector);
316
+ ignore2.collector.default(shared_collector);
317
+ var __batcher__ = null;
318
+ function shared_batcher() {
319
+ if (!__batcher__) __batcher__ = collector();
320
+ return __batcher__;
268
321
  }
269
- signal2.collector.default(shared);
270
- effect2.collector.default(shared);
271
- computed2.collector.default(shared);
272
- composed2.collector.default(shared);
273
- signal.default(signal2);
274
- effect.default(effect2);
322
+ signal2.batcher.default(shared_batcher);
323
+ composed2.batcher.default(shared_batcher);
324
+ batch2.collector.default(shared_batcher);
275
325
  collector.default(collector2);
326
+ signal.default(signal2);
276
327
  computed.default(computed2);
277
328
  composed.default(composed2);
329
+ effect.default(effect2);
330
+ batch.default(batch2);
331
+ ignore.default(ignore2);
278
332
  // Annotate the CommonJS export names for ESM import in node:
279
333
  0 && (module.exports = {
334
+ batch,
280
335
  collector,
281
336
  composed,
282
337
  computed,
283
338
  config,
284
339
  effect,
340
+ factory,
341
+ ignore,
285
342
  internal,
286
343
  signal
287
344
  });
package/dist/index.mjs CHANGED
@@ -13,16 +13,15 @@ function factory(name) {
13
13
  if (__default__) return __default__(...args);
14
14
  throw new Error(`${name}.factory() not configured!`);
15
15
  }
16
- object.default = (factory2) => {
17
- __default__ = factory2;
18
- };
19
- object.factory = (factory2) => {
20
- __factory__ = factory2;
21
- };
16
+ object.default = (factory2) => __default__ = factory2;
17
+ object.factory = (factory2) => __factory__ = factory2;
22
18
  object.configured = () => __default__ !== null || __factory__ !== null;
23
19
  return object;
24
20
  }
25
21
 
22
+ // src/core/batch.ts
23
+ var batch = factory("batch");
24
+
26
25
  // src/core/collector.ts
27
26
  var collector = factory("collector");
28
27
 
@@ -35,6 +34,9 @@ var computed = factory("computed");
35
34
  // src/core/effect.ts
36
35
  var effect = factory("effect");
37
36
 
37
+ // src/core/ignore.ts
38
+ var ignore = factory("ignore");
39
+
38
40
  // src/core/signal.ts
39
41
  var signal = factory("signal");
40
42
 
@@ -45,34 +47,52 @@ __export(internal_exports, {
45
47
  Composed: () => Composed,
46
48
  Computed: () => Computed,
47
49
  Signal: () => Signal,
50
+ batch: () => batch2,
48
51
  collector: () => collector2,
49
52
  composed: () => composed2,
50
53
  computed: () => computed2,
51
54
  effect: () => effect2,
55
+ ignore: () => ignore2,
52
56
  signal: () => signal2
53
57
  });
54
58
 
59
+ // src/internal/batch.ts
60
+ function batch2(callback, collector3 = batch2.collector()) {
61
+ if (collector3.collecting()) return callback();
62
+ collector3.collect(callback).forEach((listener) => listener());
63
+ }
64
+ batch2.collector = factory("batch.collector");
65
+
55
66
  // src/internal/collector.ts
56
67
  function collector2() {
57
68
  return new Collector(null);
58
69
  }
59
70
  var Collector = class {
60
- values;
71
+ #values;
61
72
  constructor(values) {
62
- this.values = values;
73
+ this.#values = values;
74
+ }
75
+ collecting() {
76
+ return this.#values !== null;
63
77
  }
64
78
  add(value) {
65
- if (!this.values) return;
66
- this.values.add(value);
79
+ if (!this.collecting() || !this.#values) return;
80
+ this.#values.add(value);
67
81
  }
68
82
  collect(callback) {
69
- const current = this.values;
70
- this.values = /* @__PURE__ */ new Set();
83
+ const current = this.#values;
84
+ this.#values = /* @__PURE__ */ new Set();
71
85
  callback();
72
- const collected = this.values;
73
- this.values = current;
86
+ const collected = this.#values;
87
+ this.#values = current;
74
88
  return collected;
75
89
  }
90
+ ignore(callback) {
91
+ const current = this.#values;
92
+ this.#values = null;
93
+ callback();
94
+ this.#values = current;
95
+ }
76
96
  };
77
97
 
78
98
  // src/internal/computed.ts
@@ -90,54 +110,54 @@ function computed2(compute, equals) {
90
110
  }
91
111
  computed2.collector = factory("computed.collector");
92
112
  var Computed = class {
93
- empty;
94
- value;
95
- values;
96
- dependencies;
97
- compute;
98
- equalsFn;
99
- listeners;
100
- collector;
113
+ #empty;
114
+ #value;
115
+ #values;
116
+ #dependencies;
117
+ #compute;
118
+ #equals;
119
+ #listeners;
120
+ #collector;
101
121
  constructor(empty, value, values, dependencies, listeners, collector3, compute, equals) {
102
- this.empty = empty;
103
- this.value = value;
104
- this.values = values;
105
- this.dependencies = dependencies;
106
- this.listeners = listeners;
107
- this.collector = collector3;
108
- this.compute = compute;
109
- this.equalsFn = equals;
122
+ this.#empty = empty;
123
+ this.#value = value;
124
+ this.#values = values;
125
+ this.#dependencies = dependencies;
126
+ this.#listeners = listeners;
127
+ this.#collector = collector3;
128
+ this.#compute = compute;
129
+ this.#equals = equals;
110
130
  }
111
- dirty() {
112
- if (this.empty) return true;
113
- return Array.from(this.dependencies).some((dep, index) => !dep.equals(this.values[index]));
131
+ #dirty() {
132
+ if (this.#empty) return true;
133
+ return this.#values.some(([dep, value]) => !dep.equals(value));
114
134
  }
115
135
  read() {
116
- this.collector.add(this);
117
- if (!this.dirty()) return this.value;
118
- const current = this.dependencies;
119
- const next = this.collector.collect(() => this.value = this.compute());
120
- this.dependencies = next;
121
- this.values = Array.from(next).map((dep) => dep.read());
122
- this.empty = false;
123
- if (!current.size && !next.size) return this.value;
124
- if (!this.listeners.size) return this.value;
125
- current.forEach((dep) => !next.has(dep) && this.listeners.forEach((listener) => dep.unsubscribe(listener)));
126
- next.forEach((dep) => !current.has(dep) && this.listeners.forEach((listener) => dep.subscribe(listener)));
127
- return this.value;
136
+ this.#collector.add(this);
137
+ if (!this.#dirty()) return this.#value;
138
+ const current = this.#dependencies;
139
+ const next = this.#collector.collect(() => this.#value = this.#compute());
140
+ this.#dependencies = next;
141
+ this.#values = Array.from(next).map((dep) => [dep, dep.read()]);
142
+ this.#empty = false;
143
+ if (!current.size && !next.size) return this.#value;
144
+ if (!this.#listeners.size) return this.#value;
145
+ current.forEach((dep) => !next.has(dep) && this.#listeners.forEach((listener) => dep.unsubscribe(listener)));
146
+ next.forEach((dep) => !current.has(dep) && this.#listeners.forEach((listener) => dep.subscribe(listener)));
147
+ return this.#value;
128
148
  }
129
149
  equals(other) {
130
- if (this.equalsFn) return this.equalsFn(this.read(), other);
150
+ if (this.#equals) return this.#equals(this.read(), other);
131
151
  return this.read() === other;
132
152
  }
133
153
  subscribe(callback) {
134
- this.listeners.add(callback);
135
- this.dependencies.forEach((dep) => dep.subscribe(callback));
136
- return () => this.unsubscribe(callback);
154
+ this.#listeners.add(callback);
155
+ this.#dependencies.forEach((dep) => dep.subscribe(callback));
156
+ return this.unsubscribe.bind(this, callback);
137
157
  }
138
158
  unsubscribe(callback) {
139
- this.listeners.delete(callback);
140
- this.dependencies.forEach((dep) => dep.unsubscribe(callback));
159
+ this.#listeners.delete(callback);
160
+ this.#dependencies.forEach((dep) => dep.unsubscribe(callback));
141
161
  }
142
162
  };
143
163
 
@@ -149,22 +169,26 @@ function composed2(compute, write, equals) {
149
169
  [],
150
170
  /* @__PURE__ */ new Set(),
151
171
  /* @__PURE__ */ new Set(),
172
+ composed2.batcher(),
152
173
  composed2.collector(),
153
174
  compute,
154
175
  write,
155
176
  equals
156
177
  );
157
178
  }
179
+ composed2.batcher = factory("composed.batcher");
158
180
  composed2.collector = factory("composed.collector");
159
181
  var Composed = class extends Computed {
160
- writeFn;
161
- constructor(empty, value, values, dependencies, listeners, collector3, compute, write, equals) {
182
+ #batcher;
183
+ #write;
184
+ constructor(empty, value, values, dependencies, listeners, batcher, collector3, compute, write, equals) {
162
185
  super(empty, value, values, dependencies, listeners, collector3, compute, equals);
163
- this.writeFn = write;
186
+ this.#batcher = batcher;
187
+ this.#write = write;
164
188
  }
165
189
  write(value) {
166
190
  if (this.equals(value)) return;
167
- this.writeFn(value);
191
+ batch(() => this.#write(value), this.#batcher);
168
192
  }
169
193
  };
170
194
 
@@ -189,72 +213,102 @@ function effect2(cb) {
189
213
  }
190
214
  effect2.collector = factory("effect.collector");
191
215
 
216
+ // src/internal/ignore.ts
217
+ function ignore2(callback, ...args) {
218
+ let value;
219
+ ignore2.collector().ignore(() => value = typeof callback === "function" ? callback(...args) : callback.read());
220
+ return value;
221
+ }
222
+ ignore2.collector = factory("signal.collector");
223
+
192
224
  // src/internal/signal.ts
193
225
  function signal2(value, equals) {
194
- return new Signal(value, equals, /* @__PURE__ */ new Set(), signal2.collector());
226
+ return new Signal(value, equals, /* @__PURE__ */ new Set(), signal2.batcher(), signal2.collector());
195
227
  }
228
+ signal2.batcher = factory("signal.batcher");
196
229
  signal2.collector = factory("signal.collector");
197
230
  var Signal = class {
198
- value;
199
- equalsFn;
200
- listeners;
201
- collector;
202
- constructor(value, equals, listeners, collector3) {
203
- this.value = value;
204
- this.equalsFn = equals;
205
- this.listeners = listeners;
206
- this.collector = collector3;
231
+ #value;
232
+ #equals;
233
+ #listeners;
234
+ #batcher;
235
+ #collector;
236
+ constructor(value, equals, listeners, batcher, collector3) {
237
+ this.#value = value;
238
+ this.#equals = equals;
239
+ this.#listeners = listeners;
240
+ this.#batcher = batcher;
241
+ this.#collector = collector3;
207
242
  }
208
243
  read() {
209
- if (this.collector) this.collector.add(this);
210
- return this.value;
244
+ this.#collector.add(this);
245
+ return this.#value;
211
246
  }
212
247
  write(value) {
213
248
  if (this.equals(value)) return;
214
- this.value = value;
215
- this.listeners.forEach((listener) => listener());
249
+ this.#value = value;
250
+ if (this.#batcher.collecting()) this.#listeners.forEach((listener) => this.#batcher.add(listener));
251
+ else this.#listeners.forEach((listener) => listener());
216
252
  }
217
253
  equals(other) {
218
- if (this.equalsFn) return this.equalsFn(this.value, other);
219
- return this.value === other;
254
+ if (this.#equals) return this.#equals(this.#value, other);
255
+ return this.#value === other;
220
256
  }
221
257
  subscribe(callback) {
222
- this.listeners.add(callback);
223
- return () => this.unsubscribe(callback);
258
+ this.#listeners.add(callback);
259
+ return this.unsubscribe.bind(this, callback);
224
260
  }
225
261
  unsubscribe(callback) {
226
- this.listeners.delete(callback);
262
+ this.#listeners.delete(callback);
227
263
  }
228
264
  };
229
265
 
230
- // src/index.ts
266
+ // src/core/config.ts
231
267
  function config(config2 = {}) {
232
268
  collector.factory(config2.collector);
233
269
  signal.factory(config2.signal);
234
- effect.factory(config2.effect);
235
270
  computed.factory(config2.computed);
236
271
  composed.factory(config2.composed);
272
+ effect.factory(config2.effect);
273
+ batch.factory(config2.batch);
274
+ ignore.factory(config2.ignore);
275
+ }
276
+
277
+ // src/index.ts
278
+ var __collector__ = null;
279
+ function shared_collector() {
280
+ if (!__collector__) __collector__ = collector();
281
+ return __collector__;
237
282
  }
238
- var __shared__ = null;
239
- function shared() {
240
- if (!__shared__) __shared__ = collector();
241
- return __shared__;
283
+ signal2.collector.default(shared_collector);
284
+ computed2.collector.default(shared_collector);
285
+ composed2.collector.default(shared_collector);
286
+ effect2.collector.default(shared_collector);
287
+ ignore2.collector.default(shared_collector);
288
+ var __batcher__ = null;
289
+ function shared_batcher() {
290
+ if (!__batcher__) __batcher__ = collector();
291
+ return __batcher__;
242
292
  }
243
- signal2.collector.default(shared);
244
- effect2.collector.default(shared);
245
- computed2.collector.default(shared);
246
- composed2.collector.default(shared);
247
- signal.default(signal2);
248
- effect.default(effect2);
293
+ signal2.batcher.default(shared_batcher);
294
+ composed2.batcher.default(shared_batcher);
295
+ batch2.collector.default(shared_batcher);
249
296
  collector.default(collector2);
297
+ signal.default(signal2);
250
298
  computed.default(computed2);
251
299
  composed.default(composed2);
300
+ effect.default(effect2);
301
+ batch.default(batch2);
302
+ ignore.default(ignore2);
252
303
  export {
304
+ batch,
253
305
  collector,
254
306
  composed,
255
307
  computed,
256
308
  config,
257
309
  effect,
310
+ factory,
311
+ ignore,
258
312
  internal_exports as internal,
259
313
  signal
260
314
  };
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@valentin30/signal",
3
- "version": "0.0.3",
4
- "description": "",
3
+ "version": "0.0.5",
4
+ "description": "My take on signals - lightweight reactive primitives inspired by Preact Signals, written in TypeScript.",
5
5
  "main": "dist/index.js",
6
6
  "module": "dist/index.mjs",
7
7
  "types": "dist/index.d.ts",