PageSourceSearch

https://trixbrix.eu/assets/px/tools/paint-77399650.js

js trixbrix.eu collected 2026-10-03 19:53:17 UTC 2,931 bytes, 89 lines download raw bytes

1import PaintCommand from "px/commands/paint"
2import { Tool } from "px/tools/tool"
3import { Overlay } from "px/tools/overlay"
4import { drawLegoTile } from "px/utils/lego_tile"
5import { EventEmitter } from "px/utils/events";
6import { receive } from "px/utils/deferred_promise";
7
8export default class extends Tool {
9  constructor(editor, renderer) {
10    super(editor);
11    Object.assign(this, EventEmitter);
12
13    this.renderer = renderer;
14    this.input = renderer.input;
15    this.painting = false;
16    this.paintCoords = [];
17    this.overlay = null;
18 }
19
20  async activate() {
21    this.input.on('mouseDown', this.onMouseDown);
22    this.input.on('mouseMove', this.onMouseMove);
23    this.input.on('mouseUp', this.onMouseUp);
24  }
25
26  async deactivate() {
27    this.input.off('mouseDown', this.onMouseDown);
28    this.input.off('mouseMove', this.onMouseMove);
29    this.input.off('mouseUp', this.onMouseUp);
30  }
31
32  onMouseDown = (coords) => {
33    this.painting = true;
34    this._emit("paintingStarted");
35    this.paintCoords = [];
36
37    const absolutePoint = this.mapLogicalToAbsolute(coords.x, coords.y);
38    this.paintCoords.push(absolutePoint);
39
40    this.overlay = new Overlay(this.renderer);
41    this._updateOverlay(this.paintCoords);
42  }
43
44  onMouseMove = (coords) => {
45    if (this.painting) {
46      const absolutePoint = this.mapLogicalToAbsolute(coords.x, coords.y);
47      this.paintCoords.push(absolutePoint);
48      this._updateOverlay(this.paintCoords);
49    }
50  }
51
52  onMouseUp = async () => {
53    if (this.painting) {
54      const currentColor = (await receive("uiSettings")).get("currentColor");
55      const paintCommand = new PaintCommand({ coords: this.paintCoords, color: currentColor });
56      this.painting = false;
57      this._emit("paintingFinished");
58      this.paintCoords = [];
59      const overlay = this.overlay;
60      this.overlay = null;
61
62      const imageVersion = await this.editor.execute(paintCommand);
63      overlay.hideOnCommandReady(imageVersion);
64    }
65  }
66
67  async _updateOverlay(coords) {
68    const currentColor = (await receive("uiSettings")).get("currentColor");
69    const paintCommand = new PaintCommand({ coords: coords, color: currentColor });
70    const context = this.editor.currentContext;
71    const pixelCoords = paintCommand.getPixelCoords(context.transform);
72    const overlayCtx = this.overlay.ctx;
73
74    const viewport = this.renderer.viewport;
75    const scale = viewport.scale;
76
77    this.overlay.clear();
78    
79    // Only paint pixels that are within the image boundaries
80    for (const pixelCoord of pixelCoords) {
81      if (pixelCoord.x >= 0 && pixelCoord.x < viewport.imageWidth &&
82          pixelCoord.y >= 0 && pixelCoord.y < viewport.imageHeight) {
83        const centerX = (pixelCoord.x + 0.5) * scale + viewport.offsetX;
84        const centerY = (pixelCoord.y + 0.5) * scale + viewport.offsetY;
85        drawLegoTile(overlayCtx, centerX, centerY, scale, `#${currentColor}`);
86      }
87    }
88  }
89}

Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.