@tscircuit/hypergraph 0.0.18 → 0.0.20

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.d.ts CHANGED
@@ -110,6 +110,10 @@ interface JRegion extends Region {
110
110
  x: number;
111
111
  y: number;
112
112
  };
113
+ polygon?: {
114
+ x: number;
115
+ y: number;
116
+ }[];
113
117
  isPad: boolean;
114
118
  isThroughJumper?: boolean;
115
119
  isConnectionRegion?: boolean;
@@ -276,6 +280,7 @@ declare class HyperGraphSolver<RegionType extends Region = Region, RegionPortTyp
276
280
  rippingEnabled?: boolean;
277
281
  ripCost?: number;
278
282
  };
283
+ getSolverName(): string;
279
284
  graph: HyperGraph;
280
285
  connections: Connection[];
281
286
  candidateQueue: PriorityQueue<Candidate>;
@@ -379,6 +384,7 @@ declare const JUMPER_GRAPH_SOLVER_DEFAULTS: {
379
384
  greedyMultiplier: number;
380
385
  };
381
386
  declare class JumperGraphSolver extends HyperGraphSolver<JRegion, JPort> {
387
+ getSolverName(): string;
382
388
  UNIT_OF_COST: string;
383
389
  portUsagePenalty: number;
384
390
  portUsagePenaltySq: number;
@@ -456,6 +462,10 @@ type SharedBoundary = {
456
462
  type RegionData = {
457
463
  id: string;
458
464
  bounds: Bounds | null;
465
+ polygon: {
466
+ x: number;
467
+ y: number;
468
+ }[] | null;
459
469
  center: {
460
470
  x: number;
461
471
  y: number;
@@ -493,6 +503,10 @@ declare class RegionBuilder implements RegionRef {
493
503
  constructor(id: string);
494
504
  get id(): string;
495
505
  rect(b: Bounds): this;
506
+ polygon(points: {
507
+ x: number;
508
+ y: number;
509
+ }[]): this;
496
510
  center(x: number, y: number): this;
497
511
  size(w: number, h: number, anchor?: "center" | "min"): this;
498
512
  pad(isPad?: boolean): this;
package/dist/index.js CHANGED
@@ -1829,6 +1829,9 @@ var HyperGraphSolver = class extends BaseSolver {
1829
1829
  this.candidateQueue = new PriorityQueue();
1830
1830
  this.beginNewConnection();
1831
1831
  }
1832
+ getSolverName() {
1833
+ return "HyperGraphSolver";
1834
+ }
1832
1835
  graph;
1833
1836
  connections;
1834
1837
  candidateQueue;
@@ -2114,10 +2117,11 @@ var visualizeJumperGraph = (graph, options) => {
2114
2117
  points: [],
2115
2118
  rects: [],
2116
2119
  texts: [],
2120
+ polygons: [],
2117
2121
  coordinateSystem: "cartesian"
2118
2122
  };
2119
2123
  for (const region of graph.regions) {
2120
- const { bounds, isPad, isThroughJumper, isConnectionRegion } = region.d;
2124
+ const { bounds, isPad, isThroughJumper, isConnectionRegion, polygon } = region.d;
2121
2125
  const centerX = (bounds.minX + bounds.maxX) / 2;
2122
2126
  const centerY = (bounds.minY + bounds.maxY) / 2;
2123
2127
  const width = bounds.maxX - bounds.minX;
@@ -2132,12 +2136,22 @@ var visualizeJumperGraph = (graph, options) => {
2132
2136
  } else {
2133
2137
  fill = "rgba(200, 200, 255, 0.1)";
2134
2138
  }
2135
- graphics.rects.push({
2136
- center: { x: centerX, y: centerY },
2137
- width: width - 0.1,
2138
- height: height - 0.1,
2139
- fill
2140
- });
2139
+ if (polygon && polygon.length >= 3) {
2140
+ const points = polygon;
2141
+ graphics.polygons.push({
2142
+ points,
2143
+ fill,
2144
+ stroke: "rgba(128, 128, 128, 0.5)",
2145
+ strokeWidth: 0.03
2146
+ });
2147
+ } else {
2148
+ graphics.rects.push({
2149
+ center: { x: centerX, y: centerY },
2150
+ width: width - 0.1,
2151
+ height: height - 0.1,
2152
+ fill
2153
+ });
2154
+ }
2141
2155
  }
2142
2156
  if (!options?.hidePortPoints) {
2143
2157
  for (const port of graph.ports) {
@@ -2486,6 +2500,9 @@ var JUMPER_GRAPH_SOLVER_DEFAULTS = {
2486
2500
  greedyMultiplier: 0.5518001238069296
2487
2501
  };
2488
2502
  var JumperGraphSolver = class extends HyperGraphSolver {
2503
+ getSolverName() {
2504
+ return "JumperGraphSolver";
2505
+ }
2489
2506
  UNIT_OF_COST = "hops";
2490
2507
  portUsagePenalty = JUMPER_GRAPH_SOLVER_DEFAULTS.portUsagePenalty;
2491
2508
  portUsagePenaltySq = JUMPER_GRAPH_SOLVER_DEFAULTS.portUsagePenaltySq;
@@ -2584,6 +2601,7 @@ var RegionBuilder = class {
2584
2601
  this.data = {
2585
2602
  id,
2586
2603
  bounds: null,
2604
+ polygon: null,
2587
2605
  center: null,
2588
2606
  width: null,
2589
2607
  height: null,
@@ -2600,6 +2618,35 @@ var RegionBuilder = class {
2600
2618
  // Geometry methods
2601
2619
  rect(b) {
2602
2620
  this.data.bounds = { ...b };
2621
+ this.data.polygon = null;
2622
+ this.data.center = null;
2623
+ this.data.width = null;
2624
+ this.data.height = null;
2625
+ return this;
2626
+ }
2627
+ polygon(points) {
2628
+ if (points.length < 3) {
2629
+ throw new TopologyError(
2630
+ `Region "${this.data.id}" has invalid polygon: at least 3 points required`,
2631
+ {
2632
+ regionIds: [this.data.id],
2633
+ suggestion: "Provide at least three polygon vertices"
2634
+ }
2635
+ );
2636
+ }
2637
+ for (const point of points) {
2638
+ if (!Number.isFinite(point.x) || !Number.isFinite(point.y)) {
2639
+ throw new TopologyError(
2640
+ `Region "${this.data.id}" has invalid polygon point`,
2641
+ {
2642
+ regionIds: [this.data.id],
2643
+ suggestion: "Use finite numeric x/y values"
2644
+ }
2645
+ );
2646
+ }
2647
+ }
2648
+ this.data.polygon = points.map((p) => ({ x: p.x, y: p.y }));
2649
+ this.data.bounds = null;
2603
2650
  this.data.center = null;
2604
2651
  this.data.width = null;
2605
2652
  this.data.height = null;
@@ -2608,6 +2655,7 @@ var RegionBuilder = class {
2608
2655
  center(x, y) {
2609
2656
  this.data.center = { x, y };
2610
2657
  this.data.bounds = null;
2658
+ this.data.polygon = null;
2611
2659
  return this;
2612
2660
  }
2613
2661
  size(w, h, anchor = "center") {
@@ -2624,6 +2672,7 @@ var RegionBuilder = class {
2624
2672
  this.data.height = h;
2625
2673
  this.data.anchor = anchor;
2626
2674
  this.data.bounds = null;
2675
+ this.data.polygon = null;
2627
2676
  return this;
2628
2677
  }
2629
2678
  // Semantic methods
@@ -2659,6 +2708,20 @@ function computeBoundsFromRegionData(data) {
2659
2708
  if (data.bounds) {
2660
2709
  return data.bounds;
2661
2710
  }
2711
+ if (data.polygon && data.polygon.length > 0) {
2712
+ let minX = data.polygon[0].x;
2713
+ let maxX = data.polygon[0].x;
2714
+ let minY = data.polygon[0].y;
2715
+ let maxY = data.polygon[0].y;
2716
+ for (let i = 1; i < data.polygon.length; i++) {
2717
+ const point = data.polygon[i];
2718
+ minX = Math.min(minX, point.x);
2719
+ maxX = Math.max(maxX, point.x);
2720
+ minY = Math.min(minY, point.y);
2721
+ maxY = Math.max(maxY, point.y);
2722
+ }
2723
+ return { minX, maxX, minY, maxY };
2724
+ }
2662
2725
  if (data.center && data.width !== null && data.height !== null) {
2663
2726
  const halfW = data.width / 2;
2664
2727
  const halfH = data.height / 2;
@@ -3271,6 +3334,7 @@ ${errors.map((e) => ` - ${e}`).join("\n")}`
3271
3334
  bounds,
3272
3335
  center,
3273
3336
  isPad: data.isPad,
3337
+ ...data.polygon && { polygon: data.polygon },
3274
3338
  ...data.isThroughJumper && { isThroughJumper: true },
3275
3339
  ...data.isConnectionRegion && { isConnectionRegion: true },
3276
3340
  ...data.meta
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@tscircuit/hypergraph",
3
3
  "main": "dist/index.js",
4
- "version": "0.0.18",
4
+ "version": "0.0.20",
5
5
  "type": "module",
6
6
  "scripts": {
7
7
  "start": "cosmos",
@@ -19,7 +19,7 @@
19
19
  "@tscircuit/math-utils": "^0.0.29",
20
20
  "@types/bun": "latest",
21
21
  "bun-match-svg": "^0.0.15",
22
- "graphics-debug": "^0.0.76",
22
+ "graphics-debug": "^0.0.83",
23
23
  "react-cosmos": "^7.1.0",
24
24
  "react-cosmos-plugin-vite": "^7.1.0",
25
25
  "transformation-matrix": "^3.1.0",
@@ -29,6 +29,6 @@
29
29
  "typescript": "^5"
30
30
  },
31
31
  "dependencies": {
32
- "@tscircuit/solver-utils": "^0.0.13"
32
+ "@tscircuit/solver-utils": "^0.0.14"
33
33
  }
34
34
  }