-
Notifications
You must be signed in to change notification settings - Fork 50
Implement PDIP-8 footprint #507
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
Changes from 24 commits
3f82090
2703095
7e92d2a
272d0de
e22d2dd
bae0360
867ffd8
0665c4c
32bb13b
3e37450
ab7032f
2720891
34ad3e7
035db3c
85c87c9
80261e3
6b92de9
bb26140
697ecd9
03e9a7c
e390832
bd2d1aa
fac6c06
09a0860
523b24a
751f62a
f3758c6
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,12 @@ | ||
| import { dip, dip_def, extendDipDef } from "./dip" | ||
|
|
||
| export const pdip_def = extendDipDef({ w: "300mil", p: "2.54mm" }) | ||
|
|
||
| export const pdip = (raw_params: any) => { | ||
| const parameters = pdip_def.parse(raw_params) | ||
| return dip({ | ||
| ...parameters, | ||
| num_pins: raw_params.num_pins ?? 8, | ||
| dip: true, | ||
| } as any) | ||
| } |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,11 @@ | ||
| import { dip, dip_def, extendDipDef } from "./dip" | ||
|
|
||
| export const pdip8_def = extendDipDef({ w: "300mil", p: "2.54mm" }) | ||
|
|
||
| export const pdip8 = (raw_params: any) => { | ||
| const parameters = pdip8_def.parse({ ...raw_params, num_pins: 8 }) | ||
| return dip({ | ||
| ...parameters, | ||
| dip: true, | ||
| } as any) | ||
| } |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,11 @@ | ||
| import { dip, extendDipDef } from "./dip" | ||
|
|
||
| export const spdip_def = extendDipDef({ w: "300mil", p: "2.54mm" }) | ||
|
|
||
| export const spdip = (raw_params: any) => { | ||
| const parameters = spdip_def.parse(raw_params) | ||
| return dip({ | ||
| ...parameters, | ||
| dip: true, | ||
| } as any) | ||
| } |
| Original file line number | Diff line number | Diff line change | ||||||||||||||||||||||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| @@ -0,0 +1,57 @@ | ||||||||||||||||||||||||||||||||||
| import { z } from "zod" | ||||||||||||||||||||||||||||||||||
| import { length } from "circuit-json" | ||||||||||||||||||||||||||||||||||
| import type { AnyCircuitElement, PcbSilkscreenPath } from "circuit-json" | ||||||||||||||||||||||||||||||||||
| import { rectpad } from "../helpers/rectpad" | ||||||||||||||||||||||||||||||||||
| import { silkscreenRef, type SilkscreenRef } from "../helpers/silkscreenRef" | ||||||||||||||||||||||||||||||||||
| import { base_def } from "../helpers/zod/base_def" | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| export const utdfn_def = base_def.extend({ | ||||||||||||||||||||||||||||||||||
| fn: z.string(), | ||||||||||||||||||||||||||||||||||
| num_pins: z.number().default(4), | ||||||||||||||||||||||||||||||||||
| w: z.string().default("1mm"), | ||||||||||||||||||||||||||||||||||
| h: z.string().default("1mm"), | ||||||||||||||||||||||||||||||||||
| p: z.string().default("0.65mm"), | ||||||||||||||||||||||||||||||||||
| pl: z.string().default("0.3mm"), | ||||||||||||||||||||||||||||||||||
| pw: z.string().default("0.25mm"), | ||||||||||||||||||||||||||||||||||
| epw: z.string().default("0.45mm"), | ||||||||||||||||||||||||||||||||||
| eph: z.string().default("0.45mm"), | ||||||||||||||||||||||||||||||||||
| string: z.string().optional(), | ||||||||||||||||||||||||||||||||||
| ep: z.boolean().default(true), | ||||||||||||||||||||||||||||||||||
| }) | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| export type utdfnDef = z.infer<typeof utdfn_def> | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| export const utdfn = ( | ||||||||||||||||||||||||||||||||||
| raw_params: utdfnDef, | ||||||||||||||||||||||||||||||||||
| ): { circuitJson: AnyCircuitElement[]; parameters: any } => { | ||||||||||||||||||||||||||||||||||
| const params = utdfn_def.parse(raw_params) | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| const w = length.parse(params.w) | ||||||||||||||||||||||||||||||||||
| const h = length.parse(params.h) | ||||||||||||||||||||||||||||||||||
| const p = length.parse(params.p) | ||||||||||||||||||||||||||||||||||
| const pl = length.parse(params.pl) | ||||||||||||||||||||||||||||||||||
| const pw = length.parse(params.pw) | ||||||||||||||||||||||||||||||||||
| const epw = length.parse(params.epw) | ||||||||||||||||||||||||||||||||||
| const eph = length.parse(params.eph) | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| const pads: AnyCircuitElement[] = [] | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| // UTDFN-4: 2 on each side | ||||||||||||||||||||||||||||||||||
| for (let i = 0; i < params.num_pins; i++) { | ||||||||||||||||||||||||||||||||||
| const isLeft = i < params.num_pins / 2 | ||||||||||||||||||||||||||||||||||
| const x = isLeft ? -w / 2 + pl / 2 : w / 2 - pl / 2 | ||||||||||||||||||||||||||||||||||
| const y = ((i % 2 === 0 ? 1 : -1) * p) / 2 | ||||||||||||||||||||||||||||||||||
| pads.push(rectpad(i + 1, x, y, pl, pw)) | ||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||
|
Comment on lines
+40
to
+45
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Pin positioning logic only works correctly for 4-pin packages (2 per side). For packages with more pins per side (e.g., 6-pin, 8-pin), the Either:
const pinsPerSide = params.num_pins / 2
const pinIndexOnSide = i % pinsPerSide
const y = (pinIndexOnSide - (pinsPerSide - 1) / 2) * p
Suggested change
Spotted by Graphite Agent |
||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| if (params.ep) { | ||||||||||||||||||||||||||||||||||
| pads.push(rectpad(params.num_pins + 1, 0, 0, epw, eph)) | ||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| const silkscreenRefText: SilkscreenRef = silkscreenRef(0, h / 2 + 0.5, 0.2) | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| return { | ||||||||||||||||||||||||||||||||||
| circuitJson: [...pads, silkscreenRefText], | ||||||||||||||||||||||||||||||||||
| parameters: params, | ||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||
| Original file line number | Diff line number | Diff line change | ||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
|
|
@@ -39,6 +39,20 @@ export type Footprinter = { | |||||||||||||
| dip: ( | ||||||||||||||
| num_pins?: number, | ||||||||||||||
| ) => FootprinterParamsBuilder<"w" | "p" | "id" | "od" | "wide" | "narrow"> | ||||||||||||||
| pdip: ( | ||||||||||||||
| num_pins?: number, | ||||||||||||||
| ) => FootprinterParamsBuilder<"w" | "p" | "id" | "od" | "wide" | "narrow"> | ||||||||||||||
| pdip8: () => FootprinterParamsBuilder< | ||||||||||||||
| "w" | "p" | "id" | "od" | "wide" | "narrow" | ||||||||||||||
| > | ||||||||||||||
| spdip: ( | ||||||||||||||
| num_pins?: number, | ||||||||||||||
| ) => FootprinterParamsBuilder<"w" | "p" | "id" | "od" | "wide" | "narrow"> | ||||||||||||||
| utdfn: ( | ||||||||||||||
| num_pins?: number, | ||||||||||||||
| ) => FootprinterParamsBuilder< | ||||||||||||||
| "w" | "h" | "p" | "pl" | "pw" | "epw" | "eph" | "ep" | ||||||||||||||
| > | ||||||||||||||
| cap: () => FootprinterParamsBuilder<CommonPassiveOptionKey> | ||||||||||||||
| res: () => FootprinterParamsBuilder<CommonPassiveOptionKey> | ||||||||||||||
| diode: () => FootprinterParamsBuilder<CommonPassiveOptionKey> | ||||||||||||||
|
|
@@ -386,7 +400,11 @@ export const footprinter = (): Footprinter & { | |||||||||||||
| } | ||||||||||||||
| } | ||||||||||||||
| return (v: any) => { | ||||||||||||||
| if (Object.keys(target).length === 0) { | ||||||||||||||
| if ( | ||||||||||||||
| Object.keys(target).length === 0 || | ||||||||||||||
| prop === "pdip" || | ||||||||||||||
| prop === "pdip8" | ||||||||||||||
| ) { | ||||||||||||||
|
Comment on lines
+403
to
+407
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The special case for For example, Fix: if (Object.keys(target).length === 0) {
if (`${prop}${v}` in FOOTPRINT_FN) {
target[`${prop}${v}`] = true
target.fn = `${prop}${v}`
} else {
target[prop] = true
target.fn = prop
if (prop === "res" || prop === "cap") {
// ... existing logic
} else {
target.num_pins = Number.isNaN(Number.parseFloat(v))
? undefined
: Number.parseFloat(v)
}
}
}The special case should be removed since
Suggested change
Spotted by Graphite Agent |
||||||||||||||
| if (`${prop}${v}` in FOOTPRINT_FN) { | ||||||||||||||
| target[`${prop}${v}`] = true | ||||||||||||||
| target.fn = `${prop}${v}` | ||||||||||||||
|
|
||||||||||||||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Critical bug in pin number parsing regex. The new regex
/jst.*(\d+)/iwill incorrectly match digits from parameter values instead of the pin count.For example:
jst_ph_2_p2.54could match2fromp2.54instead of the pin count2jst_ph_4_w6.0could match6or4unpredictablyThe old regex
/(?:^|_)jst(\d+)(?:_|$)/correctly required word boundaries around the digit sequence.Spotted by Graphite Agent

Is this helpful? React 👍 or 👎 to let us know.