circuit-json-to-connectivity-map 0.0.12 → 0.0.14

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
@@ -7,6 +7,7 @@ declare class ConnectivityMap {
7
7
  netMap: Record<string, string[]>;
8
8
  idToNetMap: Record<string, string>;
9
9
  constructor(netMap: Record<string, string[]>);
10
+ addConnections(connections: string[][]): void;
10
11
  getIdsConnectedToNet(netId: string): string[];
11
12
  getNetConnectedToId(id: string): string | undefined;
12
13
  areIdsConnected(id1: string, id2: string): boolean;
@@ -33,6 +34,7 @@ declare class PcbConnectivityMap {
33
34
  private _buildPortMap;
34
35
  private _buildTraceMap;
35
36
  private _buildTraceConnectivityMap;
37
+ addTrace(trace: PCBTrace): void;
36
38
  _arePcbTracesConnected(trace1: PCBTrace, trace2: PCBTrace): boolean;
37
39
  areTracesConnected(traceId1: string, traceId2: string): boolean;
38
40
  getAllTracesConnectedToTrace(traceId: string): PCBTrace[];
package/dist/index.js CHANGED
@@ -54,6 +54,41 @@ var ConnectivityMap = class {
54
54
  }
55
55
  }
56
56
  }
57
+ addConnections(connections) {
58
+ for (const connection of connections) {
59
+ const existingNets = /* @__PURE__ */ new Set();
60
+ for (const id of connection) {
61
+ const existingNetId = this.idToNetMap[id];
62
+ if (existingNetId) {
63
+ existingNets.add(existingNetId);
64
+ }
65
+ }
66
+ let targetNetId;
67
+ if (existingNets.size === 0) {
68
+ targetNetId = `connectivity_net${Object.keys(this.netMap).length}`;
69
+ this.netMap[targetNetId] = [];
70
+ } else if (existingNets.size === 1) {
71
+ targetNetId = existingNets.values().next().value ?? `connectivity_net${Object.keys(this.netMap).length}`;
72
+ } else {
73
+ targetNetId = existingNets.values().next().value ?? `connectivity_net${Object.keys(this.netMap).length}`;
74
+ for (const netId of existingNets) {
75
+ if (netId !== targetNetId) {
76
+ this.netMap[targetNetId].push(...this.netMap[netId]);
77
+ this.netMap[netId] = this.netMap[targetNetId];
78
+ for (const id of this.netMap[targetNetId]) {
79
+ this.idToNetMap[id] = targetNetId;
80
+ }
81
+ }
82
+ }
83
+ }
84
+ for (const id of connection) {
85
+ if (!this.netMap[targetNetId].includes(id)) {
86
+ this.netMap[targetNetId].push(id);
87
+ }
88
+ this.idToNetMap[id] = targetNetId;
89
+ }
90
+ }
91
+ }
57
92
  getIdsConnectedToNet(netId) {
58
93
  return this.netMap[netId] || [];
59
94
  }
@@ -66,7 +101,7 @@ var ConnectivityMap = class {
66
101
  return netId1 === netId2 || netId2 === id1 || netId2 === id1;
67
102
  }
68
103
  areAllIdsConnected(ids) {
69
- let netId = this.getNetConnectedToId(ids[0]);
104
+ const netId = this.getNetConnectedToId(ids[0]);
70
105
  for (const id of ids) {
71
106
  const nextNetId = this.getNetConnectedToId(id);
72
107
  if (nextNetId === void 0) {
@@ -133,74 +168,8 @@ var getFullConnectivityMapFromCircuitJson = (circuitJson) => {
133
168
  return new ConnectivityMap(netMap);
134
169
  };
135
170
 
136
- // src/math-utils/line-intersects-line.ts
137
- function lineIntersectsLine([a1, a2], [b1, b2], {
138
- lineThickness = 0
139
- } = {}) {
140
- if (lineThickness === 0) {
141
- return doSegmentsIntersect(a1, a2, b1, b2);
142
- }
143
- const minDist = segmentsDistance(a1, a2, b1, b2);
144
- return minDist <= lineThickness;
145
- }
146
- function doSegmentsIntersect(p1, q1, p2, q2) {
147
- const o1 = orientation(p1, q1, p2);
148
- const o2 = orientation(p1, q1, q2);
149
- const o3 = orientation(p2, q2, p1);
150
- const o4 = orientation(p2, q2, q1);
151
- if (o1 !== o2 && o3 !== o4) {
152
- return true;
153
- }
154
- if (o1 === 0 && onSegment(p1, p2, q1)) return true;
155
- if (o2 === 0 && onSegment(p1, q2, q1)) return true;
156
- if (o3 === 0 && onSegment(p2, p1, q2)) return true;
157
- if (o4 === 0 && onSegment(p2, q1, q2)) return true;
158
- return false;
159
- }
160
- function orientation(p, q, r) {
161
- const val = (q.y - p.y) * (r.x - q.x) - (q.x - p.x) * (r.y - q.y);
162
- if (val === 0) return 0;
163
- return val > 0 ? 1 : 2;
164
- }
165
- function onSegment(p, q, r) {
166
- return q.x <= Math.max(p.x, r.x) && q.x >= Math.min(p.x, r.x) && q.y <= Math.max(p.y, r.y) && q.y >= Math.min(p.y, r.y);
167
- }
168
- function segmentsDistance(a1, a2, b1, b2) {
169
- if (a1.x === a2.x && a1.y === a2.y) {
170
- return pointToSegmentDistance(a1, b1, b2);
171
- }
172
- if (b1.x === b2.x && b1.y === b2.y) {
173
- return pointToSegmentDistance(b1, a1, a2);
174
- }
175
- if (doSegmentsIntersect(a1, a2, b1, b2)) {
176
- return 0;
177
- }
178
- const distances = [
179
- pointToSegmentDistance(a1, b1, b2),
180
- pointToSegmentDistance(a2, b1, b2),
181
- pointToSegmentDistance(b1, a1, a2),
182
- pointToSegmentDistance(b2, a1, a2)
183
- ];
184
- return Math.min(...distances);
185
- }
186
- function pointToSegmentDistance(p, v, w) {
187
- const l2 = (w.x - v.x) ** 2 + (w.y - v.y) ** 2;
188
- if (l2 === 0) return distance(p, v);
189
- let t = ((p.x - v.x) * (w.x - v.x) + (p.y - v.y) * (w.y - v.y)) / l2;
190
- t = Math.max(0, Math.min(1, t));
191
- const projection = {
192
- x: v.x + t * (w.x - v.x),
193
- y: v.y + t * (w.y - v.y)
194
- };
195
- return distance(p, projection);
196
- }
197
- function distance(p1, p2) {
198
- const dx = p1.x - p2.x;
199
- const dy = p1.y - p2.y;
200
- return Math.sqrt(dx * dx + dy * dy);
201
- }
202
-
203
171
  // src/PcbConnectivityMap.ts
172
+ import { doesLineIntersectLine } from "@tscircuit/math-utils";
204
173
  var PcbConnectivityMap = class {
205
174
  circuitJson;
206
175
  traceIdToElm;
@@ -255,6 +224,21 @@ var PcbConnectivityMap = class {
255
224
  }
256
225
  return new ConnectivityMap(findConnectedNetworks(connections));
257
226
  }
227
+ addTrace(trace) {
228
+ this.traceIdToElm.set(trace.pcb_trace_id, trace);
229
+ const connections = [];
230
+ for (const rp of trace.route) {
231
+ if (rp.route_type === "wire") {
232
+ if (rp.start_pcb_port_id) {
233
+ connections.push([rp.start_pcb_port_id, trace.pcb_trace_id]);
234
+ }
235
+ if (rp.end_pcb_port_id) {
236
+ connections.push([rp.end_pcb_port_id, trace.pcb_trace_id]);
237
+ }
238
+ }
239
+ }
240
+ this.connMap.addConnections(connections);
241
+ }
258
242
  _arePcbTracesConnected(trace1, trace2) {
259
243
  for (let i = 0; i < trace1.route.length - 1; i++) {
260
244
  const segment1A = trace1.route[i];
@@ -266,7 +250,7 @@ var PcbConnectivityMap = class {
266
250
  const segment2B = trace2.route[j + 1];
267
251
  if (segment2A.route_type !== "wire") continue;
268
252
  if (segment2B.route_type !== "wire") continue;
269
- const isOverlapping = lineIntersectsLine(
253
+ const isOverlapping = doesLineIntersectLine(
270
254
  [segment1A, segment1B],
271
255
  [segment2A, segment2B],
272
256
  {
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/findConnectedNetworks.ts","../src/ConnectivityMap.ts","../src/getSourcePortConnectivityMapFromCircuitJson.ts","../src/getFullConnectivityMapFromCircuitJson.ts","../src/math-utils/line-intersects-line.ts","../src/PcbConnectivityMap.ts"],"sourcesContent":["type NodeId = string\n\nexport function findConnectedNetworks(\n connections: Array<NodeId[]>,\n): Record<string, string[]> {\n const networks: Map<string, Set<string>> = new Map()\n let netCounter = 0\n\n function getOrCreateNetwork(nodeId: string): Set<string> {\n for (const [, network] of networks) {\n if (network.has(nodeId)) {\n return network\n }\n }\n const newNetwork = new Set<string>()\n networks.set(`connectivity_net${netCounter++}`, newNetwork)\n return newNetwork\n }\n\n for (const connection of connections) {\n let network: Set<string> | null = null\n\n for (const nodeId of connection) {\n if (!network) {\n network = getOrCreateNetwork(nodeId)\n } else if (!network.has(nodeId)) {\n const existingNetwork = getOrCreateNetwork(nodeId)\n if (existingNetwork !== network) {\n // Merge networks\n for (const node of existingNetwork) {\n network.add(node)\n }\n networks.delete(\n Array.from(networks.entries()).find(\n ([, net]) => net === existingNetwork,\n )![0],\n )\n }\n }\n network.add(nodeId)\n }\n }\n\n return Object.fromEntries(\n Array.from(networks.entries()).map(([netId, connectedNodes]) => [\n netId,\n Array.from(connectedNodes),\n ]),\n )\n}\n","export class ConnectivityMap {\n netMap: Record<string, string[]>\n\n idToNetMap: Record<string, string>\n\n constructor(netMap: Record<string, string[]>) {\n this.netMap = netMap\n this.idToNetMap = {}\n for (const [netId, ids] of Object.entries(netMap)) {\n for (const id of ids) {\n this.idToNetMap[id] = netId\n }\n }\n }\n\n getIdsConnectedToNet(netId: string): string[] {\n return this.netMap[netId] || []\n }\n\n getNetConnectedToId(id: string): string | undefined {\n return this.idToNetMap[id]\n }\n\n areIdsConnected(id1: string, id2: string): boolean {\n const netId1 = this.getNetConnectedToId(id1)\n const netId2 = this.getNetConnectedToId(id2)\n return netId1 === netId2 || netId2 === id1 || netId2 === id1\n }\n\n areAllIdsConnected(ids: string[]): boolean {\n let netId = this.getNetConnectedToId(ids[0])\n for (const id of ids) {\n const nextNetId = this.getNetConnectedToId(id)\n if (nextNetId === undefined) {\n return false\n }\n if (nextNetId !== netId) {\n return false\n }\n }\n return true\n }\n}\n","import type { AnySoupElement } from \"@tscircuit/soup\"\nimport { findConnectedNetworks } from \"./findConnectedNetworks\"\nimport { ConnectivityMap } from \"./ConnectivityMap\"\n\nexport const getSourcePortConnectivityMapFromCircuitJson = (\n circuitJson: AnySoupElement[],\n) => {\n const connections: string[][] = []\n\n for (const element of circuitJson) {\n if (element.type === \"source_trace\") {\n connections.push([\n ...(element.connected_source_port_ids ?? []),\n ...(element.connected_source_net_ids ?? []),\n ])\n }\n }\n\n const netMap = findConnectedNetworks(connections)\n\n return new ConnectivityMap(netMap)\n}\n","import type { AnySoupElement } from \"@tscircuit/soup\"\nimport { findConnectedNetworks } from \"./findConnectedNetworks\"\nimport { ConnectivityMap } from \"./ConnectivityMap\"\n\nexport const getFullConnectivityMapFromCircuitJson = (\n circuitJson: AnySoupElement[],\n) => {\n const connections: string[][] = []\n\n for (const element of circuitJson) {\n if (element.type === \"source_trace\") {\n connections.push(\n [\n element.source_trace_id,\n ...(element.connected_source_port_ids ?? []),\n ...(element.connected_source_net_ids ?? []),\n ].filter(Boolean),\n )\n } else if (element.type === \"pcb_port\") {\n const { pcb_port_id, source_port_id } = element\n if (source_port_id && pcb_port_id) {\n connections.push([source_port_id, pcb_port_id])\n }\n } else if (element.type === \"pcb_smtpad\") {\n const { pcb_smtpad_id, pcb_port_id } = element\n if (pcb_port_id && pcb_smtpad_id) {\n connections.push([pcb_smtpad_id, pcb_port_id])\n }\n } else if (element.type === \"pcb_plated_hole\") {\n const { pcb_plated_hole_id, pcb_port_id } = element\n if (pcb_port_id && pcb_plated_hole_id) {\n connections.push([pcb_plated_hole_id, pcb_port_id])\n }\n } else if (element.type === \"pcb_trace\") {\n const { pcb_trace_id, source_trace_id } = element\n if (source_trace_id && pcb_trace_id) {\n connections.push([pcb_trace_id, source_trace_id])\n }\n }\n }\n\n const netMap = findConnectedNetworks(connections)\n\n return new ConnectivityMap(netMap)\n}\n","type Point = {\n x: number\n y: number\n}\n\nexport function lineIntersectsLine(\n [a1, a2]: [Point, Point],\n [b1, b2]: [Point, Point],\n {\n lineThickness = 0,\n }: {\n lineThickness?: number\n } = {},\n): boolean {\n if (lineThickness === 0) {\n return doSegmentsIntersect(a1, a2, b1, b2)\n }\n const minDist = segmentsDistance(a1, a2, b1, b2)\n return minDist <= lineThickness\n}\n\nfunction doSegmentsIntersect(\n p1: Point,\n q1: Point,\n p2: Point,\n q2: Point,\n): boolean {\n const o1 = orientation(p1, q1, p2)\n const o2 = orientation(p1, q1, q2)\n const o3 = orientation(p2, q2, p1)\n const o4 = orientation(p2, q2, q1)\n\n // General case\n if (o1 !== o2 && o3 !== o4) {\n return true\n }\n\n // Special Cases\n if (o1 === 0 && onSegment(p1, p2, q1)) return true\n if (o2 === 0 && onSegment(p1, q2, q1)) return true\n if (o3 === 0 && onSegment(p2, p1, q2)) return true\n if (o4 === 0 && onSegment(p2, q1, q2)) return true\n\n return false\n}\n\nfunction orientation(p: Point, q: Point, r: Point): number {\n const val = (q.y - p.y) * (r.x - q.x) - (q.x - p.x) * (r.y - q.y)\n if (val === 0) return 0 // colinear\n return val > 0 ? 1 : 2 // clock or counterclock wise\n}\n\nfunction onSegment(p: Point, q: Point, r: Point): boolean {\n return (\n q.x <= Math.max(p.x, r.x) &&\n q.x >= Math.min(p.x, r.x) &&\n q.y <= Math.max(p.y, r.y) &&\n q.y >= Math.min(p.y, r.y)\n )\n}\n\nfunction segmentsDistance(a1: Point, a2: Point, b1: Point, b2: Point): number {\n // Handle degenerate cases: segments of zero length\n if (a1.x === a2.x && a1.y === a2.y) {\n return pointToSegmentDistance(a1, b1, b2)\n }\n if (b1.x === b2.x && b1.y === b2.y) {\n return pointToSegmentDistance(b1, a1, a2)\n }\n\n // Check if segments intersect\n if (doSegmentsIntersect(a1, a2, b1, b2)) {\n return 0\n }\n\n // Compute the minimum distance between the segments\n const distances = [\n pointToSegmentDistance(a1, b1, b2),\n pointToSegmentDistance(a2, b1, b2),\n pointToSegmentDistance(b1, a1, a2),\n pointToSegmentDistance(b2, a1, a2),\n ]\n\n return Math.min(...distances)\n}\n\nfunction pointToSegmentDistance(p: Point, v: Point, w: Point): number {\n const l2 = (w.x - v.x) ** 2 + (w.y - v.y) ** 2\n if (l2 === 0) return distance(p, v)\n\n let t = ((p.x - v.x) * (w.x - v.x) + (p.y - v.y) * (w.y - v.y)) / l2\n t = Math.max(0, Math.min(1, t))\n\n const projection = {\n x: v.x + t * (w.x - v.x),\n y: v.y + t * (w.y - v.y),\n }\n\n return distance(p, projection)\n}\n\nfunction distance(p1: Point, p2: Point): number {\n const dx = p1.x - p2.x\n const dy = p1.y - p2.y\n return Math.sqrt(dx * dx + dy * dy)\n}\n","import type { AnyCircuitElement, PCBPort, PCBTrace } from \"@tscircuit/soup\"\nimport { ConnectivityMap } from \"./ConnectivityMap\"\nimport { lineIntersectsLine } from \"./math-utils/line-intersects-line\"\nimport { findConnectedNetworks } from \"./findConnectedNetworks\"\n\n/**\n * A PCB Connectivity Map is a connectivity map that has analyzed what traces and ports are actually connected on the\n * PCB.\n *\n * This is useful for determining how to route a trace on the PCB. For example, you may want to determine where the\n * nearest connected net point is to connect an unrouted pin.\n */\nexport class PcbConnectivityMap {\n circuitJson: AnyCircuitElement[]\n traceIdToElm: Map<string, PCBTrace>\n portIdToElm: Map<string, PCBPort>\n connMap: ConnectivityMap\n\n constructor(circuitJson: AnyCircuitElement[]) {\n this.circuitJson = circuitJson\n this.traceIdToElm = new Map()\n this.portIdToElm = new Map()\n this._buildTraceMap()\n this._buildPortMap()\n this.connMap = this._buildTraceConnectivityMap()\n }\n\n private _buildPortMap() {\n for (const element of this.circuitJson) {\n if (element.type === \"pcb_port\") {\n this.portIdToElm.set(element.pcb_port_id, element as PCBPort)\n }\n }\n }\n\n private _buildTraceMap() {\n for (const element of this.circuitJson) {\n if (element.type === \"pcb_trace\") {\n this.traceIdToElm.set(element.pcb_trace_id, element as PCBTrace)\n }\n }\n }\n\n private _buildTraceConnectivityMap(): ConnectivityMap {\n const connections: string[][] = []\n const traceIds = Array.from(this.traceIdToElm.keys())\n\n for (let i = 0; i < traceIds.length; i++) {\n for (let j = i + 1; j < traceIds.length; j++) {\n const trace1 = this.traceIdToElm.get(traceIds[i])!\n const trace2 = this.traceIdToElm.get(traceIds[j])!\n if (this._arePcbTracesConnected(trace1, trace2)) {\n connections.push([traceIds[i], traceIds[j]])\n }\n }\n }\n\n for (const port of this.portIdToElm.values()) {\n for (const trace of this.traceIdToElm.values()) {\n for (const rp of trace.route) {\n if (rp.route_type === \"wire\") {\n if (rp.start_pcb_port_id === port.pcb_port_id) {\n connections.push([port.pcb_port_id, trace.pcb_trace_id])\n } else if (rp.end_pcb_port_id === port.pcb_port_id) {\n connections.push([trace.pcb_trace_id, port.pcb_port_id])\n }\n }\n }\n }\n }\n\n return new ConnectivityMap(findConnectedNetworks(connections))\n }\n\n _arePcbTracesConnected(trace1: PCBTrace, trace2: PCBTrace): boolean {\n for (let i = 0; i < trace1.route.length - 1; i++) {\n const segment1A = trace1.route[i]\n const segment1B = trace1.route[i + 1]\n if (segment1A.route_type !== \"wire\") continue\n if (segment1B.route_type !== \"wire\") continue\n for (let j = 0; j < trace2.route.length - 1; j++) {\n const segment2A = trace2.route[j]\n const segment2B = trace2.route[j + 1]\n\n if (segment2A.route_type !== \"wire\") continue\n if (segment2B.route_type !== \"wire\") continue\n\n // Check if lines are overlapping\n const isOverlapping = lineIntersectsLine(\n [segment1A, segment1B],\n [segment2A, segment2B],\n {\n lineThickness: (segment1A.width + segment2A.width) / 2,\n },\n )\n if (isOverlapping) {\n return true\n }\n }\n }\n return false\n }\n\n areTracesConnected(traceId1: string, traceId2: string): boolean {\n return this.connMap.areIdsConnected(traceId1, traceId2)\n }\n\n getAllTracesConnectedToTrace(traceId: string): PCBTrace[] {\n const netId = this.connMap.getNetConnectedToId(traceId)\n return netId\n ? this.connMap\n .getIdsConnectedToNet(netId)\n .filter((id) => this.traceIdToElm.has(id))\n .map((id) => this.traceIdToElm.get(id) as PCBTrace)\n : []\n }\n\n getAllTracesConnectedToPort(portId: string): PCBTrace[] {\n const netId = this.connMap.getNetConnectedToId(portId)\n return netId\n ? this.connMap\n .getIdsConnectedToNet(netId)\n .filter((id) => this.traceIdToElm.has(id))\n .map((id) => this.traceIdToElm.get(id) as PCBTrace)\n : []\n }\n}\n"],"mappings":"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","names":[]}
1
+ {"version":3,"sources":["../src/findConnectedNetworks.ts","../src/ConnectivityMap.ts","../src/getSourcePortConnectivityMapFromCircuitJson.ts","../src/getFullConnectivityMapFromCircuitJson.ts","../src/PcbConnectivityMap.ts"],"sourcesContent":["type NodeId = string\n\nexport function findConnectedNetworks(\n connections: Array<NodeId[]>,\n): Record<string, string[]> {\n const networks: Map<string, Set<string>> = new Map()\n let netCounter = 0\n\n function getOrCreateNetwork(nodeId: string): Set<string> {\n for (const [, network] of networks) {\n if (network.has(nodeId)) {\n return network\n }\n }\n const newNetwork = new Set<string>()\n networks.set(`connectivity_net${netCounter++}`, newNetwork)\n return newNetwork\n }\n\n for (const connection of connections) {\n let network: Set<string> | null = null\n\n for (const nodeId of connection) {\n if (!network) {\n network = getOrCreateNetwork(nodeId)\n } else if (!network.has(nodeId)) {\n const existingNetwork = getOrCreateNetwork(nodeId)\n if (existingNetwork !== network) {\n // Merge networks\n for (const node of existingNetwork) {\n network.add(node)\n }\n networks.delete(\n Array.from(networks.entries()).find(\n ([, net]) => net === existingNetwork,\n )![0],\n )\n }\n }\n network.add(nodeId)\n }\n }\n\n return Object.fromEntries(\n Array.from(networks.entries()).map(([netId, connectedNodes]) => [\n netId,\n Array.from(connectedNodes),\n ]),\n )\n}\n","export class ConnectivityMap {\n netMap: Record<string, string[]>\n\n idToNetMap: Record<string, string>\n\n constructor(netMap: Record<string, string[]>) {\n this.netMap = netMap\n this.idToNetMap = {}\n for (const [netId, ids] of Object.entries(netMap)) {\n for (const id of ids) {\n this.idToNetMap[id] = netId\n }\n }\n }\n\n addConnections(connections: string[][]) {\n for (const connection of connections) {\n const existingNets = new Set<string>()\n\n // Find all existing nets for the connection\n for (const id of connection) {\n const existingNetId = this.idToNetMap[id]\n if (existingNetId) {\n existingNets.add(existingNetId)\n }\n }\n\n let targetNetId: string\n\n if (existingNets.size === 0) {\n // If no existing nets found, create a new one\n targetNetId = `connectivity_net${Object.keys(this.netMap).length}`\n this.netMap[targetNetId] = []\n } else if (existingNets.size === 1) {\n // If only one existing net found, use it\n targetNetId =\n existingNets.values().next().value ??\n `connectivity_net${Object.keys(this.netMap).length}`\n } else {\n // If multiple nets found, merge them\n targetNetId =\n existingNets.values().next().value ??\n `connectivity_net${Object.keys(this.netMap).length}`\n for (const netId of existingNets) {\n if (netId !== targetNetId) {\n this.netMap[targetNetId].push(...this.netMap[netId])\n\n // we could delete the net, but setting it to reference the other net\n // will make sure any usage of the old netId will still work\n this.netMap[netId] = this.netMap[targetNetId]\n for (const id of this.netMap[targetNetId]) {\n this.idToNetMap[id] = targetNetId\n }\n }\n }\n }\n\n // Add all ids to the target net\n for (const id of connection) {\n if (!this.netMap[targetNetId].includes(id)) {\n this.netMap[targetNetId].push(id)\n }\n this.idToNetMap[id] = targetNetId\n }\n }\n }\n\n getIdsConnectedToNet(netId: string): string[] {\n return this.netMap[netId] || []\n }\n\n getNetConnectedToId(id: string): string | undefined {\n return this.idToNetMap[id]\n }\n\n areIdsConnected(id1: string, id2: string): boolean {\n const netId1 = this.getNetConnectedToId(id1)\n const netId2 = this.getNetConnectedToId(id2)\n return netId1 === netId2 || netId2 === id1 || netId2 === id1\n }\n\n areAllIdsConnected(ids: string[]): boolean {\n const netId = this.getNetConnectedToId(ids[0])\n for (const id of ids) {\n const nextNetId = this.getNetConnectedToId(id)\n if (nextNetId === undefined) {\n return false\n }\n if (nextNetId !== netId) {\n return false\n }\n }\n return true\n }\n}\n","import type { AnySoupElement } from \"@tscircuit/soup\"\nimport { findConnectedNetworks } from \"./findConnectedNetworks\"\nimport { ConnectivityMap } from \"./ConnectivityMap\"\n\nexport const getSourcePortConnectivityMapFromCircuitJson = (\n circuitJson: AnySoupElement[],\n) => {\n const connections: string[][] = []\n\n for (const element of circuitJson) {\n if (element.type === \"source_trace\") {\n connections.push([\n ...(element.connected_source_port_ids ?? []),\n ...(element.connected_source_net_ids ?? []),\n ])\n }\n }\n\n const netMap = findConnectedNetworks(connections)\n\n return new ConnectivityMap(netMap)\n}\n","import type { AnySoupElement } from \"@tscircuit/soup\"\nimport { findConnectedNetworks } from \"./findConnectedNetworks\"\nimport { ConnectivityMap } from \"./ConnectivityMap\"\n\nexport const getFullConnectivityMapFromCircuitJson = (\n circuitJson: AnySoupElement[],\n) => {\n const connections: string[][] = []\n\n for (const element of circuitJson) {\n if (element.type === \"source_trace\") {\n connections.push(\n [\n element.source_trace_id,\n ...(element.connected_source_port_ids ?? []),\n ...(element.connected_source_net_ids ?? []),\n ].filter(Boolean),\n )\n } else if (element.type === \"pcb_port\") {\n const { pcb_port_id, source_port_id } = element\n if (source_port_id && pcb_port_id) {\n connections.push([source_port_id, pcb_port_id])\n }\n } else if (element.type === \"pcb_smtpad\") {\n const { pcb_smtpad_id, pcb_port_id } = element\n if (pcb_port_id && pcb_smtpad_id) {\n connections.push([pcb_smtpad_id, pcb_port_id])\n }\n } else if (element.type === \"pcb_plated_hole\") {\n const { pcb_plated_hole_id, pcb_port_id } = element\n if (pcb_port_id && pcb_plated_hole_id) {\n connections.push([pcb_plated_hole_id, pcb_port_id])\n }\n } else if (element.type === \"pcb_trace\") {\n const { pcb_trace_id, source_trace_id } = element\n if (source_trace_id && pcb_trace_id) {\n connections.push([pcb_trace_id, source_trace_id])\n }\n }\n }\n\n const netMap = findConnectedNetworks(connections)\n\n return new ConnectivityMap(netMap)\n}\n","import type { AnyCircuitElement, PCBPort, PCBTrace } from \"@tscircuit/soup\"\nimport { ConnectivityMap } from \"./ConnectivityMap\"\nimport { doesLineIntersectLine } from \"@tscircuit/math-utils\"\nimport { findConnectedNetworks } from \"./findConnectedNetworks\"\n\n/**\n * A PCB Connectivity Map is a connectivity map that has analyzed what traces and ports are actually connected on the\n * PCB.\n *\n * This is useful for determining how to route a trace on the PCB. For example, you may want to determine where the\n * nearest connected net point is to connect an unrouted pin.\n */\nexport class PcbConnectivityMap {\n circuitJson: AnyCircuitElement[]\n traceIdToElm: Map<string, PCBTrace>\n portIdToElm: Map<string, PCBPort>\n connMap: ConnectivityMap\n\n constructor(circuitJson: AnyCircuitElement[]) {\n this.circuitJson = circuitJson\n this.traceIdToElm = new Map()\n this.portIdToElm = new Map()\n this._buildTraceMap()\n this._buildPortMap()\n this.connMap = this._buildTraceConnectivityMap()\n }\n\n private _buildPortMap() {\n for (const element of this.circuitJson) {\n if (element.type === \"pcb_port\") {\n this.portIdToElm.set(element.pcb_port_id, element as PCBPort)\n }\n }\n }\n\n private _buildTraceMap() {\n for (const element of this.circuitJson) {\n if (element.type === \"pcb_trace\") {\n this.traceIdToElm.set(element.pcb_trace_id, element as PCBTrace)\n }\n }\n }\n\n private _buildTraceConnectivityMap(): ConnectivityMap {\n const connections: string[][] = []\n const traceIds = Array.from(this.traceIdToElm.keys())\n\n for (let i = 0; i < traceIds.length; i++) {\n for (let j = i + 1; j < traceIds.length; j++) {\n const trace1 = this.traceIdToElm.get(traceIds[i])!\n const trace2 = this.traceIdToElm.get(traceIds[j])!\n if (this._arePcbTracesConnected(trace1, trace2)) {\n connections.push([traceIds[i], traceIds[j]])\n }\n }\n }\n\n for (const port of this.portIdToElm.values()) {\n for (const trace of this.traceIdToElm.values()) {\n for (const rp of trace.route) {\n if (rp.route_type === \"wire\") {\n if (rp.start_pcb_port_id === port.pcb_port_id) {\n connections.push([port.pcb_port_id, trace.pcb_trace_id])\n } else if (rp.end_pcb_port_id === port.pcb_port_id) {\n connections.push([trace.pcb_trace_id, port.pcb_port_id])\n }\n }\n }\n }\n }\n\n return new ConnectivityMap(findConnectedNetworks(connections))\n }\n\n addTrace(trace: PCBTrace) {\n this.traceIdToElm.set(trace.pcb_trace_id, trace)\n const connections: string[][] = []\n for (const rp of trace.route) {\n if (rp.route_type === \"wire\") {\n if (rp.start_pcb_port_id) {\n connections.push([rp.start_pcb_port_id, trace.pcb_trace_id])\n }\n if (rp.end_pcb_port_id) {\n connections.push([rp.end_pcb_port_id, trace.pcb_trace_id])\n }\n }\n }\n\n this.connMap.addConnections(connections)\n }\n\n _arePcbTracesConnected(trace1: PCBTrace, trace2: PCBTrace): boolean {\n for (let i = 0; i < trace1.route.length - 1; i++) {\n const segment1A = trace1.route[i]\n const segment1B = trace1.route[i + 1]\n if (segment1A.route_type !== \"wire\") continue\n if (segment1B.route_type !== \"wire\") continue\n for (let j = 0; j < trace2.route.length - 1; j++) {\n const segment2A = trace2.route[j]\n const segment2B = trace2.route[j + 1]\n\n if (segment2A.route_type !== \"wire\") continue\n if (segment2B.route_type !== \"wire\") continue\n\n // Check if lines are overlapping\n const isOverlapping = doesLineIntersectLine(\n [segment1A, segment1B],\n [segment2A, segment2B],\n {\n lineThickness: (segment1A.width + segment2A.width) / 2,\n },\n )\n if (isOverlapping) {\n return true\n }\n }\n }\n return false\n }\n\n areTracesConnected(traceId1: string, traceId2: string): boolean {\n return this.connMap.areIdsConnected(traceId1, traceId2)\n }\n\n getAllTracesConnectedToTrace(traceId: string): PCBTrace[] {\n const netId = this.connMap.getNetConnectedToId(traceId)\n return netId\n ? this.connMap\n .getIdsConnectedToNet(netId)\n .filter((id) => this.traceIdToElm.has(id))\n .map((id) => this.traceIdToElm.get(id) as PCBTrace)\n : []\n }\n\n getAllTracesConnectedToPort(portId: string): PCBTrace[] {\n const netId = this.connMap.getNetConnectedToId(portId)\n return netId\n ? this.connMap\n .getIdsConnectedToNet(netId)\n .filter((id) => this.traceIdToElm.has(id))\n .map((id) => this.traceIdToElm.get(id) as PCBTrace)\n : []\n }\n}\n"],"mappings":"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","names":[]}
package/package.json CHANGED
@@ -2,7 +2,7 @@
2
2
  "name": "circuit-json-to-connectivity-map",
3
3
  "main": "dist/index.js",
4
4
  "type": "module",
5
- "version": "0.0.12",
5
+ "version": "0.0.14",
6
6
  "files": [
7
7
  "dist"
8
8
  ],
@@ -19,5 +19,8 @@
19
19
  },
20
20
  "peerDependencies": {
21
21
  "typescript": "^5.0.0"
22
+ },
23
+ "dependencies": {
24
+ "@tscircuit/math-utils": "^0.0.2"
22
25
  }
23
26
  }