@empirica/core
Version:
Empirica Core
208 lines (205 loc) • 4.91 kB
JavaScript
import {
Scope,
Scopes
} from "./chunk-RXGVZSIF.js";
// src/player/scopes.ts
var Scopes2 = class extends Scopes {
constructor(scopesObs, donesObs, ctx, kinds, attributes, steps) {
super(scopesObs, donesObs, ctx, kinds, attributes);
this.steps = steps;
}
create(scopeClass, scope) {
return new scopeClass(
this.ctx,
scope,
this,
this.attributes,
this.steps
);
}
};
var Scope2 = class extends Scope {
constructor(ctx, scope, scopes, attributes, steps) {
super(ctx, scope, attributes);
this.scopes = scopes;
this.steps = steps;
}
scopeByKey(key) {
const id = this.get(key);
if (!id || typeof id !== "string") {
return;
}
return this.scopes.scope(id);
}
ticker(id) {
return this.steps.step(id);
}
tickerByKey(key) {
const id = this.get(key);
if (!id || typeof id !== "string") {
return;
}
return this.ticker(id);
}
};
// src/player/steps.ts
import { BehaviorSubject, map } from "rxjs";
var scheduled = [];
var mockNow = null;
function pnow() {
if (mockNow !== null) {
return mockNow;
} else {
return performance.now();
}
}
function timeout(callback, ms) {
if (mockNow !== null) {
const schd = {
cb: callback,
from: mockNow,
dur: ms
};
scheduled.push(schd);
} else {
setTimeout(callback, ms);
}
}
var Step = class {
constructor(step, ticker) {
this.running = false;
this.ticker = new BehaviorSubject(void 0);
this.startAt = 0;
this.endAt = 0;
ticker.pipe(map(this.recalc.bind(this))).subscribe({
next: (val) => {
this.ticker.next(val);
}
});
this._update(step);
}
recalc(t) {
if (!this.running) {
return void 0;
}
return {
started: t >= this.startAt,
ended: t >= this.endAt,
elapsed: Math.round(t - this.startAt),
remaining: Math.round(this.endAt - t),
duration: this.endAt - this.startAt
};
}
obs() {
return this.ticker;
}
get current() {
return this.recalc(pnow());
}
// internal only
_update(step) {
if (!step.running) {
this.running = false;
this.ticker.next(void 0);
return;
}
if (step.elapsed === null || step.remaining === null || step.elapsed === void 0 || step.remaining === void 0) {
this.running = false;
return;
}
const now = pnow();
this.startAt = now - step.elapsed * 1e3;
this.endAt = now + step.remaining * 1e3;
this.running = step.elapsed >= 0 && step.remaining >= 0;
this.ticker.next(this.recalc(now));
}
// internal only
_stop() {
this.running = false;
this.ticker.next(void 0);
}
};
var Steps = class {
constructor(stepsObs, donesObs) {
this.steps = /* @__PURE__ */ new Map();
this.updates = /* @__PURE__ */ new Map();
this._hadUpdates = false;
stepsObs.subscribe({
next: ({ step, removed }) => {
this.update(step, removed);
}
});
donesObs.subscribe({
next: () => {
this.next();
}
});
this.ticker = new BehaviorSubject(Math.floor(pnow()));
const controller = new AbortController();
timerInterval(1e3, controller.signal, (t) => {
this.ticker.next(t);
});
}
step(stepID) {
return this.steps.get(stepID);
}
hadUpdates() {
const hadUpdates = this._hadUpdates;
this._hadUpdates = false;
return hadUpdates;
}
update(step, removed) {
if (removed) {
this.updates.set(step.id, true);
} else {
this.updates.set(step.id, step);
}
this._hadUpdates = true;
}
next() {
for (const [id, stepOrDel] of this.updates) {
let step = this.steps.get(id);
if (typeof stepOrDel === "boolean") {
if (step) {
step._stop();
this.steps.delete(id);
}
} else {
if (!step) {
step = new Step(stepOrDel, this.ticker);
this.steps.set(id, step);
}
step._update(stepOrDel);
}
}
this.updates.clear();
}
};
var root = typeof self === "object" && self.self == self ? self : typeof global === "object" && global.global == global ? global : {};
if (!root["requestAnimationFrame"]) {
root["requestAnimationFrame"] = (cb) => cb(pnow());
}
function timerInterval(ms = 1e3, signal, callback) {
const start = Math.floor(pnow() / 1e3) * 1e3;
function frame(time) {
if (signal.aborted)
return;
callback(time);
scheduleFrame(time);
}
function scheduleFrame(time) {
const elapsed = time - start;
const roundedElapsed = Math.round(elapsed / ms) * ms;
const targetNext = start + roundedElapsed + ms;
const delay = targetNext - pnow();
timeout(() => requestAnimationFrame(frame), delay);
}
scheduleFrame(start);
}
export {
Scopes2 as Scopes,
Scope2 as Scope,
Step,
Steps
};
//# sourceMappingURL=chunk-IJG2YOZB.js.map