"""Quad flat no-lead IC package (VQFN) by TI package outline. Centred on the origin with the seating plane on the XY plane: terminals along all four sides, pin 1 at the +Y end of the -X side and counting counter-clockwise seen from above, and the exposed thermal pad in the middle. Dimensions from the TI outline named by `package`; see the README.""" from steve import Model package = "RGE0024H" # TI package outline detail = "full" # full: body, pin-1 mark, terminals and thermal pad; simple: the body only # outline: (kind, pins, pitch, body size, height max, standoff, terminal length, terminal width, thermal pad size, terminal thickness), bodies and thermal # pads square, ranges as (min, max), single values as drawn (thickness is the outline's reference), all in mm. # TI package outlines in TI datasheets, https://www.ti.com/lit/ds/symlink/.pdf: RGE0024H in BQ24166 (SLUSAP4B, 4219016/A 08/2017), RGZ0048A and # RHB0032E in CC2640R2F (SWRS204C, 4219044/D 02/2022 and 4223442/B 08/2019), RGC0064B in MSP430F5529 (SLAS590P, 4219010/A 10/2018), RGW0020A in TPS7A47 # (SBVS204G, 4219039/A 06/2018). Thermal pads are drawn as nominal +/-0.1. RGC0064B's height is 0.8 to 1.0; the others give 1 maximum. OUTLINES = { "RGW0020A": ("VQFN", 20, 0.65, (4.9, 5.1), 1.0, (0.0, 0.05), (0.45, 0.65), (0.26, 0.36), 3.15, 0.1), "RGE0024H": ("VQFN", 24, 0.5, (3.9, 4.1), 1.0, (0.0, 0.05), (0.28, 0.48), (0.18, 0.30), 2.7, 0.2), "RHB0032E": ("VQFN", 32, 0.5, (4.9, 5.1), 1.0, (0.0, 0.05), (0.3, 0.5), (0.2, 0.3), 3.45, 0.2), "RGZ0048A": ("VQFN", 48, 0.5, (6.9, 7.1), 1.0, (0.0, 0.05), (0.3, 0.5), (0.18, 0.30), 5.15, 0.2), "RGC0064B": ("VQFN", 64, 0.5, (8.85, 9.15), 1.0, (0.0, 0.05), (0.3, 0.5), (0.18, 0.30), 4.25, 0.2), } # The pin-1 mark is a proportion, for looks. def mid(pair): return (pair[0] + pair[1]) / 2 kind, pins, pitch, size, top, standoff, term_l, term_w, pad, thick = OUTLINES[package] size, standoff, term_l, term_w = mid(size), mid(standoff), mid(term_l), mid(term_w) per_side = pins // 4 first = -(per_side - 1) * pitch / 2 half = size / 2 model = Model() model.plane("body_plane", on="XY", offset=standoff, name="Body") with model.sketch("body_sketch", on="body_plane", name="Body") as sk: sk.rect("body_rect", (-half, -half), (half, half)) model.extrude("body", "body_sketch", distance=top - standoff, name="Body") if detail == "full": model.plane("top_plane", on="XY", offset=top, name="Top") with model.sketch("mark_sketch", on="top_plane", name="Pin-1 mark") as sk: sk.circle("mark_circle", (-half + 0.1 * size, half - 0.1 * size), 0.04 * size) model.extrude("mark", "mark_sketch", distance=-0.05, op="cut", name="Pin-1 mark") with model.sketch("terms_x", on="XY", name="Terminals") as sk: for i in range(per_side): y = first + i * pitch sk.rect(f"term_west_{i}", (-half, y - term_w / 2), (-half + term_l, y + term_w / 2)) sk.rect(f"term_east_{i}", (half - term_l, y - term_w / 2), (half, y + term_w / 2)) model.extrude("terms_x_body", "terms_x", distance=thick, name="Terminals") with model.sketch("terms_y", on="XY", name="Terminals") as sk: for i in range(per_side): x = first + i * pitch sk.rect(f"term_south_{i}", (x - term_w / 2, -half), (x + term_w / 2, -half + term_l)) sk.rect(f"term_north_{i}", (x - term_w / 2, half - term_l), (x + term_w / 2, half)) model.extrude("terms_y_body", "terms_y", distance=thick, name="Terminals") with model.sketch("pad_sketch", on="XY", name="Thermal pad") as sk: sk.rect("pad_rect", (-pad / 2, -pad / 2), (pad / 2, pad / 2)) model.extrude("pad", "pad_sketch", distance=thick, name="Thermal pad") model.material("pla", color="#26282b") result = model.result()