{"version":3,"file":"tracespace-plotter.umd.cjs","sources":["../src/tree.ts","../src/coordinate-math.ts","../src/bounding-box.ts","../src/options.ts","../src/tool-store.ts","../src/location-store.ts","../src/graphic-plotter/shapes.ts","../src/graphic-plotter/plot-shape.ts","../src/graphic-plotter/plot-rect-path.ts","../src/graphic-plotter/plot-path.ts","../src/graphic-plotter/plot-macro.ts","../src/graphic-plotter/index.ts","../src/index.ts"],"sourcesContent":["import type {Node, Parent} from 'unist'\n\nimport type {UnitsType} from '@tracespace/parser'\n\nexport const IMAGE = 'image'\nexport const IMAGE_SHAPE = 'imageShape'\nexport const IMAGE_PATH = 'imagePath'\nexport const IMAGE_REGION = 'imageRegion'\n\nexport const LINE = 'line'\nexport const ARC = 'arc'\n\nexport const CIRCLE = 'circle'\nexport const RECTANGLE = 'rectangle'\nexport const POLYGON = 'polygon'\nexport const OUTLINE = 'outline'\nexport const LAYERED_SHAPE = 'layeredShape'\n\nexport type Position = [x: number, y: number]\n\nexport type ArcPosition = [x: number, y: number, theta: number]\n\nexport type SizeEnvelope = [x1: number, y1: number, x2: number, y2: number] | []\n\nexport type ImageNode = ImageTree | ImageShape | ImagePath | ImageRegion\n\nexport interface CircleShape {\n  type: typeof CIRCLE\n  cx: number\n  cy: number\n  r: number\n}\n\nexport interface RectangleShape {\n  type: typeof RECTANGLE\n  x: number\n  y: number\n  xSize: number\n  ySize: number\n  r?: number\n}\n\nexport interface PolygonShape {\n  type: typeof POLYGON\n  points: Position[]\n}\n\nexport interface OutlineShape {\n  type: typeof OUTLINE\n  segments: PathSegment[]\n}\n\nexport interface LayeredShape {\n  type: typeof LAYERED_SHAPE\n  shapes: ErasableShape[]\n}\n\nexport type HoleShape = CircleShape | RectangleShape\n\nexport type SimpleShape =\n  | CircleShape\n  | RectangleShape\n  | PolygonShape\n  | OutlineShape\n\nexport type Shape = SimpleShape | LayeredShape\n\nexport type ErasableShape = SimpleShape & {erase?: boolean}\n\nexport type ImageGraphic = ImageShape | ImagePath | ImageRegion\n\nexport interface ImageTree extends Parent {\n  type: typeof IMAGE\n  units: UnitsType\n  size: SizeEnvelope\n  children: ImageGraphic[]\n}\n\nexport interface ImageShape extends Node {\n  type: typeof IMAGE_SHAPE\n  shape: Shape\n}\n\nexport interface ImagePath extends Node {\n  type: typeof IMAGE_PATH\n  width: number\n  segments: PathSegment[]\n}\n\nexport interface ImageRegion extends Node {\n  type: typeof IMAGE_REGION\n  segments: PathSegment[]\n}\n\nexport type PathSegment = PathLineSegment | PathArcSegment\n\nexport interface PathLineSegment {\n  type: typeof LINE\n  start: Position\n  end: Position\n}\n\nexport interface PathArcSegment {\n  type: typeof ARC\n  start: ArcPosition\n  end: ArcPosition\n  center: Position\n  radius: number\n}\n","// Mathematical procedures\nimport type {Position} from './tree'\n\nexport const {PI} = Math\nexport const HALF_PI = PI / 2\nexport const THREE_HALF_PI = 3 * HALF_PI\nexport const TWO_PI = 2 * PI\n\nexport function limitAngle(theta: number): number {\n  if (theta >= 0 && theta <= TWO_PI) return theta\n  if (theta < 0) return theta + TWO_PI\n  if (theta > TWO_PI) return theta - TWO_PI\n  return limitAngle(theta)\n}\n\nexport function rotateQuadrant(theta: number): number {\n  return theta >= HALF_PI ? theta - HALF_PI : theta + THREE_HALF_PI\n}\n\nexport function degreesToRadians(degrees: number): number {\n  return (degrees * Math.PI) / 180\n}\n\nexport function rotateAndShift(\n  point: Position,\n  shift: Position,\n  degrees = 0\n): Position {\n  const rotation = degreesToRadians(degrees)\n  const [sin, cos] = [Math.sin(rotation), Math.cos(rotation)]\n  const [x, y] = point\n  const nextX = x * cos - y * sin + shift[0]\n  const nextY = x * sin + y * cos + shift[1]\n\n  return [nextX, nextY]\n}\n\nexport function positionsEqual(a: number[], b: number[]): boolean {\n  return a[0] === b[0] && a[1] === b[1]\n}\n","import * as Tree from './tree'\nimport {TWO_PI, limitAngle, rotateQuadrant} from './coordinate-math'\nimport type {SizeEnvelope as Box, Position, ArcPosition} from './tree'\n\nexport type {SizeEnvelope as Box} from './tree'\n\nexport function isEmpty(box: Box): box is [] {\n  return box.length === 0\n}\n\nexport function empty(): Box {\n  return []\n}\n\nexport function add(a: Box, b: Box): Box {\n  if (isEmpty(a)) return b\n  if (isEmpty(b)) return a\n\n  return [\n    Math.min(a[0], b[0]),\n    Math.min(a[1], b[1]),\n    Math.max(a[2], b[2]),\n    Math.max(a[3], b[3]),\n  ]\n}\n\nexport function sum(boxes: Box[]): Box {\n  return boxes.reduce(add, empty())\n}\n\nexport function fromGraphics(graphics: Tree.ImageGraphic[]): Box {\n  return sum(graphics.map(fromGraphic))\n}\n\nexport function fromGraphic(graphic: Tree.ImageGraphic): Box {\n  return graphic.type === Tree.IMAGE_SHAPE\n    ? fromShape(graphic.shape)\n    : fromPath(\n        graphic.segments,\n        graphic.type === Tree.IMAGE_PATH ? graphic.width : undefined\n      )\n}\n\nexport function fromShape(shape: Tree.Shape): Box {\n  switch (shape.type) {\n    case Tree.CIRCLE: {\n      const {cx, cy, r} = shape\n      return fromPosition([cx, cy], r)\n    }\n\n    case Tree.RECTANGLE: {\n      const {x, y, xSize, ySize} = shape\n      return [x, y, x + xSize, y + ySize]\n    }\n\n    case Tree.POLYGON: {\n      return sum(shape.points.map(p => fromPosition(p)))\n    }\n\n    case Tree.OUTLINE: {\n      return fromPath(shape.segments)\n    }\n\n    case Tree.LAYERED_SHAPE: {\n      return sum(shape.shapes.filter(({erase}) => !erase).map(fromShape))\n    }\n  }\n}\n\nexport function fromPath(segments: Tree.PathSegment[], width = 0): Box {\n  const rTool = width / 2\n  const keyPoints: Array<Tree.Position | Tree.ArcPosition> = []\n\n  for (const segment of segments) {\n    keyPoints.push(segment.start, segment.end)\n\n    if (segment.type === Tree.ARC) {\n      const {start, end, center, radius} = segment\n      const sweep = Math.abs(end[2] - start[2])\n\n      // Normalize direction to counter-clockwise\n      let [thetaStart, thetaEnd] =\n        end[2] > start[2] ? [start[2], end[2]] : [end[2], start[2]]\n\n      thetaStart = limitAngle(thetaStart)\n      thetaEnd = limitAngle(thetaEnd)\n\n      const axisPoints: Tree.Position[] = [\n        [center[0] + radius, center[1]],\n        [center[0], center[1] + radius],\n        [center[0] - radius, center[1]],\n        [center[0], center[1] - radius],\n      ]\n\n      for (const p of axisPoints) {\n        if (thetaStart > thetaEnd || sweep === TWO_PI) {\n          keyPoints.push(p)\n        }\n\n        // Rotate to check for next axis key point\n        thetaStart = rotateQuadrant(thetaStart)\n        thetaEnd = rotateQuadrant(thetaEnd)\n      }\n    }\n  }\n\n  return sum(keyPoints.map(p => fromPosition(p, rTool)))\n}\n\nfunction fromPosition(position: Position | ArcPosition, radius = 0): Box {\n  return [\n    position[0] - radius,\n    position[1] - radius,\n    position[0] + radius,\n    position[1] + radius,\n  ]\n}\n","import type {\n  GerberTree,\n  UnitsType,\n  Format,\n  ZeroSuppression,\n} from '@tracespace/parser'\nimport {\n  UNITS,\n  COORDINATE_FORMAT,\n  GRAPHIC,\n  COMMENT,\n  LEADING,\n  TRAILING,\n  IN,\n} from '@tracespace/parser'\n\nexport interface PlotOptions {\n  units: UnitsType\n  coordinateFormat: Format\n  zeroSuppression: ZeroSuppression\n}\n\nconst FORMAT_COMMENT_RE = /FORMAT={?(\\d):(\\d)/\n\nexport function getPlotOptions(tree: GerberTree): PlotOptions {\n  const {children: treeNodes} = tree\n  let units: UnitsType | null = null\n  let coordinateFormat: Format | null = null\n  let zeroSuppression: ZeroSuppression | null = null\n  let index = 0\n\n  while (\n    index < treeNodes.length &&\n    (units === null || coordinateFormat === null || zeroSuppression === null)\n  ) {\n    const node = treeNodes[index]\n\n    switch (node.type) {\n      case UNITS: {\n        units = node.units\n        break\n      }\n\n      case COORDINATE_FORMAT: {\n        coordinateFormat = node.format\n        zeroSuppression = node.zeroSuppression\n        break\n      }\n\n      case GRAPHIC: {\n        const {coordinates} = node\n\n        for (const coordinate of Object.values(coordinates)) {\n          if (zeroSuppression !== null) break\n\n          if (coordinate!.endsWith('0') || coordinate!.includes('.')) {\n            zeroSuppression = LEADING\n          } else if (coordinate!.startsWith('0')) {\n            zeroSuppression = TRAILING\n          }\n        }\n\n        break\n      }\n\n      case COMMENT: {\n        const {comment} = node\n        const formatMatch = FORMAT_COMMENT_RE.exec(comment)\n\n        if (/suppress trailing/i.test(comment)) {\n          zeroSuppression = TRAILING\n        } else if (/(suppress leading|keep zeros)/i.test(comment)) {\n          zeroSuppression = LEADING\n        }\n\n        if (formatMatch) {\n          coordinateFormat = [Number(formatMatch[1]), Number(formatMatch[2])]\n        }\n\n        break\n      }\n\n      default:\n    }\n\n    index += 1\n  }\n\n  return {\n    units: units ?? IN,\n    coordinateFormat: coordinateFormat ?? [2, 4],\n    zeroSuppression: zeroSuppression ?? LEADING,\n  }\n}\n","// Tool store\n// Keeps track of the defined tools, defined macros, and the current tool\nimport type {\n  GerberNode,\n  SimpleShape,\n  HoleShape,\n  MacroBlock,\n} from '@tracespace/parser'\nimport {\n  MACRO_SHAPE,\n  TOOL_CHANGE,\n  TOOL_DEFINITION,\n  TOOL_MACRO,\n} from '@tracespace/parser'\n\nexport const SIMPLE_TOOL = 'simpleTool'\n\nexport const MACRO_TOOL = 'macroTool'\n\nexport interface SimpleTool {\n  type: typeof SIMPLE_TOOL\n  shape: SimpleShape\n  hole?: HoleShape\n}\n\nexport interface MacroTool {\n  type: typeof MACRO_TOOL\n  macro: MacroBlock[]\n  variableValues: number[]\n}\n\nexport type Tool = SimpleTool | MacroTool\n\nexport interface ToolStore {\n  use(node: GerberNode): Tool | undefined\n}\n\nexport function createToolStore(): ToolStore {\n  return Object.create(ToolStorePrototype)\n}\n\ninterface ToolStoreState {\n  _currentToolCode: string | undefined\n  _toolsByCode: Partial<Record<string, Tool>>\n  _macrosByName: Partial<Record<string, MacroBlock[]>>\n}\n\nconst ToolStorePrototype: ToolStore & ToolStoreState = {\n  _currentToolCode: undefined,\n  _toolsByCode: {},\n  _macrosByName: {},\n\n  use(node: GerberNode): Tool | undefined {\n    if (node.type === TOOL_MACRO) {\n      this._macrosByName[node.name] = node.children\n    }\n\n    if (node.type === TOOL_DEFINITION) {\n      const {shape, hole} = node\n      const tool: Tool =\n        shape.type === MACRO_SHAPE\n          ? {\n              type: MACRO_TOOL,\n              macro: this._macrosByName[shape.name] ?? [],\n              variableValues: shape.variableValues,\n            }\n          : {type: SIMPLE_TOOL, shape, ...(hole && {hole})}\n\n      this._toolsByCode[node.code] = tool\n    }\n\n    if (node.type === TOOL_DEFINITION || node.type === TOOL_CHANGE) {\n      this._currentToolCode = node.code\n    }\n\n    return typeof this._currentToolCode === 'string'\n      ? this._toolsByCode[this._currentToolCode]\n      : undefined\n  },\n}\n","// Track the location of the plotter and parse coordinate strings\nimport type {GerberNode} from '@tracespace/parser'\nimport {GRAPHIC, TRAILING} from '@tracespace/parser'\n\nimport type {PlotOptions} from './options'\n\nexport interface Point {\n  x: number\n  y: number\n}\n\nexport interface ArcOffsets {\n  i: number\n  j: number\n  a: number\n}\n\nexport interface Location {\n  startPoint: Point\n  endPoint: Point\n  arcOffsets: ArcOffsets\n}\n\nexport interface LocationStore {\n  use(node: GerberNode, options: PlotOptions): Location\n}\n\nexport function createLocationStore(): LocationStore {\n  return Object.create(LocationStorePrototype)\n}\n\ninterface LocationStoreState {\n  _DEFAULT_ARC_OFFSETS: ArcOffsets\n  _previousPoint: Point\n}\n\nconst LocationStorePrototype: LocationStore & LocationStoreState = {\n  _DEFAULT_ARC_OFFSETS: {i: 0, j: 0, a: 0},\n  _previousPoint: {x: 0, y: 0},\n\n  use(node: GerberNode, options: PlotOptions): Location {\n    let arcOffsets = this._DEFAULT_ARC_OFFSETS\n    let startPoint = this._previousPoint\n    let endPoint = startPoint\n\n    if (node.type === GRAPHIC) {\n      const {coordinates} = node\n      const x0 = parseCoordinate(coordinates.x0, startPoint.x, options)\n      const y0 = parseCoordinate(coordinates.y0, startPoint.y, options)\n      const x = parseCoordinate(coordinates.x, x0, options)\n      const y = parseCoordinate(coordinates.y, y0, options)\n      const i = parseCoordinate(coordinates.i, 0, options)\n      const j = parseCoordinate(coordinates.j, 0, options)\n      const a = parseCoordinate(coordinates.a, 0, options)\n\n      if (startPoint.x !== x0 || startPoint.y !== y0) {\n        startPoint = {x: x0, y: y0}\n      }\n\n      if (endPoint.x !== x || endPoint.y !== y) {\n        endPoint = {x, y}\n      }\n\n      if (i !== 0 || j !== 0 || a !== 0) {\n        arcOffsets = {i, j, a}\n      }\n    }\n\n    this._previousPoint = endPoint\n    return {startPoint, endPoint, arcOffsets}\n  },\n}\n\nfunction parseCoordinate(\n  coordinate: string | undefined,\n  defaultValue: number,\n  options: PlotOptions\n): number {\n  if (typeof coordinate !== 'string') {\n    return defaultValue\n  }\n\n  if (coordinate.includes('.') || coordinate === '0') {\n    return Number(coordinate)\n  }\n\n  const {coordinateFormat, zeroSuppression} = options\n  const [integerPlaces, decimalPlaces] = coordinateFormat\n\n  const [sign, signlessCoordinate] =\n    coordinate.startsWith('+') || coordinate.startsWith('-')\n      ? [coordinate[0], coordinate.slice(1)]\n      : ['+', coordinate]\n\n  const digits = integerPlaces + decimalPlaces\n  const paddedCoordinate =\n    zeroSuppression === TRAILING\n      ? signlessCoordinate.padEnd(digits, '0')\n      : signlessCoordinate.padStart(digits, '0')\n\n  const leading = paddedCoordinate.slice(0, integerPlaces)\n  const trailing = paddedCoordinate.slice(integerPlaces)\n\n  return Number(`${sign}${leading}.${trailing}`)\n}\n","import type {SimpleShape} from '@tracespace/parser'\nimport {CIRCLE, RECTANGLE, OBROUND, POLYGON} from '@tracespace/parser'\n\nimport {\n  HALF_PI,\n  PI,\n  THREE_HALF_PI,\n  TWO_PI,\n  degreesToRadians,\n} from '../coordinate-math'\n\nimport * as Tree from '../tree'\nimport type {Point} from '../location-store'\n\nexport function createShape(\n  shape: SimpleShape,\n  point: Point\n): Tree.SimpleShape {\n  const {x, y} = point\n\n  switch (shape.type) {\n    case CIRCLE: {\n      const {diameter} = shape\n      return {type: Tree.CIRCLE, cx: x, cy: y, r: diameter / 2}\n    }\n\n    case RECTANGLE:\n    case OBROUND: {\n      const {xSize, ySize} = shape\n      const xHalf = xSize / 2\n      const yHalf = ySize / 2\n      const rectangle: Tree.RectangleShape = {\n        type: Tree.RECTANGLE,\n        x: x - xHalf,\n        y: y - yHalf,\n        xSize,\n        ySize,\n      }\n\n      if (shape.type === OBROUND) {\n        rectangle.r = Math.min(xHalf, yHalf)\n      }\n\n      return rectangle\n    }\n\n    case POLYGON: {\n      const {diameter, rotation, vertices} = shape\n      const r = diameter / 2\n      const offset = degreesToRadians(rotation ?? 0)\n      const step = TWO_PI / vertices\n      const points = Array.from({length: vertices}).map<Tree.Position>(\n        (_, i) => {\n          const theta = step * i + offset\n          const pointX = x + r * Math.cos(theta)\n          const pointY = y + r * Math.sin(theta)\n          return [pointX, pointY]\n        }\n      )\n\n      return {type: Tree.POLYGON, points}\n    }\n  }\n}\n\nexport function shapeToSegments(shape: Tree.SimpleShape): Tree.PathSegment[] {\n  if (shape.type === Tree.CIRCLE) {\n    const {cx, cy, r} = shape\n    return [\n      {\n        type: Tree.ARC,\n        start: [cx + r, cy, 0],\n        end: [cx + r, cy, TWO_PI],\n        center: [cx, cy],\n        radius: r,\n      },\n    ]\n  }\n\n  if (shape.type === Tree.RECTANGLE) {\n    const {x, y, xSize, ySize, r} = shape\n\n    if (r === xSize / 2) {\n      return [\n        {\n          type: Tree.LINE,\n          start: [x + xSize, y + r],\n          end: [x + xSize, y + ySize - r],\n        },\n        {\n          type: Tree.ARC,\n          start: [x + xSize, y + ySize - r, 0],\n          end: [x, y + ySize - r, PI],\n          center: [x + r, y + ySize - r],\n          radius: r,\n        },\n        {type: Tree.LINE, start: [x, y + ySize - r], end: [x, y + r]},\n        {\n          type: Tree.ARC,\n          start: [x, y + r, PI],\n          end: [x + xSize, y + r, TWO_PI],\n          center: [x + r, y + r],\n          radius: r,\n        },\n      ]\n    }\n\n    if (r === ySize / 2) {\n      return [\n        {type: Tree.LINE, start: [x + r, y], end: [x + xSize - r, y]},\n        {\n          type: Tree.ARC,\n          start: [x + xSize - r, y, -HALF_PI],\n          end: [x + xSize - r, y + ySize, HALF_PI],\n          center: [x + xSize - r, y + r],\n          radius: r,\n        },\n        {\n          type: Tree.LINE,\n          start: [x + xSize - r, y + ySize],\n          end: [x + r, y + ySize],\n        },\n        {\n          type: Tree.ARC,\n          start: [x + r, y + ySize, HALF_PI],\n          end: [x + r, y, THREE_HALF_PI],\n          center: [x + r, y + r],\n          radius: r,\n        },\n      ]\n    }\n\n    return [\n      {type: Tree.LINE, start: [x, y], end: [x + xSize, y]},\n      {type: Tree.LINE, start: [x + xSize, y], end: [x + xSize, y + ySize]},\n      {type: Tree.LINE, start: [x + xSize, y + ySize], end: [x, y + ySize]},\n      {type: Tree.LINE, start: [x, y + ySize], end: [x, y]},\n    ]\n  }\n\n  if (shape.type === Tree.POLYGON) {\n    return shape.points.map((start, i) => {\n      const endIndex = i < shape.points.length - 1 ? i + 1 : 0\n      return {type: Tree.LINE, start, end: shape.points[endIndex]}\n    })\n  }\n\n  return shape.segments\n}\n","import {MACRO_SHAPE} from '@tracespace/parser'\n\nimport * as Tree from '../tree'\nimport type {Location} from '../location-store'\nimport type {SimpleTool} from '../tool-store'\n\nimport {createShape, shapeToSegments} from './shapes'\n\nexport function plotShape(tool: SimpleTool, location: Location): Tree.Shape {\n  const {shape: toolShape, hole: toolHole} = tool\n  const shape = createShape(toolShape, location.endPoint)\n  const holeShape = toolHole\n    ? createShape(toolHole, location.endPoint)\n    : undefined\n\n  return holeShape === undefined\n    ? shape\n    : {\n        type: Tree.OUTLINE,\n        segments: [...shapeToSegments(shape), ...shapeToSegments(holeShape)],\n      }\n}\n","// Functions for stroking rectangular tools\n// Stroking rectangular tools is deprecated by the Gerber spec\n// This functionality may be dropped and replaced with a warning\nimport type {Rectangle} from '@tracespace/parser'\n\nimport * as Tree from '../tree'\nimport {positionsEqual, HALF_PI, PI} from '../coordinate-math'\n\n// Rectangular tools make interesting stroke geometry; see the Gerber spec\n// for graphics and examples\nexport function plotRectPath(\n  segments: Tree.PathSegment[],\n  shape: Rectangle\n): Tree.ImageShape {\n  const shapes = segments\n    .filter((s): s is Tree.PathLineSegment => s.type === Tree.LINE)\n    .map(segment => plotRectPathSegment(segment, shape))\n\n  return {type: Tree.IMAGE_SHAPE, shape: {type: Tree.LAYERED_SHAPE, shapes}}\n}\n\nfunction plotRectPathSegment(\n  segment: Tree.PathLineSegment,\n  shape: Rectangle\n): Tree.PolygonShape {\n  // Since a rectangular stroke like this is so unique to Gerber, it's easier\n  // for downstream graphics generators if we calculate the boundaries of the\n  // correct shape and emit a region rather than a path with a width (which is\n  // what we do for circle tools)\n  const {start, end} = segment\n  const [sx, sy] = start\n  const [ex, ey] = end\n  const [xOffset, yOffset] = [shape.xSize / 2, shape.ySize / 2]\n  const theta = Math.atan2(ey - sy, ex - ey)\n\n  const [sxMin, sxMax] = [sx - xOffset, sx + xOffset]\n  const [syMin, syMax] = [sy - yOffset, sy + yOffset]\n  const [exMin, exMax] = [ex - xOffset, ex + xOffset]\n  const [eyMin, eyMax] = [ey - yOffset, ey + yOffset]\n\n  // Go through the quadrants of the XY plane centered about start to decide\n  // which segments define the boundaries of the stroke shape\n  let points: Tree.Position[] = []\n  if (positionsEqual(start, end)) {\n    points = [\n      [sxMin, syMin],\n      [sxMax, syMin],\n      [exMax, eyMin],\n      [exMax, eyMax],\n      [exMin, eyMax],\n      [sxMin, syMax],\n    ]\n  } else if (theta >= 0 && theta < HALF_PI) {\n    // First quadrant move\n    points = [\n      [sxMin, syMin],\n      [sxMax, syMin],\n      [exMax, eyMin],\n      [exMax, eyMax],\n      [exMin, eyMax],\n      [sxMin, syMax],\n    ]\n  } else if (theta >= HALF_PI && theta <= PI) {\n    // Second quadrant move\n    points = [\n      [sxMax, syMin],\n      [sxMax, syMax],\n      [exMax, eyMax],\n      [exMin, eyMax],\n      [exMin, eyMin],\n      [sxMin, syMin],\n    ]\n  } else if (theta >= -PI && theta < -HALF_PI) {\n    // Third quadrant move\n    points = [\n      [sxMax, syMax],\n      [sxMin, syMax],\n      [exMin, eyMax],\n      [exMin, eyMin],\n      [exMax, eyMin],\n      [sxMax, syMin],\n    ]\n  } else {\n    // Fourth quadrant move\n    points = [\n      [sxMin, syMax],\n      [sxMin, syMin],\n      [exMin, eyMin],\n      [exMax, eyMin],\n      [exMax, eyMax],\n      [sxMax, syMax],\n    ]\n  }\n\n  return {type: Tree.POLYGON, points}\n}\n","import * as Tree from '../tree'\nimport type {Tool} from '../tool-store'\nimport {SIMPLE_TOOL} from '../tool-store'\nimport type {Location, Point} from '../location-store'\nimport {TWO_PI} from '../coordinate-math'\n\nimport {plotRectPath} from './plot-rect-path'\n\nexport const CW = 'cw'\nexport const CCW = 'ccw'\n\nexport type ArcDirection = typeof CW | typeof CCW\n\nexport function plotSegment(\n  location: Location,\n  arcDirection?: ArcDirection,\n  ambiguousArcCenter?: boolean\n): Tree.PathSegment {\n  return arcDirection === undefined\n    ? createLineSegment(location)\n    : createArcSegment(location, arcDirection, ambiguousArcCenter)\n}\n\nexport function plotPath(\n  segments: Tree.PathSegment[],\n  tool: Tool | undefined,\n  region = false\n): Tree.ImageGraphic | undefined {\n  if (segments.length > 0) {\n    if (region) {\n      return {type: Tree.IMAGE_REGION, segments}\n    }\n\n    if (tool?.type === SIMPLE_TOOL && tool.shape.type === Tree.CIRCLE) {\n      return {type: Tree.IMAGE_PATH, width: tool.shape.diameter, segments}\n    }\n\n    if (tool?.type === SIMPLE_TOOL && tool.shape.type === Tree.RECTANGLE) {\n      return plotRectPath(segments, tool.shape)\n    }\n  }\n}\n\nfunction createLineSegment(location: Location): Tree.PathLineSegment {\n  return {\n    type: Tree.LINE,\n    start: [location.startPoint.x, location.startPoint.y],\n    end: [location.endPoint.x, location.endPoint.y],\n  }\n}\n\nfunction createArcSegment(\n  location: Location,\n  arcDirection: ArcDirection,\n  ambiguousArcCenter = false\n): Tree.PathSegment {\n  const {startPoint, endPoint, arcOffsets} = location\n  const radius =\n    arcOffsets.a > 0\n      ? arcOffsets.a\n      : (arcOffsets.i ** 2 + arcOffsets.j ** 2) ** 0.5\n\n  if (ambiguousArcCenter || arcOffsets.a > 0) {\n    if (startPoint.x === endPoint.x && startPoint.y === endPoint.y) {\n      return createLineSegment(location)\n    }\n\n    // Get the center candidates and select the candidate with the smallest arc\n    const [start, end, center] = findCenterCandidates(location, radius)\n      .map(centerPoint => {\n        return getArcPositions(startPoint, endPoint, centerPoint, arcDirection)\n      })\n      .sort(([startA, endA], [startB, endB]) => {\n        const absSweepA = Math.abs(endA[2] - startA[2])\n        const absSweepB = Math.abs(endB[2] - startB[2])\n        return absSweepA - absSweepB\n      })[0]\n\n    return {type: Tree.ARC, start, end, center, radius}\n  }\n\n  const centerPoint = {\n    x: startPoint.x + arcOffsets.i,\n    y: startPoint.y + arcOffsets.j,\n  }\n\n  const [start, end, center] = getArcPositions(\n    startPoint,\n    endPoint,\n    centerPoint,\n    arcDirection\n  )\n\n  return {type: Tree.ARC, start, end, center, radius}\n}\n\nexport function getArcPositions(\n  startPoint: Point,\n  endPoint: Point,\n  centerPoint: Point,\n  arcDirection: ArcDirection\n): [start: Tree.ArcPosition, end: Tree.ArcPosition, center: Tree.Position] {\n  let startAngle = Math.atan2(\n    startPoint.y - centerPoint.y,\n    startPoint.x - centerPoint.x\n  )\n  let endAngle = Math.atan2(\n    endPoint.y - centerPoint.y,\n    endPoint.x - centerPoint.x\n  )\n\n  // If counter-clockwise, end angle should be greater than start angle\n  if (arcDirection === CCW) {\n    endAngle = endAngle > startAngle ? endAngle : endAngle + TWO_PI\n  } else {\n    startAngle = startAngle > endAngle ? startAngle : startAngle + TWO_PI\n  }\n\n  return [\n    [startPoint.x, startPoint.y, startAngle],\n    [endPoint.x, endPoint.y, endAngle],\n    [centerPoint.x, centerPoint.y],\n  ]\n}\n\n// Find arc center candidates by finding the intersection points\n// of two circles with `radius` centered on the start and end points\n// https://math.stackexchange.com/a/1367732\nfunction findCenterCandidates(location: Location, radius: number): Point[] {\n  // This function assumes that start and end are different points\n  const {x: x1, y: y1} = location.startPoint\n  const {x: x2, y: y2} = location.endPoint\n\n  // Distance between the start and end points\n  const [dx, dy] = [x2 - x1, y2 - y1]\n  const [sx, sy] = [x2 + x1, y2 + y1]\n  const distance = Math.sqrt(dx ** 2 + dy ** 2)\n\n  // If the distance to the midpoint equals the arc radius, then there is\n  // exactly one intersection at the midpoint; if the distance to the midpoint\n  // is greater than the radius, assume we've got a rounding error and just use\n  // the midpoint\n  if (radius <= distance / 2) {\n    return [{x: x1 + dx / 2, y: y1 + dy / 2}]\n  }\n\n  // No good name for these variables, but it's how the math works out\n  const factor = Math.sqrt((4 * radius ** 2) / distance ** 2 - 1)\n  const [xBase, yBase] = [sx / 2, sy / 2]\n  const [xAddend, yAddend] = [(dy * factor) / 2, (dx * factor) / 2]\n\n  return [\n    {x: xBase + xAddend, y: yBase - yAddend},\n    {x: xBase - xAddend, y: yBase + yAddend},\n  ]\n}\n","// Plot a tool macro as shapes\nimport type {MacroPrimitiveCode, MacroValue} from '@tracespace/parser'\nimport {\n  MACRO_VARIABLE,\n  MACRO_PRIMITIVE,\n  MACRO_CIRCLE,\n  MACRO_VECTOR_LINE_DEPRECATED,\n  MACRO_VECTOR_LINE,\n  MACRO_CENTER_LINE,\n  MACRO_LOWER_LEFT_LINE_DEPRECATED,\n  MACRO_OUTLINE,\n  MACRO_POLYGON,\n  MACRO_MOIRE_DEPRECATED,\n  MACRO_THERMAL,\n} from '@tracespace/parser'\n\nimport {PI, rotateAndShift, positionsEqual} from '../coordinate-math'\n\nimport * as Tree from '../tree'\nimport type {MacroTool} from '../tool-store'\nimport type {Location} from '../location-store'\n\nimport {shapeToSegments} from './shapes'\nimport {CW, CCW, getArcPositions} from './plot-path'\n\ntype VariableValues = Record<string, number>\n\nexport function plotMacro(\n  tool: MacroTool,\n  location: Location\n): Tree.LayeredShape {\n  const shapes: Tree.ErasableShape[] = []\n  const variableValues: VariableValues = Object.fromEntries(\n    tool.variableValues.map((value, i) => [`$${i + 1}`, value])\n  )\n\n  for (const block of tool.macro) {\n    if (block.type === MACRO_VARIABLE) {\n      variableValues[block.name] = solveExpression(block.value, variableValues)\n    }\n\n    if (block.type === MACRO_PRIMITIVE) {\n      const origin: Tree.Position = [location.endPoint.x, location.endPoint.y]\n      const parameters = block.parameters.map(p => {\n        return solveExpression(p, variableValues)\n      })\n\n      shapes.push(...plotPrimitive(block.code, origin, parameters))\n    }\n  }\n\n  return {type: Tree.LAYERED_SHAPE, shapes}\n}\n\nfunction solveExpression(\n  expression: MacroValue,\n  variables: VariableValues\n): number {\n  if (typeof expression === 'number') return expression\n  if (typeof expression === 'string') return variables[expression]\n\n  const left = solveExpression(expression.left, variables)\n  const right = solveExpression(expression.right, variables)\n\n  switch (expression.operator) {\n    case '+': {\n      return left + right\n    }\n\n    case '-': {\n      return left - right\n    }\n\n    case 'x': {\n      return left * right\n    }\n\n    case '/': {\n      return left / right\n    }\n  }\n}\n\nfunction plotPrimitive(\n  code: MacroPrimitiveCode,\n  origin: Tree.Position,\n  parameters: number[]\n): Tree.ErasableShape[] {\n  switch (code) {\n    case MACRO_CIRCLE: {\n      return [plotCircle(origin, parameters)]\n    }\n\n    case MACRO_VECTOR_LINE:\n    case MACRO_VECTOR_LINE_DEPRECATED: {\n      return [plotVectorLine(origin, parameters)]\n    }\n\n    case MACRO_CENTER_LINE: {\n      return [plotCenterLine(origin, parameters)]\n    }\n\n    case MACRO_LOWER_LEFT_LINE_DEPRECATED: {\n      return [plotLowerLeftLine(origin, parameters)]\n    }\n\n    case MACRO_OUTLINE: {\n      return [plotOutline(origin, parameters)]\n    }\n\n    case MACRO_POLYGON: {\n      return [plotPolygon(origin, parameters)]\n    }\n\n    case MACRO_MOIRE_DEPRECATED: {\n      return plotMoire(origin, parameters)\n    }\n\n    case MACRO_THERMAL: {\n      return [plotThermal(origin, parameters)]\n    }\n  }\n\n  return []\n}\n\nfunction plotCircle(\n  origin: Tree.Position,\n  parameters: number[]\n): Tree.ErasableShape {\n  const [exposure, diameter, cx0, cy0, degrees] = parameters\n  const r = diameter / 2\n  const [cx, cy] = rotateAndShift([cx0, cy0], origin, degrees)\n\n  return {type: Tree.CIRCLE, erase: exposure === 0, cx, cy, r}\n}\n\nfunction plotVectorLine(\n  origin: Tree.Position,\n  parameters: number[]\n): Tree.ErasableShape {\n  const [exposure, width, sx, sy, ex, ey, degrees] = parameters\n  const [dy, dx] = [ey - sy, ex - sx]\n  const halfWid = width / 2\n  const dist = Math.sqrt(dy ** 2 + dx ** 2)\n  const [xOff, yOff] = [(halfWid * dx) / dist, (halfWid * dy) / dist]\n\n  return {\n    type: Tree.POLYGON,\n    erase: exposure === 0,\n    points: (\n      [\n        [sx + xOff, sy - yOff],\n        [ex + xOff, ey - yOff],\n        [ex - xOff, ey + yOff],\n        [sx - xOff, sy + yOff],\n      ] as Tree.Position[]\n    ).map(p => rotateAndShift(p, origin, degrees)),\n  }\n}\n\nfunction plotCenterLine(\n  origin: Tree.Position,\n  parameters: number[]\n): Tree.ErasableShape {\n  const [exposure, width, height, cx, cy, degrees] = parameters\n  const [halfWidth, halfHeight] = [width / 2, height / 2]\n\n  return {\n    type: Tree.POLYGON,\n    erase: exposure === 0,\n    points: (\n      [\n        [cx - halfWidth, cy - halfHeight],\n        [cx + halfWidth, cy - halfHeight],\n        [cx + halfWidth, cy + halfHeight],\n        [cx - halfWidth, cy + halfHeight],\n      ] as Tree.Position[]\n    ).map(p => rotateAndShift(p, origin, degrees)),\n  }\n}\n\nfunction plotLowerLeftLine(\n  origin: Tree.Position,\n  parameters: number[]\n): Tree.ErasableShape {\n  const [exposure, width, height, x, y, degrees] = parameters\n\n  return {\n    type: Tree.POLYGON,\n    erase: exposure === 0,\n    points: (\n      [\n        [x, y],\n        [x + width, y],\n        [x + width, y + height],\n        [x, y + height],\n      ] as Tree.Position[]\n    ).map(p => rotateAndShift(p, origin, degrees)),\n  }\n}\n\nfunction plotOutline(\n  origin: Tree.Position,\n  parameters: number[]\n): Tree.ErasableShape {\n  const [exposure, , ...coords] = parameters.slice(0, -1)\n  const degrees = parameters[parameters.length - 1]\n\n  return {\n    type: Tree.POLYGON,\n    erase: exposure === 0,\n    points: coords\n      .flatMap<[number, number]>((coordinate, i) =>\n        i % 2 === 1 ? [[coords[i - 1], coordinate]] : []\n      )\n      .map(p => rotateAndShift(p, origin, degrees)),\n  }\n}\n\nfunction plotPolygon(\n  origin: Tree.Position,\n  parameters: number[]\n): Tree.ErasableShape {\n  const [exposure, vertices, cx, cy, diameter, degrees] = parameters\n  const r = diameter / 2\n  const step = (2 * PI) / vertices\n  const points: Tree.Position[] = []\n  let i\n\n  for (i = 0; i < vertices; i++) {\n    const theta = step * i\n    const pointX = cx + r * Math.cos(theta)\n    const pointY = cy + r * Math.sin(theta)\n    points.push(rotateAndShift([pointX, pointY], origin, degrees))\n  }\n\n  return {type: Tree.POLYGON, erase: exposure === 0, points}\n}\n\nfunction plotMoire(\n  origin: Tree.Position,\n  parameters: number[]\n): Tree.ErasableShape[] {\n  const rotate = (p: Tree.Position): Tree.Position =>\n    rotateAndShift(p, origin, parameters[8])\n\n  const [cx0, cy0, d, ringThx, ringGap, ringN, lineThx, lineLength] = parameters\n  const [cx, cy] = rotate([cx0, cy0])\n  const halfLineThx = lineThx / 2\n  const halfLineLength = lineLength / 2\n\n  const radii = []\n  let count = 0\n  let dRemain = d\n\n  while (dRemain >= 0 && count < ringN) {\n    const r = dRemain / 2\n    const rHole = r - ringThx\n\n    radii.push(r)\n    if (rHole > 0) radii.push(rHole)\n    count += 1\n    dRemain = 2 * (rHole - ringGap)\n  }\n\n  return [\n    {\n      type: Tree.OUTLINE,\n      segments: radii.flatMap(r => {\n        return shapeToSegments({type: Tree.CIRCLE, cx, cy, r})\n      }),\n    },\n    // Vertical stroke\n    {\n      type: Tree.POLYGON,\n      points: (\n        [\n          [cx0 - halfLineThx, cy0 - halfLineLength],\n          [cx0 + halfLineThx, cy0 - halfLineLength],\n          [cx0 + halfLineThx, cy0 + halfLineLength],\n          [cx0 - halfLineThx, cy0 + halfLineLength],\n        ] as Tree.Position[]\n      ).map(rotate),\n    },\n    // Horizontal stroke\n    {\n      type: Tree.POLYGON,\n      points: (\n        [\n          [cx0 - halfLineLength, cy0 - halfLineThx],\n          [cx0 + halfLineLength, cy0 - halfLineThx],\n          [cx0 + halfLineLength, cy0 + halfLineThx],\n          [cx0 - halfLineLength, cy0 + halfLineThx],\n        ] as Tree.Position[]\n      ).map(rotate),\n    },\n  ]\n}\n\nfunction plotThermal(\n  origin: Tree.Position,\n  parameters: number[]\n): Tree.ErasableShape {\n  const [cx0, cy0, od, id, gap, degrees] = parameters\n  const center = rotateAndShift([cx0, cy0], origin, degrees)\n  const [or, ir] = [od / 2, id / 2]\n  const halfGap = gap / 2\n  const oIntSquare = or ** 2 - halfGap ** 2\n  const iIntSquare = ir ** 2 - halfGap ** 2\n  const oInt = Math.sqrt(oIntSquare)\n  const iInt = iIntSquare >= 0 ? Math.sqrt(iIntSquare) : halfGap\n  const positions = [0, 90, 180, 270]\n  const segments: Tree.PathSegment[] = []\n\n  for (const rot of positions) {\n    const points = (\n      [\n        [iInt, halfGap],\n        [oInt, halfGap],\n        [halfGap, oInt],\n        [halfGap, iInt],\n      ] as Tree.Position[]\n    )\n      .map(p => rotateAndShift(p, [cx0, cy0], rot))\n      .map(p => rotateAndShift(p, origin, degrees))\n\n    const [os, oe, oc] = getArcPositions(\n      {x: points[1][0], y: points[1][1]},\n      {x: points[2][0], y: points[2][1]},\n      {x: center[0], y: center[1]},\n      CCW\n    )\n\n    segments.push(\n      {type: Tree.LINE, start: points[0], end: points[1]},\n      {type: Tree.ARC, start: os, end: oe, center: oc, radius: or},\n      {type: Tree.LINE, start: points[2], end: points[3]}\n    )\n\n    if (!positionsEqual(points[0], points[3])) {\n      const [is, ie, ic] = getArcPositions(\n        {x: points[3][0], y: points[3][1]},\n        {x: points[0][0], y: points[0][1]},\n        {x: center[0], y: center[1]},\n        CW\n      )\n      segments.push({\n        type: Tree.ARC,\n        start: is,\n        end: ie,\n        center: ic,\n        radius: ir,\n      })\n    }\n  }\n\n  return {type: Tree.OUTLINE, segments}\n}\n","// Graphic plotter\n// Takes nodes and turns them into graphics to be added to the image\nimport type {\n  GerberNode,\n  GraphicType,\n  Filetype,\n  InterpolateModeType,\n} from '@tracespace/parser'\nimport {\n  GRAPHIC,\n  SHAPE,\n  SEGMENT,\n  MOVE,\n  SLOT,\n  DONE,\n  LINE,\n  CCW_ARC,\n  CW_ARC,\n  DRILL,\n  SINGLE,\n  INTERPOLATE_MODE,\n  QUADRANT_MODE,\n  REGION_MODE,\n} from '@tracespace/parser'\n\nimport * as Tree from '../tree'\nimport type {Tool} from '../tool-store'\nimport {SIMPLE_TOOL, MACRO_TOOL} from '../tool-store'\nimport type {Location} from '../location-store'\n\nimport {plotShape} from './plot-shape'\nimport {plotMacro} from './plot-macro'\nimport type {ArcDirection} from './plot-path'\nimport {CCW, CW, plotSegment, plotPath} from './plot-path'\n\nexport interface GraphicPlotter {\n  plot(\n    node: GerberNode,\n    tool: Tool | undefined,\n    location: Location\n  ): Tree.ImageGraphic[]\n}\n\nexport function createGraphicPlotter(filetype: Filetype): GraphicPlotter {\n  const plotter = Object.create(GraphicPlotterPrototype)\n\n  return filetype === DRILL\n    ? Object.assign(plotter, DrillGraphicPlotterTrait)\n    : plotter\n}\n\ninterface GraphicPlotterImpl extends GraphicPlotter {\n  _currentPath: CurrentPath | undefined\n  _arcDirection: ArcDirection | undefined\n  _ambiguousArcCenter: boolean\n  _regionMode: boolean\n  _defaultGraphic: NonNullable<GraphicType> | undefined\n\n  _setGraphicState(node: GerberNode): NonNullable<GraphicType> | undefined\n\n  _plotCurrentPath(\n    node: GerberNode,\n    nextTool: Tool | undefined,\n    nextGraphicType: NonNullable<GraphicType> | undefined\n  ): Tree.ImageGraphic | undefined\n}\n\ninterface CurrentPath {\n  segments: Tree.PathSegment[]\n  tool: Tool | undefined\n  region: boolean\n}\n\nconst GraphicPlotterPrototype: GraphicPlotterImpl = {\n  _currentPath: undefined,\n  _arcDirection: undefined,\n  _ambiguousArcCenter: false,\n  _regionMode: false,\n  _defaultGraphic: undefined,\n\n  plot(\n    node: GerberNode,\n    tool: Tool | undefined,\n    location: Location\n  ): Tree.ImageGraphic[] {\n    const graphics: Tree.ImageGraphic[] = []\n    const nextGraphicType = this._setGraphicState(node)\n    const pathGraphic = this._plotCurrentPath(node, tool, nextGraphicType)\n\n    if (pathGraphic) {\n      graphics.push(pathGraphic)\n    }\n\n    if (nextGraphicType === SHAPE && tool?.type === SIMPLE_TOOL) {\n      graphics.push({type: Tree.IMAGE_SHAPE, shape: plotShape(tool, location)})\n    }\n\n    if (nextGraphicType === SHAPE && tool?.type === MACRO_TOOL) {\n      graphics.push({type: Tree.IMAGE_SHAPE, shape: plotMacro(tool, location)})\n    }\n\n    if (nextGraphicType === SEGMENT) {\n      this._currentPath = this._currentPath ?? {\n        segments: [],\n        region: this._regionMode,\n        tool,\n      }\n\n      this._currentPath.segments.push(\n        plotSegment(location, this._arcDirection, this._ambiguousArcCenter)\n      )\n    }\n\n    if (nextGraphicType === SLOT) {\n      const pathGraphic = plotPath([plotSegment(location)], tool)\n\n      if (pathGraphic) {\n        graphics.push(pathGraphic)\n      }\n    }\n\n    return graphics\n  },\n\n  _setGraphicState(node: GerberNode): NonNullable<GraphicType> | undefined {\n    if (node.type === INTERPOLATE_MODE) {\n      this._arcDirection = arcDirectionFromMode(node.mode)\n    }\n\n    if (node.type === QUADRANT_MODE) {\n      this._ambiguousArcCenter = node.quadrant === SINGLE\n    }\n\n    if (node.type === REGION_MODE) {\n      this._regionMode = node.region\n    }\n\n    if (node.type !== GRAPHIC) {\n      return undefined\n    }\n\n    if (node.graphic === SEGMENT) {\n      this._defaultGraphic = SEGMENT\n    } else if (node.graphic !== null) {\n      this._defaultGraphic = undefined\n    }\n\n    return node.graphic ?? this._defaultGraphic\n  },\n\n  _plotCurrentPath(\n    node: GerberNode,\n    nextTool: Tool | undefined,\n    nextGraphicType: NonNullable<GraphicType> | undefined\n  ): Tree.ImageGraphic | undefined {\n    if (this._currentPath === undefined) {\n      return undefined\n    }\n\n    if (\n      nextTool !== this._currentPath.tool ||\n      node.type === REGION_MODE ||\n      node.type === DONE ||\n      (nextGraphicType === MOVE && this._currentPath.region) ||\n      (nextGraphicType === SHAPE && this._currentPath !== undefined)\n    ) {\n      const pathGraphic = plotPath(\n        this._currentPath.segments,\n        this._currentPath.tool,\n        this._currentPath.region\n      )\n\n      this._currentPath = undefined\n      return pathGraphic\n    }\n  },\n}\n\nconst DrillGraphicPlotterTrait: Partial<GraphicPlotterImpl> = {\n  _defaultGraphic: SHAPE,\n  _ambiguousArcCenter: true,\n\n  _setGraphicState(node: GerberNode): NonNullable<GraphicType> | undefined {\n    if (node.type === INTERPOLATE_MODE) {\n      const {mode} = node\n      this._arcDirection = arcDirectionFromMode(mode)\n\n      if (mode === CW_ARC || mode === CCW_ARC || mode === LINE) {\n        this._defaultGraphic = SEGMENT\n      } else if (mode === MOVE) {\n        this._defaultGraphic = MOVE\n      } else {\n        this._defaultGraphic = SHAPE\n      }\n    }\n\n    if (node.type !== GRAPHIC) {\n      return undefined\n    }\n\n    return node.graphic ?? this._defaultGraphic\n  },\n}\n\nfunction arcDirectionFromMode(\n  mode: InterpolateModeType\n): ArcDirection | undefined {\n  if (mode === CCW_ARC) return CCW\n  if (mode === CW_ARC) return CW\n  return undefined\n}\n","// @tracespace/plotter\n// build abstract board images from @tracespace/parser ASTs\nimport type {GerberTree} from '@tracespace/parser'\n\nimport {fromGraphics as sizeFromGraphics} from './bounding-box'\nimport {getPlotOptions} from './options'\nimport {createToolStore} from './tool-store'\nimport {createLocationStore} from './location-store'\nimport {createGraphicPlotter} from './graphic-plotter'\nimport {IMAGE} from './tree'\nimport type {ImageTree} from './tree'\n\nexport * from './tree'\nexport * as BoundingBox from './bounding-box'\nexport {TWO_PI, positionsEqual} from './coordinate-math'\n\nexport function plot(tree: GerberTree): ImageTree {\n  const plotOptions = getPlotOptions(tree)\n  const toolStore = createToolStore()\n  const locationStore = createLocationStore()\n  const graphicPlotter = createGraphicPlotter(tree.filetype)\n  const children = []\n\n  for (const node of tree.children) {\n    const tool = toolStore.use(node)\n    const location = locationStore.use(node, plotOptions)\n    const graphics = graphicPlotter.plot(node, tool, location)\n\n    children.push(...graphics)\n  }\n\n  return {\n    type: IMAGE,\n    units: plotOptions.units,\n    size: sizeFromGraphics(children),\n    children,\n  }\n}\n"],"names":["IMAGE","IMAGE_SHAPE","IMAGE_PATH","IMAGE_REGION","LINE","ARC","CIRCLE","RECTANGLE","POLYGON","OUTLINE","LAYERED_SHAPE","PI","HALF_PI","THREE_HALF_PI","TWO_PI","limitAngle","theta","rotateQuadrant","degreesToRadians","degrees","rotateAndShift","point","shift","rotation","sin","cos","x","y","nextX","nextY","positionsEqual","a","b","isEmpty","box","empty","add","sum","boxes","fromGraphics","graphics","fromGraphic","graphic","Tree.IMAGE_SHAPE","fromShape","fromPath","Tree.IMAGE_PATH","shape","Tree.CIRCLE","cx","cy","r","fromPosition","Tree.RECTANGLE","xSize","ySize","Tree.POLYGON","p","Tree.OUTLINE","Tree.LAYERED_SHAPE","erase","segments","width","rTool","keyPoints","segment","Tree.ARC","start","end","center","radius","sweep","thetaStart","thetaEnd","axisPoints","position","FORMAT_COMMENT_RE","getPlotOptions","tree","treeNodes","units","coordinateFormat","zeroSuppression","index","node","UNITS","COORDINATE_FORMAT","GRAPHIC","coordinates","coordinate","LEADING","TRAILING","COMMENT","comment","formatMatch","IN","SIMPLE_TOOL","MACRO_TOOL","createToolStore","ToolStorePrototype","TOOL_MACRO","TOOL_DEFINITION","hole","tool","MACRO_SHAPE","TOOL_CHANGE","createLocationStore","LocationStorePrototype","options","arcOffsets","startPoint","endPoint","x0","parseCoordinate","y0","i","j","defaultValue","integerPlaces","decimalPlaces","sign","signlessCoordinate","digits","paddedCoordinate","leading","trailing","createShape","diameter","OBROUND","xHalf","yHalf","rectangle","vertices","offset","step","points","_","pointX","pointY","shapeToSegments","Tree.LINE","endIndex","plotShape","location","toolShape","toolHole","holeShape","plotRectPath","shapes","plotRectPathSegment","sx","sy","ex","ey","xOffset","yOffset","sxMin","sxMax","syMin","syMax","exMin","exMax","eyMin","eyMax","CW","CCW","plotSegment","arcDirection","ambiguousArcCenter","createLineSegment","createArcSegment","plotPath","region","Tree.IMAGE_REGION","findCenterCandidates","centerPoint","getArcPositions","startA","endA","startB","endB","absSweepA","absSweepB","startAngle","endAngle","x1","y1","x2","y2","dx","dy","distance","factor","xBase","yBase","xAddend","yAddend","plotMacro","variableValues","value","block","MACRO_VARIABLE","solveExpression","MACRO_PRIMITIVE","origin","parameters","plotPrimitive","expression","variables","left","right","code","MACRO_CIRCLE","plotCircle","MACRO_VECTOR_LINE","MACRO_VECTOR_LINE_DEPRECATED","plotVectorLine","MACRO_CENTER_LINE","plotCenterLine","MACRO_LOWER_LEFT_LINE_DEPRECATED","plotLowerLeftLine","MACRO_OUTLINE","plotOutline","MACRO_POLYGON","plotPolygon","MACRO_MOIRE_DEPRECATED","plotMoire","MACRO_THERMAL","plotThermal","exposure","cx0","cy0","halfWid","dist","xOff","yOff","height","halfWidth","halfHeight","coords","rotate","d","ringThx","ringGap","ringN","lineThx","lineLength","halfLineThx","halfLineLength","radii","count","dRemain","rHole","od","id","gap","or","ir","halfGap","oIntSquare","iIntSquare","oInt","iInt","positions","rot","os","oe","oc","is","ie","ic","createGraphicPlotter","filetype","plotter","GraphicPlotterPrototype","DRILL","DrillGraphicPlotterTrait","nextGraphicType","pathGraphic","SHAPE","SEGMENT","SLOT","INTERPOLATE_MODE","arcDirectionFromMode","QUADRANT_MODE","SINGLE","REGION_MODE","nextTool","DONE","MOVE","mode","CW_ARC","CCW_ARC","plot","plotOptions","toolStore","locationStore","graphicPlotter","children","sizeFromGraphics"],"mappings":"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"}