Press n or j to go to the next uncovered block, b, p or k for the previous block.
| 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 | 1x 51x 6x 6x 6x 6x 6x 6x 1x 5x 1x 1x 6x 1x 4x 4x 4x 4x 4x 4x 4x 3x 6x 3x 1x 1x 1x 4x 4x 4x 4x 4x 4x 4x 4x 6x 6x 6x 6x 6x 6x 6x 6x 6x 6x | import { Slice } from "../slice";
import type { EditorContext } from "../editor-context";
import { ZoomSlice } from "./zoom-slice";
import { ViewportSlice } from "./viewport-slice";
import { CursorSlice } from "./cursor-slice";
import { TimingSlice } from "./timing-slice";
import { ChartSlice } from "./chart-slice";
import { SnapSlice } from "./snap-slice";
import { BASE_SCALE_Y, ZOOM_PRESETS } from "../types";
export class ViewCommandSlice extends Slice {
static readonly sliceKey = "viewCommand";
constructor(ctx: EditorContext) {
super(ctx);
}
setZoom(zoom: number): void {
const zoomSlice = this.ctx.get(ZoomSlice);
const viewport = this.ctx.get(ViewportSlice);
const oldZoom = zoomSlice.$zoom.get();
zoomSlice.$zoom.set(zoom);
const newScrollTop = this.computeZoomScrollOffset(oldZoom, zoom);
viewport.requestScroll({ x: viewport.$scroll.get().x, y: newScrollTop });
}
zoomIn(): void {
const current = this.ctx.get(ZoomSlice).$zoom.get();
const next = ZOOM_PRESETS.find((z) => z > current);
Eif (next) this.setZoom(next);
}
zoomOut(): void {
const current = this.ctx.get(ZoomSlice).$zoom.get();
const prev = [...ZOOM_PRESETS].reverse().find((z) => z < current);
Eif (prev) this.setZoom(prev);
}
navigateSnap(direction: "up" | "down"): void {
const cursor = this.ctx.get(CursorSlice);
const viewport = this.ctx.get(ViewportSlice);
const currentPulse = cursor.$cursorPulse.get();
const engine = this.ctx.get(TimingSlice).getTimingEngine();
const snap = this.ctx.get(SnapSlice).$snap.get();
const size = this.ctx.get(ChartSlice).getChartSize();
let targetPulse: number;
if (direction === "up") {
const points = engine.getSnapPoints(snap, { start: currentPulse, end: size });
const next = points.find((p) => p > currentPulse);
targetPulse = next !== undefined ? next : currentPulse;
} else {
const points = engine.getSnapPoints(snap, { start: 0, end: currentPulse });
const prev = points.length > 0 ? points[points.length - 1] : undefined;
targetPulse = prev !== undefined ? prev : currentPulse;
}
const scaleY = viewport.getScaleY();
const trackHeight = viewport.getTrackHeight();
const currentY = trackHeight - currentPulse * scaleY;
const targetY = trackHeight - targetPulse * scaleY;
const deltaY = targetY - currentY;
cursor.$cursorPulse.set(targetPulse);
const currentScroll = viewport.$scroll.get();
viewport.requestScroll({ x: currentScroll.x, y: currentScroll.y + deltaY });
}
computeZoomScrollOffset(oldZoom: number, newZoom: number): number {
const size = this.ctx.get(ChartSlice).getChartSize();
const oldScaleY = BASE_SCALE_Y * oldZoom;
const newScaleY = BASE_SCALE_Y * newZoom;
const cursorPulse = this.ctx.get(CursorSlice).$cursorPulse.get();
const oldScrollTop = this.ctx.get(ViewportSlice).$scroll.get().y;
const oldTrackHeight = size * oldScaleY;
const newTrackHeight = size * newScaleY;
const oldPlayheadY = oldTrackHeight - cursorPulse * oldScaleY - 1;
const newPlayheadY = newTrackHeight - cursorPulse * newScaleY - 1;
return oldScrollTop + newPlayheadY - oldPlayheadY;
}
}
|