mirror of
https://github.com/bilawalsidhu/gods-eye-view.git
synced 2026-11-05 10:53:59 +00:00
style: format state subscriptions and their adopted controls
This commit is contained in:
1 parent
45d97376d0
commit
e0652b19f2
12 files changed
+299
-88
No files matched your search
+77
-14
@@ -2,16 +2,50 @@ import { createStateChannel } from '../app/stateChannel.js';
|
||||
|
||||
/** One cancellable place lookup at a time, under the caller's camera authority. */
|
||||
export class LocationSearch {
|
||||
constructor({ input, begin, isCurrent, beforeFly, search, onStart, onResult, onMissing, onError, onSettled }) {
|
||||
Object.assign(this, { input, begin, isCurrent, beforeFly, search, onStart, onResult, onMissing, onError, onSettled });
|
||||
constructor({
|
||||
input,
|
||||
begin,
|
||||
isCurrent,
|
||||
beforeFly,
|
||||
search,
|
||||
onStart,
|
||||
onResult,
|
||||
onMissing,
|
||||
onError,
|
||||
onSettled,
|
||||
}) {
|
||||
Object.assign(this, {
|
||||
input,
|
||||
begin,
|
||||
isCurrent,
|
||||
beforeFly,
|
||||
search,
|
||||
onStart,
|
||||
onResult,
|
||||
onMissing,
|
||||
onError,
|
||||
onSettled,
|
||||
});
|
||||
this.controller = null;
|
||||
this.generation = 0;
|
||||
this.destroyed = false;
|
||||
this.state = { status: 'idle', searching: false, query: '', generation: null, requestId: 0, destination: null, error: null };
|
||||
this.state = {
|
||||
status: 'idle',
|
||||
searching: false,
|
||||
query: '',
|
||||
generation: null,
|
||||
requestId: 0,
|
||||
destination: null,
|
||||
error: null,
|
||||
};
|
||||
this.channel = createStateChannel(() => this.state);
|
||||
}
|
||||
getState() { return this.channel.getSnapshot(); }
|
||||
subscribe(listener, options) { return this.channel.subscribe(listener, options); }
|
||||
getState() {
|
||||
return this.channel.getSnapshot();
|
||||
}
|
||||
subscribe(listener, options) {
|
||||
return this.channel.subscribe(listener, options);
|
||||
}
|
||||
async run(query) {
|
||||
query = String(query || '').trim();
|
||||
if (!query || this.destroyed) return;
|
||||
@@ -25,9 +59,25 @@ export class LocationSearch {
|
||||
const controller = new AbortController();
|
||||
this.controller = controller;
|
||||
const generation = ++this.generation;
|
||||
const current = () => !this.destroyed && generation === this.generation && this.isCurrent(authority);
|
||||
const change = (type) => ({ type, generation: authority, requestId: generation, query });
|
||||
this.state = { status: 'searching', searching: true, query, generation: authority, requestId: generation, destination: null, error: null };
|
||||
const current = () =>
|
||||
!this.destroyed &&
|
||||
generation === this.generation &&
|
||||
this.isCurrent(authority);
|
||||
const change = (type) => ({
|
||||
type,
|
||||
generation: authority,
|
||||
requestId: generation,
|
||||
query,
|
||||
});
|
||||
this.state = {
|
||||
status: 'searching',
|
||||
searching: true,
|
||||
query,
|
||||
generation: authority,
|
||||
requestId: generation,
|
||||
destination: null,
|
||||
error: null,
|
||||
};
|
||||
try {
|
||||
this.onStart?.(authority);
|
||||
if (!current() || controller.signal.aborted) return;
|
||||
@@ -43,7 +93,11 @@ export class LocationSearch {
|
||||
if (destination) {
|
||||
this.onResult?.(destination, query);
|
||||
if (!current() || controller.signal.aborted) return;
|
||||
this.state = { ...this.state, status: 'found', destination: { ...destination } };
|
||||
this.state = {
|
||||
...this.state,
|
||||
status: 'found',
|
||||
destination: { ...destination },
|
||||
};
|
||||
this.channel.publish(change('found'));
|
||||
} else {
|
||||
this.onMissing?.();
|
||||
@@ -55,15 +109,24 @@ export class LocationSearch {
|
||||
if (controller.signal.aborted || !current()) return;
|
||||
this.onError?.(error);
|
||||
if (!current() || controller.signal.aborted) return;
|
||||
this.state = { ...this.state, status: 'failed', error: { message: String(error?.message || error) } };
|
||||
this.state = {
|
||||
...this.state,
|
||||
status: 'failed',
|
||||
error: { message: String(error?.message || error) },
|
||||
};
|
||||
this.channel.publish(change('failed'));
|
||||
} finally {
|
||||
if (this.controller === controller) this.controller = null;
|
||||
if (!this.destroyed) {
|
||||
if (generation === this.generation) this.state = {
|
||||
...this.state, searching: false,
|
||||
status: this.state.status === 'searching' ? 'cancelled' : this.state.status,
|
||||
};
|
||||
if (generation === this.generation)
|
||||
this.state = {
|
||||
...this.state,
|
||||
searching: false,
|
||||
status:
|
||||
this.state.status === 'searching'
|
||||
? 'cancelled'
|
||||
: this.state.status,
|
||||
};
|
||||
this.onSettled?.(authority);
|
||||
this.channel.publish(change('settled'));
|
||||
}
|
||||
|
||||
Reference in new issue
Block a user