@hkdigital/lib-core 0.4.25 → 0.4.27
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/network/loaders/audio/AudioScene.svelte.d.ts +30 -10
- package/dist/network/loaders/audio/AudioScene.svelte.js +113 -74
- package/dist/network/loaders/image/ImageScene.svelte.d.ts +24 -13
- package/dist/network/loaders/image/ImageScene.svelte.js +118 -83
- package/dist/network/states/NetworkLoader.svelte.d.ts +2 -2
- package/dist/network/states/NetworkLoader.svelte.js +15 -17
- package/dist/state/machines/finite-state-machine/FiniteStateMachine.svelte.d.ts +2 -2
- package/dist/state/machines/finite-state-machine/FiniteStateMachine.svelte.js +13 -13
- package/dist/state/machines/finite-state-machine/README.md +31 -31
- package/dist/state/machines/finite-state-machine/typedef.d.ts +3 -3
- package/dist/state/machines/finite-state-machine/typedef.js +18 -12
- package/dist/state/machines/loading-state-machine/LoadingStateMachine.svelte.d.ts +4 -4
- package/dist/state/machines/loading-state-machine/LoadingStateMachine.svelte.js +15 -9
- package/dist/state/machines/loading-state-machine/README.md +95 -70
- package/dist/state/machines/loading-state-machine/constants.d.ts +4 -2
- package/dist/state/machines/loading-state-machine/constants.js +4 -2
- package/package.json +1 -1
|
@@ -13,6 +13,30 @@ export default class AudioScene {
|
|
|
13
13
|
loaded: boolean;
|
|
14
14
|
muted: boolean;
|
|
15
15
|
targetGain: number;
|
|
16
|
+
/**
|
|
17
|
+
* Get audio scene loading progress
|
|
18
|
+
*/
|
|
19
|
+
get progress(): {
|
|
20
|
+
totalBytesLoaded: number;
|
|
21
|
+
totalSize: number;
|
|
22
|
+
sourcesLoaded: number;
|
|
23
|
+
numberOfSources: number;
|
|
24
|
+
};
|
|
25
|
+
/**
|
|
26
|
+
* Get audio scene abort progress
|
|
27
|
+
*/
|
|
28
|
+
get abortProgress(): {
|
|
29
|
+
sourcesAborted: number;
|
|
30
|
+
numberOfSources: number;
|
|
31
|
+
};
|
|
32
|
+
/**
|
|
33
|
+
* Start loading all audio sources
|
|
34
|
+
*/
|
|
35
|
+
load(): void;
|
|
36
|
+
/**
|
|
37
|
+
* Abort loading all audio sources
|
|
38
|
+
*/
|
|
39
|
+
abort(): void;
|
|
16
40
|
destroy(): void;
|
|
17
41
|
/**
|
|
18
42
|
* Add in-memory audio source
|
|
@@ -28,16 +52,6 @@ export default class AudioScene {
|
|
|
28
52
|
url: string;
|
|
29
53
|
config?: SourceConfig;
|
|
30
54
|
}): void;
|
|
31
|
-
/**
|
|
32
|
-
* Start loading all audio sources
|
|
33
|
-
*/
|
|
34
|
-
load(): void;
|
|
35
|
-
/**
|
|
36
|
-
* Set an audio context to use
|
|
37
|
-
*
|
|
38
|
-
* @param {AudioContext} [audioContext]
|
|
39
|
-
*/
|
|
40
|
-
setAudioContext(audioContext?: AudioContext): void;
|
|
41
55
|
/**
|
|
42
56
|
* Get a source that can be used to play the audio once
|
|
43
57
|
*
|
|
@@ -46,6 +60,12 @@ export default class AudioScene {
|
|
|
46
60
|
* @returns {Promise<AudioBufferSourceNode>}
|
|
47
61
|
*/
|
|
48
62
|
getSourceNode(label: string): Promise<AudioBufferSourceNode>;
|
|
63
|
+
/**
|
|
64
|
+
* Set an audio context to use
|
|
65
|
+
*
|
|
66
|
+
* @param {AudioContext} [audioContext]
|
|
67
|
+
*/
|
|
68
|
+
setAudioContext(audioContext?: AudioContext): void;
|
|
49
69
|
/**
|
|
50
70
|
* Set target gain
|
|
51
71
|
*
|
|
@@ -5,12 +5,14 @@ import { LoadingStateMachine } from '../../../state/machines.js';
|
|
|
5
5
|
import {
|
|
6
6
|
STATE_INITIAL,
|
|
7
7
|
STATE_LOADING,
|
|
8
|
-
STATE_UNLOADING,
|
|
9
8
|
STATE_LOADED,
|
|
10
|
-
|
|
9
|
+
STATE_ABORTING,
|
|
10
|
+
STATE_ABORTED,
|
|
11
11
|
STATE_ERROR,
|
|
12
12
|
LOAD,
|
|
13
|
-
LOADED
|
|
13
|
+
LOADED,
|
|
14
|
+
ABORT,
|
|
15
|
+
ABORTED
|
|
14
16
|
} from '../../../state/machines.js';
|
|
15
17
|
|
|
16
18
|
import AudioLoader from './AudioLoader.svelte.js';
|
|
@@ -30,10 +32,9 @@ import AudioLoader from './AudioLoader.svelte.js';
|
|
|
30
32
|
export default class AudioScene {
|
|
31
33
|
#state = new LoadingStateMachine();
|
|
32
34
|
|
|
33
|
-
// @note this exported state is set by
|
|
35
|
+
// @note this exported state is set by onenter
|
|
34
36
|
state = $state(STATE_INITIAL);
|
|
35
37
|
|
|
36
|
-
// @note this exported state is set by $effect's
|
|
37
38
|
loaded = $derived.by(() => {
|
|
38
39
|
return this.state === STATE_LOADED;
|
|
39
40
|
});
|
|
@@ -87,6 +88,27 @@ export default class AudioScene {
|
|
|
87
88
|
};
|
|
88
89
|
});
|
|
89
90
|
|
|
91
|
+
#abortProgress = $derived.by(() => {
|
|
92
|
+
let sourcesAborted = 0;
|
|
93
|
+
const sources = this.#memorySources;
|
|
94
|
+
const numberOfSources = sources.length;
|
|
95
|
+
|
|
96
|
+
for (let j = 0; j < numberOfSources; j++) {
|
|
97
|
+
const source = sources[j];
|
|
98
|
+
const { audioLoader } = source;
|
|
99
|
+
const loaderState = audioLoader.state;
|
|
100
|
+
|
|
101
|
+
if (loaderState === STATE_ABORTED || loaderState === STATE_ERROR) {
|
|
102
|
+
sourcesAborted++;
|
|
103
|
+
}
|
|
104
|
+
} // end for
|
|
105
|
+
|
|
106
|
+
return {
|
|
107
|
+
sourcesAborted,
|
|
108
|
+
numberOfSources
|
|
109
|
+
};
|
|
110
|
+
});
|
|
111
|
+
|
|
90
112
|
/**
|
|
91
113
|
* Construct AudioScene
|
|
92
114
|
*/
|
|
@@ -110,46 +132,62 @@ export default class AudioScene {
|
|
|
110
132
|
});
|
|
111
133
|
|
|
112
134
|
$effect(() => {
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
{
|
|
116
|
-
// console.log('AudioScene:loading');
|
|
117
|
-
this.#startLoading();
|
|
118
|
-
}
|
|
119
|
-
break;
|
|
120
|
-
|
|
121
|
-
case STATE_UNLOADING:
|
|
122
|
-
{
|
|
123
|
-
// console.log('AudioScene:unloading');
|
|
124
|
-
// this.#startUnLoading();
|
|
125
|
-
}
|
|
126
|
-
break;
|
|
127
|
-
|
|
128
|
-
case STATE_LOADED:
|
|
129
|
-
{
|
|
130
|
-
// console.log('AudioScene:loaded');
|
|
131
|
-
|
|
132
|
-
// tODO
|
|
133
|
-
// this.#abortLoading = null;
|
|
134
|
-
}
|
|
135
|
-
break;
|
|
136
|
-
|
|
137
|
-
case STATE_CANCELLED:
|
|
138
|
-
{
|
|
139
|
-
// console.log('AudioScene:cancelled');
|
|
140
|
-
// TODO
|
|
141
|
-
}
|
|
142
|
-
break;
|
|
143
|
-
|
|
144
|
-
case STATE_ERROR:
|
|
145
|
-
{
|
|
146
|
-
console.error('AudioScene:error', state.error);
|
|
147
|
-
}
|
|
148
|
-
break;
|
|
149
|
-
} // end switch
|
|
135
|
+
if (state.current === STATE_ABORTING) {
|
|
136
|
+
const { sourcesAborted, numberOfSources } = this.#abortProgress;
|
|
150
137
|
|
|
151
|
-
|
|
138
|
+
if (sourcesAborted === numberOfSources) {
|
|
139
|
+
// console.debug(`AudioScene: ${numberOfSources} sources aborted`);
|
|
140
|
+
this.#state.send(ABORTED);
|
|
141
|
+
}
|
|
142
|
+
}
|
|
152
143
|
});
|
|
144
|
+
|
|
145
|
+
state.onenter = ( currentState ) => {
|
|
146
|
+
// console.log('onenter', currentState );
|
|
147
|
+
|
|
148
|
+
if(currentState === STATE_LOADING )
|
|
149
|
+
{
|
|
150
|
+
// console.log('AudioScene:loading');
|
|
151
|
+
this.#startLoading();
|
|
152
|
+
}
|
|
153
|
+
else if(currentState === STATE_ABORTING )
|
|
154
|
+
{
|
|
155
|
+
// console.log('AudioScene:aborting');
|
|
156
|
+
this.#startAbort();
|
|
157
|
+
}
|
|
158
|
+
|
|
159
|
+
this.state = state.current;
|
|
160
|
+
};
|
|
161
|
+
}
|
|
162
|
+
|
|
163
|
+
/* ==== Common loader interface */
|
|
164
|
+
|
|
165
|
+
/**
|
|
166
|
+
* Get audio scene loading progress
|
|
167
|
+
*/
|
|
168
|
+
get progress() {
|
|
169
|
+
return this.#progress;
|
|
170
|
+
}
|
|
171
|
+
|
|
172
|
+
/**
|
|
173
|
+
* Get audio scene abort progress
|
|
174
|
+
*/
|
|
175
|
+
get abortProgress() {
|
|
176
|
+
return this.#abortProgress;
|
|
177
|
+
}
|
|
178
|
+
|
|
179
|
+
/**
|
|
180
|
+
* Start loading all audio sources
|
|
181
|
+
*/
|
|
182
|
+
load() {
|
|
183
|
+
this.#state.send(LOAD);
|
|
184
|
+
}
|
|
185
|
+
|
|
186
|
+
/**
|
|
187
|
+
* Abort loading all audio sources
|
|
188
|
+
*/
|
|
189
|
+
abort() {
|
|
190
|
+
this.#state.send(ABORT);
|
|
153
191
|
}
|
|
154
192
|
|
|
155
193
|
destroy() {
|
|
@@ -157,6 +195,8 @@ export default class AudioScene {
|
|
|
157
195
|
// TODO: Unload AUdioLoaders?
|
|
158
196
|
}
|
|
159
197
|
|
|
198
|
+
/* ==== Source definitions */
|
|
199
|
+
|
|
160
200
|
/**
|
|
161
201
|
* Add in-memory audio source
|
|
162
202
|
* - Uses an AudioLoader instance to load audio data from network
|
|
@@ -175,36 +215,7 @@ export default class AudioScene {
|
|
|
175
215
|
this.#memorySources.push({ label, audioLoader, config });
|
|
176
216
|
}
|
|
177
217
|
|
|
178
|
-
|
|
179
|
-
* Start loading all audio sources
|
|
180
|
-
*/
|
|
181
|
-
load() {
|
|
182
|
-
this.#state.send(LOAD);
|
|
183
|
-
|
|
184
|
-
// FIXME: in unit test when moved to startloading it hangs!
|
|
185
|
-
|
|
186
|
-
for (const { audioLoader } of this.#memorySources) {
|
|
187
|
-
audioLoader.load();
|
|
188
|
-
}
|
|
189
|
-
}
|
|
190
|
-
|
|
191
|
-
/**
|
|
192
|
-
* Set an audio context to use
|
|
193
|
-
*
|
|
194
|
-
* @param {AudioContext} [audioContext]
|
|
195
|
-
*/
|
|
196
|
-
setAudioContext( audioContext ) {
|
|
197
|
-
this.#audioContext = audioContext;
|
|
198
|
-
}
|
|
199
|
-
|
|
200
|
-
async #startLoading() {
|
|
201
|
-
// console.log('#startLoading');
|
|
202
|
-
|
|
203
|
-
// FIXME: in unit test when moved to startloading it hangs!
|
|
204
|
-
// for (const { audioLoader } of this.#memorySources) {
|
|
205
|
-
// audioLoader.load();
|
|
206
|
-
// }
|
|
207
|
-
}
|
|
218
|
+
/* ==== Resource access */
|
|
208
219
|
|
|
209
220
|
/**
|
|
210
221
|
* Get a source that can be used to play the audio once
|
|
@@ -240,6 +251,33 @@ export default class AudioScene {
|
|
|
240
251
|
return sourceNode;
|
|
241
252
|
}
|
|
242
253
|
|
|
254
|
+
/**
|
|
255
|
+
* Set an audio context to use
|
|
256
|
+
*
|
|
257
|
+
* @param {AudioContext} [audioContext]
|
|
258
|
+
*/
|
|
259
|
+
setAudioContext( audioContext ) {
|
|
260
|
+
this.#audioContext = audioContext;
|
|
261
|
+
}
|
|
262
|
+
|
|
263
|
+
async #startLoading() {
|
|
264
|
+
// console.log('#startLoading');
|
|
265
|
+
|
|
266
|
+
for (const { audioLoader } of this.#memorySources) {
|
|
267
|
+
audioLoader.load();
|
|
268
|
+
}
|
|
269
|
+
}
|
|
270
|
+
|
|
271
|
+
#startAbort() {
|
|
272
|
+
// console.log('#startAbort');
|
|
273
|
+
|
|
274
|
+
for (const { audioLoader } of this.#memorySources) {
|
|
275
|
+
audioLoader.abort();
|
|
276
|
+
}
|
|
277
|
+
}
|
|
278
|
+
|
|
279
|
+
/* ==== Audio specific */
|
|
280
|
+
|
|
243
281
|
/**
|
|
244
282
|
* Set target gain
|
|
245
283
|
*
|
|
@@ -281,6 +319,7 @@ export default class AudioScene {
|
|
|
281
319
|
this.setTargetGain(this.#unmutedTargetGain);
|
|
282
320
|
}
|
|
283
321
|
|
|
322
|
+
/* ==== Internals */
|
|
284
323
|
|
|
285
324
|
#getGainNode()
|
|
286
325
|
{
|
|
@@ -322,4 +361,4 @@ export default class AudioScene {
|
|
|
322
361
|
|
|
323
362
|
throw new Error(`Source [${label}] has not been defined`);
|
|
324
363
|
}
|
|
325
|
-
}
|
|
364
|
+
} // end class
|
|
@@ -10,6 +10,30 @@
|
|
|
10
10
|
export default class ImageScene {
|
|
11
11
|
state: string;
|
|
12
12
|
loaded: boolean;
|
|
13
|
+
/**
|
|
14
|
+
* Get image scene loading progress
|
|
15
|
+
*/
|
|
16
|
+
get progress(): {
|
|
17
|
+
totalBytesLoaded: number;
|
|
18
|
+
totalSize: number;
|
|
19
|
+
sourcesLoaded: number;
|
|
20
|
+
numberOfSources: number;
|
|
21
|
+
};
|
|
22
|
+
/**
|
|
23
|
+
* Get image scene abort progress
|
|
24
|
+
*/
|
|
25
|
+
get abortProgress(): {
|
|
26
|
+
sourcesAborted: number;
|
|
27
|
+
numberOfSources: number;
|
|
28
|
+
};
|
|
29
|
+
/**
|
|
30
|
+
* Start loading all image sources
|
|
31
|
+
*/
|
|
32
|
+
load(): void;
|
|
33
|
+
/**
|
|
34
|
+
* Abort loading all image sources
|
|
35
|
+
*/
|
|
36
|
+
abort(): void;
|
|
13
37
|
destroy(): void;
|
|
14
38
|
/**
|
|
15
39
|
* Add image source
|
|
@@ -23,19 +47,6 @@ export default class ImageScene {
|
|
|
23
47
|
label: string;
|
|
24
48
|
imageSource: import("../../../config/typedef.js").ImageSource;
|
|
25
49
|
}): void;
|
|
26
|
-
/**
|
|
27
|
-
* Start loading all image sources
|
|
28
|
-
*/
|
|
29
|
-
load(): void;
|
|
30
|
-
/**
|
|
31
|
-
* Get image scene loading progress
|
|
32
|
-
*/
|
|
33
|
-
get progress(): {
|
|
34
|
-
totalBytesLoaded: number;
|
|
35
|
-
totalSize: number;
|
|
36
|
-
sourcesLoaded: number;
|
|
37
|
-
numberOfSources: number;
|
|
38
|
-
};
|
|
39
50
|
/**
|
|
40
51
|
* Get an image loader
|
|
41
52
|
*
|
|
@@ -7,12 +7,14 @@ import { LoadingStateMachine } from '../../../state/machines.js';
|
|
|
7
7
|
import {
|
|
8
8
|
STATE_INITIAL,
|
|
9
9
|
STATE_LOADING,
|
|
10
|
-
STATE_UNLOADING,
|
|
11
10
|
STATE_LOADED,
|
|
12
|
-
|
|
11
|
+
STATE_ABORTING,
|
|
12
|
+
STATE_ABORTED,
|
|
13
13
|
STATE_ERROR,
|
|
14
14
|
LOAD,
|
|
15
|
-
LOADED
|
|
15
|
+
LOADED,
|
|
16
|
+
ABORT,
|
|
17
|
+
ABORTED
|
|
16
18
|
} from '../../../state/machines.js';
|
|
17
19
|
|
|
18
20
|
import ImageLoader from './ImageLoader.svelte.js';
|
|
@@ -31,10 +33,9 @@ import ImageLoader from './ImageLoader.svelte.js';
|
|
|
31
33
|
export default class ImageScene {
|
|
32
34
|
#state = new LoadingStateMachine();
|
|
33
35
|
|
|
34
|
-
// @note this exported state is set by
|
|
36
|
+
// @note this exported state is set by onenter
|
|
35
37
|
state = $state(STATE_INITIAL);
|
|
36
38
|
|
|
37
|
-
// @note this exported state is set by $effect's
|
|
38
39
|
loaded = $derived.by(() => {
|
|
39
40
|
return this.state === STATE_LOADED;
|
|
40
41
|
});
|
|
@@ -74,6 +75,27 @@ export default class ImageScene {
|
|
|
74
75
|
};
|
|
75
76
|
});
|
|
76
77
|
|
|
78
|
+
#abortProgress = $derived.by(() => {
|
|
79
|
+
let sourcesAborted = 0;
|
|
80
|
+
const sources = this.#imageSources;
|
|
81
|
+
const numberOfSources = sources.length;
|
|
82
|
+
|
|
83
|
+
for (let j = 0; j < numberOfSources; j++) {
|
|
84
|
+
const source = sources[j];
|
|
85
|
+
const { imageLoader } = source;
|
|
86
|
+
const loaderState = imageLoader.state;
|
|
87
|
+
|
|
88
|
+
if (loaderState === STATE_ABORTED || loaderState === STATE_ERROR) {
|
|
89
|
+
sourcesAborted++;
|
|
90
|
+
}
|
|
91
|
+
} // end for
|
|
92
|
+
|
|
93
|
+
return {
|
|
94
|
+
sourcesAborted,
|
|
95
|
+
numberOfSources
|
|
96
|
+
};
|
|
97
|
+
});
|
|
98
|
+
|
|
77
99
|
#sourcesLoaded = $derived( this.#progress.sourcesLoaded );
|
|
78
100
|
#numberOfSources = $derived( this.#progress.numberOfSources );
|
|
79
101
|
|
|
@@ -92,55 +114,72 @@ export default class ImageScene {
|
|
|
92
114
|
}
|
|
93
115
|
} );
|
|
94
116
|
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
{
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
case STATE_CANCELLED:
|
|
122
|
-
{
|
|
123
|
-
// console.log('ImageScene:cancelled');
|
|
124
|
-
// TODO
|
|
125
|
-
}
|
|
126
|
-
break;
|
|
127
|
-
|
|
128
|
-
case STATE_ERROR:
|
|
129
|
-
{
|
|
130
|
-
console.log('ImageScene:error', state);
|
|
131
|
-
}
|
|
132
|
-
break;
|
|
133
|
-
} // end switch
|
|
134
|
-
|
|
135
|
-
this.state = state;
|
|
117
|
+
$effect(() => {
|
|
118
|
+
if (state.current === STATE_ABORTING) {
|
|
119
|
+
const { sourcesAborted, numberOfSources } = this.#abortProgress;
|
|
120
|
+
|
|
121
|
+
if (sourcesAborted === numberOfSources) {
|
|
122
|
+
// console.debug(`ImageScene: ${numberOfSources} sources aborted`);
|
|
123
|
+
this.#state.send(ABORTED);
|
|
124
|
+
}
|
|
125
|
+
}
|
|
126
|
+
});
|
|
127
|
+
|
|
128
|
+
state.onenter = ( currentState ) => {
|
|
129
|
+
// console.log('onenter', currentState );
|
|
130
|
+
|
|
131
|
+
if(currentState === STATE_LOADING )
|
|
132
|
+
{
|
|
133
|
+
// console.log('ImageScene:loading');
|
|
134
|
+
this.#startLoading();
|
|
135
|
+
}
|
|
136
|
+
else if(currentState === STATE_ABORTING )
|
|
137
|
+
{
|
|
138
|
+
// console.log('ImageScene:aborting');
|
|
139
|
+
this.#startAbort();
|
|
140
|
+
}
|
|
141
|
+
|
|
142
|
+
this.state = currentState;
|
|
136
143
|
};
|
|
137
144
|
}
|
|
138
145
|
|
|
146
|
+
/* ==== Common loader interface */
|
|
147
|
+
|
|
148
|
+
/**
|
|
149
|
+
* Get image scene loading progress
|
|
150
|
+
*/
|
|
151
|
+
get progress() {
|
|
152
|
+
return this.#progress;
|
|
153
|
+
}
|
|
154
|
+
|
|
155
|
+
/**
|
|
156
|
+
* Get image scene abort progress
|
|
157
|
+
*/
|
|
158
|
+
get abortProgress() {
|
|
159
|
+
return this.#abortProgress;
|
|
160
|
+
}
|
|
161
|
+
|
|
162
|
+
/**
|
|
163
|
+
* Start loading all image sources
|
|
164
|
+
*/
|
|
165
|
+
load() {
|
|
166
|
+
this.#state.send(LOAD);
|
|
167
|
+
}
|
|
168
|
+
|
|
169
|
+
/**
|
|
170
|
+
* Abort loading all image sources
|
|
171
|
+
*/
|
|
172
|
+
abort() {
|
|
173
|
+
this.#state.send(ABORT);
|
|
174
|
+
}
|
|
175
|
+
|
|
139
176
|
destroy() {
|
|
140
177
|
// TODO: disconnect all image sources?
|
|
141
178
|
// TODO: Unload ImageLoaders?
|
|
142
179
|
}
|
|
143
180
|
|
|
181
|
+
/* ==== Source definitions */
|
|
182
|
+
|
|
144
183
|
/**
|
|
145
184
|
* Add image source
|
|
146
185
|
* - Uses an ImageLoader instance to load image data from network
|
|
@@ -159,42 +198,7 @@ export default class ImageScene {
|
|
|
159
198
|
this.#imageSources.push({ label, imageLoader });
|
|
160
199
|
}
|
|
161
200
|
|
|
162
|
-
|
|
163
|
-
* Start loading all image sources
|
|
164
|
-
*/
|
|
165
|
-
load() {
|
|
166
|
-
this.#state.send(LOAD);
|
|
167
|
-
}
|
|
168
|
-
|
|
169
|
-
async #startLoading() {
|
|
170
|
-
for (const { imageLoader } of this.#imageSources) {
|
|
171
|
-
imageLoader.load();
|
|
172
|
-
}
|
|
173
|
-
}
|
|
174
|
-
|
|
175
|
-
/**
|
|
176
|
-
* Get Image source
|
|
177
|
-
*
|
|
178
|
-
* @param {string} label
|
|
179
|
-
*
|
|
180
|
-
* @returns {ImageSceneSource}
|
|
181
|
-
*/
|
|
182
|
-
#getImageSceneSource(label) {
|
|
183
|
-
for (const source of this.#imageSources) {
|
|
184
|
-
if (label === source.label) {
|
|
185
|
-
return source;
|
|
186
|
-
}
|
|
187
|
-
}
|
|
188
|
-
|
|
189
|
-
throw new Error(`Source [${label}] has not been defined`);
|
|
190
|
-
}
|
|
191
|
-
|
|
192
|
-
/**
|
|
193
|
-
* Get image scene loading progress
|
|
194
|
-
*/
|
|
195
|
-
get progress() {
|
|
196
|
-
return this.#progress;
|
|
197
|
-
}
|
|
201
|
+
/* ==== Resource access */
|
|
198
202
|
|
|
199
203
|
/**
|
|
200
204
|
* Get an image loader
|
|
@@ -236,4 +240,35 @@ export default class ImageScene {
|
|
|
236
240
|
|
|
237
241
|
return source.imageLoader.getObjectURL();
|
|
238
242
|
}
|
|
239
|
-
|
|
243
|
+
|
|
244
|
+
async #startLoading() {
|
|
245
|
+
for (const { imageLoader } of this.#imageSources) {
|
|
246
|
+
imageLoader.load();
|
|
247
|
+
}
|
|
248
|
+
}
|
|
249
|
+
|
|
250
|
+
#startAbort() {
|
|
251
|
+
for (const { imageLoader } of this.#imageSources) {
|
|
252
|
+
imageLoader.abort();
|
|
253
|
+
}
|
|
254
|
+
}
|
|
255
|
+
|
|
256
|
+
/* ==== Internals */
|
|
257
|
+
|
|
258
|
+
/**
|
|
259
|
+
* Get Image source
|
|
260
|
+
*
|
|
261
|
+
* @param {string} label
|
|
262
|
+
*
|
|
263
|
+
* @returns {ImageSceneSource}
|
|
264
|
+
*/
|
|
265
|
+
#getImageSceneSource(label) {
|
|
266
|
+
for (const source of this.#imageSources) {
|
|
267
|
+
if (label === source.label) {
|
|
268
|
+
return source;
|
|
269
|
+
}
|
|
270
|
+
}
|
|
271
|
+
|
|
272
|
+
throw new Error(`Source [${label}] has not been defined`);
|
|
273
|
+
}
|
|
274
|
+
} // end class
|
|
@@ -45,9 +45,9 @@ export default class NetworkLoader {
|
|
|
45
45
|
/**
|
|
46
46
|
* Abort the current loading operation
|
|
47
47
|
* - Only works when in STATE_LOADING
|
|
48
|
-
* - Aborts network requests and transitions to
|
|
48
|
+
* - Aborts network requests and transitions to STATE_ABORTING
|
|
49
49
|
*/
|
|
50
|
-
|
|
50
|
+
abort(): void;
|
|
51
51
|
/**
|
|
52
52
|
* Get network data size in bytes
|
|
53
53
|
* - Info comes from the content length response header
|
|
@@ -7,14 +7,14 @@ import {
|
|
|
7
7
|
STATE_LOADING,
|
|
8
8
|
STATE_UNLOADING,
|
|
9
9
|
STATE_LOADED,
|
|
10
|
-
|
|
11
|
-
STATE_ERROR,
|
|
10
|
+
STATE_ABORTING,
|
|
12
11
|
LOAD,
|
|
13
12
|
ERROR,
|
|
14
13
|
LOADED,
|
|
15
14
|
UNLOAD,
|
|
16
15
|
INITIAL,
|
|
17
|
-
|
|
16
|
+
ABORT,
|
|
17
|
+
ABORTED
|
|
18
18
|
} from '../../state/machines.js';
|
|
19
19
|
|
|
20
20
|
import * as expect from '../../util/expect.js';
|
|
@@ -90,10 +90,6 @@ export default class NetworkLoader {
|
|
|
90
90
|
const state = this._state;
|
|
91
91
|
// const progress = this.progress;
|
|
92
92
|
|
|
93
|
-
//
|
|
94
|
-
// ISSUE: $effect is not triggered by this._state changes,
|
|
95
|
-
// using onenter instead
|
|
96
|
-
//
|
|
97
93
|
this._state.onenter = () => {
|
|
98
94
|
switch (state.current) {
|
|
99
95
|
case STATE_LOADING:
|
|
@@ -127,21 +123,23 @@ export default class NetworkLoader {
|
|
|
127
123
|
}
|
|
128
124
|
break;
|
|
129
125
|
|
|
130
|
-
case
|
|
126
|
+
case STATE_ABORTING:
|
|
131
127
|
{
|
|
132
|
-
// console.log('NetworkLoader:
|
|
128
|
+
// console.log('NetworkLoader:aborting');
|
|
133
129
|
if (this._abortLoading) {
|
|
134
130
|
this._abortLoading();
|
|
135
131
|
this._abortLoading = null;
|
|
136
132
|
}
|
|
133
|
+
// Transition to aborted state after abort completes
|
|
134
|
+
this._state.send(ABORTED);
|
|
137
135
|
}
|
|
138
136
|
break;
|
|
139
137
|
|
|
140
|
-
case STATE_ERROR:
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
138
|
+
// case STATE_ERROR:
|
|
139
|
+
// {
|
|
140
|
+
// console.log('NetworkLoader:error', state.error);
|
|
141
|
+
// }
|
|
142
|
+
// break;
|
|
145
143
|
} // end switch
|
|
146
144
|
};
|
|
147
145
|
}
|
|
@@ -164,10 +162,10 @@ export default class NetworkLoader {
|
|
|
164
162
|
/**
|
|
165
163
|
* Abort the current loading operation
|
|
166
164
|
* - Only works when in STATE_LOADING
|
|
167
|
-
* - Aborts network requests and transitions to
|
|
165
|
+
* - Aborts network requests and transitions to STATE_ABORTING
|
|
168
166
|
*/
|
|
169
|
-
|
|
170
|
-
this._state.send(
|
|
167
|
+
abort() {
|
|
168
|
+
this._state.send(ABORT);
|
|
171
169
|
}
|
|
172
170
|
|
|
173
171
|
/**
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/** @typedef {import('./typedef.js').
|
|
1
|
+
/** @typedef {import('./typedef.js').TransitionData} TransitionData */
|
|
2
2
|
/** @typedef {import('./typedef.js').OnEnterCallback} OnEnterCallback */
|
|
3
3
|
/** @typedef {import('./typedef.js').OnExitCallback} OnExitCallback */
|
|
4
4
|
/**
|
|
@@ -50,7 +50,7 @@ export default class FiniteStateMachine extends EventEmitter {
|
|
|
50
50
|
get current(): any;
|
|
51
51
|
#private;
|
|
52
52
|
}
|
|
53
|
-
export type
|
|
53
|
+
export type TransitionData = import("./typedef.js").TransitionData;
|
|
54
54
|
export type OnEnterCallback = import("./typedef.js").OnEnterCallback;
|
|
55
55
|
export type OnExitCallback = import("./typedef.js").OnExitCallback;
|
|
56
56
|
import EventEmitter from '../../../generic/events/classes/EventEmitter.js';
|