Skip to content

feat: add SPDIP and UTDFN footprints#570

Open
sungdark wants to merge 1 commit intotscircuit:mainfrom
sungdark:feat/add-spdip-utdfn-pdip
Open

feat: add SPDIP and UTDFN footprints#570
sungdark wants to merge 1 commit intotscircuit:mainfrom
sungdark:feat/add-spdip-utdfn-pdip

Conversation

@sungdark
Copy link
Copy Markdown

@sungdark sungdark commented Apr 2, 2026

Summary

This PR adds two new footprints and string aliases:

Changes

  1. SPDIP (Shrink DIP) - Issue Implement SPDIP-28 #180

    • New spdip function with pitch = 1.778mm (vs standard 2.54mm)
    • Supports spdip28, spdip8, SPDIP-28 etc.
  2. UTDFN-4-EP(1x1) - Issue Implement UTDFN-4-EP(1x1) #183

    • New utdfn function for Ultra-Thin DFN with exposed thermal pad
    • Body: 1.0mm x 0.6mm, pitch 0.5mm
    • Supports utdfn4, UTDFN-4-EP(1x1) etc.
  3. PDIP string alias - Issue Implement PDIP-8 #371

    • Added normalization for "pdip8" to "dip8"
    • JLCPCB sPDIP-8 is the same as standard DIP-8

Note

Testing

  • All 391 tests pass
  • New tests added for spdip and utdfn footprints

- Add spdip (Shrink DIP) footprint with 1.778mm pitch
- Add utdfn (Ultra-Thin DFN) footprint with thermal pad for UTDFN-4-EP(1x1)
- Add string normalization for pdip, spdip, and UTDFN-4-EP(1x1) aliases
- Add tests for spdip and utdfn footprints
- Fix string normalization for sot-223-N and to-220f-N aliases

Fixes: Issue tscircuit#371 (PDIP-8 alias), Issue tscircuit#180 (SPDIP-28), Issue tscircuit#183 (UTDFN-4-EP)
Note: SOT-223-5 (Issue tscircuit#181) was already implemented
@sungdark sungdark requested a review from seveibar as a code owner April 2, 2026 10:05
Comment on lines +1 to +39
import { test, expect } from "bun:test"
import { convertCircuitJsonToPcbSvg } from "circuit-to-svg"
import { fp } from "../src/footprinter"
import type { AnyCircuitElement } from "circuit-json"

test("spdip28", () => {
const circuitJson = fp
.string("spdip28")
.circuitJson() as AnyCircuitElement[]
const svgContent = convertCircuitJsonToPcbSvg(circuitJson)
expect(svgContent).toMatchSvgSnapshot(import.meta.path, "spdip28")
})

test("SPDIP-28 (alias)", () => {
const aliasSvg = convertCircuitJsonToPcbSvg(
fp.string("SPDIP-28").circuitJson(),
)
const canonicalSvg = convertCircuitJsonToPcbSvg(
fp.string("spdip28").circuitJson(),
)
expect(aliasSvg).toEqual(canonicalSvg)
})

test("spdip8", () => {
const circuitJson = fp
.string("spdip8")
.circuitJson() as AnyCircuitElement[]
const svgContent = convertCircuitJsonToPcbSvg(circuitJson)
expect(svgContent).toMatchSvgSnapshot(import.meta.path, "spdip8")
})

test("spdip default params", () => {
const json = fp.string("spdip28").json()
// SPDIP defaults: pitch = 1.778mm (shrink), width = 7.62mm (narrow body)
expect(json.fn).toBe("spdip")
expect(json.num_pins).toBe(28)
expect(json.w).toBe(7.62)
expect(json.p).toBe(1.778)
})
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This test file contains 4 test() calls, which violates the rule that a *.test.ts file may have AT MOST one test(...). The file should be split into multiple numbered files like spdip1.test.ts, spdip2.test.ts, spdip3.test.ts, and spdip4.test.ts, with each file containing only one test() call.

Spotted by Graphite (based on custom rule: Custom rule)

Fix in Graphite


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

Comment on lines +1 to +32
import { test, expect } from "bun:test"
import { convertCircuitJsonToPcbSvg } from "circuit-to-svg"
import { fp } from "../src/footprinter"
import type { AnyCircuitElement } from "circuit-json"

test("utdfn4", () => {
const circuitJson = fp
.string("utdfn4")
.circuitJson() as AnyCircuitElement[]
const svgContent = convertCircuitJsonToPcbSvg(circuitJson)
expect(svgContent).toMatchSvgSnapshot(import.meta.path, "utdfn4")
})

test("UTDFN-4-EP(1x1) alias", () => {
const aliasSvg = convertCircuitJsonToPcbSvg(
fp.string("UTDFN-4-EP(1x1)").circuitJson(),
)
const canonicalSvg = convertCircuitJsonToPcbSvg(
fp.string("utdfn4").circuitJson(),
)
expect(aliasSvg).toEqual(canonicalSvg)
})

test("utdfn4 default params", () => {
const json = fp.string("utdfn4").json()
// UTDFN-4-EP(1x1) defaults: w=1.0mm, p=0.5mm
// Note: h is computed from pin layout, not passed as param
expect(json.fn).toBe("utdfn")
expect(json.num_pins).toBe(4)
expect(json.w).toBe(1)
expect(json.p).toBe(0.5)
})
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This test file contains 3 test() calls, which violates the rule that a *.test.ts file may have AT MOST one test(...). The file should be split into multiple numbered files like utdfn1.test.ts, utdfn2.test.ts, and utdfn3.test.ts, with each file containing only one test() call.

Spotted by Graphite (based on custom rule: Custom rule)

Fix in Graphite


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

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant