import {EVENT_SELECT} from './config.js'; import {add, copy, mult} from './vector.js'; export class Select { sim = undefined; box = { start: undefined, end: undefined, }; selectedSingle = undefined; selectedGroup = []; constructor(sim) { this.sim = sim; // TODO: Move this to a new Keyboard class singleton window.addEventListener('keydown', (e) => { switch (e.key) { case 'Tab': { e.preventDefault(); if (!this.selectedGroup.length) return; const currentIdx = this.selectedGroup.indexOf(this.selectedSingle); const newIdx = (currentIdx + 1) % this.selectedGroup.length; this.selectedSingle = this.selectedGroup[newIdx]; break; } } }); } handlePointerDown({x: clientX, y: clientY}) { this.box.start = this.sim.screenToSim(clientX, clientY); this.box.end = this.box.start; // this.getSelectedObjects(); } handlePointerMove({x: clientX, y: clientY}) { if (!this.box.start) return; this.box.end = this.sim.screenToSim(clientX, clientY); } handlePointerUp() { if (!this.box.start) return; const start = copy(this.box.start); const end = copy(this.box.end); this.box.start = { x: Math.min(start.x, end.x), y: Math.min(start.y, end.y), }; this.box.end = { x: Math.max(start.x, end.x), y: Math.max(start.y, end.y), }; this.getSelectedObjects(); this.sim.div.dispatchEvent(new CustomEvent(EVENT_SELECT)); this.box = { start: undefined, end: undefined, }; } frame(elapsedTime) { if (!this.box.start) return; // If panning, let's update the position of our box so it doesn't drift away const {velocity} = this.sim.panning; const delta = mult(velocity, elapsedTime); this.box.start = add(this.box.start, delta); this.box.end = add(this.box.end, delta); // Display the box this.sim.display.drawBox(this.box.start, this.box.end); } getSelectedObjects() { const {start, end} = this.box; if (!start) return; this.selectedGroup = this.sim.system.filter(({position: {x, y}}) => { return x >= start.x && x <= end.x && y >= start.y && y <= end.y; }); // For now, first object in group is selected single this.selectedSingle = this.selectedGroup[0] ?? undefined; } // cb: ({selectedGroup, selectedSingle}) => undefined onSelect(cb) { this.sim.div.addEventListener(EVENT_SELECT, () => { const {selectedGroup, selectedSingle} = this; cb({selectedGroup, selectedSingle}); }); } }