jscad-electronics 0.0.182 → 0.0.184

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/vanilla.d.ts CHANGED
@@ -28,12 +28,13 @@ type NemaMotorProps = NemaMotorModelPropsInput & {
28
28
  bodyColor?: string;
29
29
  capColor?: string;
30
30
  shaftColor?: string;
31
+ screwColor?: string;
31
32
  };
32
33
  type NemaFrameMotorProps = Omit<NemaMotorProps, "nemaSize">;
33
34
  /** Mounting face at Z=0, body along -Z, shaft along +Z; all lengths in mm.
34
35
  * Parameters follow the modelprinter NEMA contract; JSCAD builds all geometry.
35
36
  */
36
- declare function NemaMotor({ bodyColor, capColor, shaftColor, ...props }: NemaMotorProps): react_jsx_runtime.JSX.Element;
37
+ declare function NemaMotor({ bodyColor, capColor, shaftColor, screwColor, ...props }: NemaMotorProps): react_jsx_runtime.JSX.Element;
37
38
  declare const NEMA8: (props: NemaFrameMotorProps) => react_jsx_runtime.JSX.Element;
38
39
  declare const NEMA17: (props: NemaFrameMotorProps) => react_jsx_runtime.JSX.Element;
39
40
  declare const NEMA23: (props: NemaFrameMotorProps) => react_jsx_runtime.JSX.Element;
package/dist/vanilla.js CHANGED
@@ -218,7 +218,7 @@ var createHexSocketBoltMesh = (input) => {
218
218
  } = hexSocketBoltDimensions[props.metricSize];
219
219
  const { length, showThreads } = props;
220
220
  const segments = 96;
221
- const steps = Math.max(2, Math.ceil(length / pitch * 24));
221
+ const steps = showThreads ? Math.max(2, Math.ceil(length / pitch * 24)) : 2;
222
222
  if (steps > 24e3)
223
223
  throw new Error(
224
224
  "Bolt length exceeds mesh resolution limit (1000 thread turns)"
@@ -254,8 +254,11 @@ var createHexSocketBoltMesh = (input) => {
254
254
  }
255
255
  };
256
256
  let previous = -1;
257
- for (let step = 0; step <= steps; step++) {
258
- const z = -length + length * step / steps;
257
+ const shaftLevels = showThreads ? Array.from(
258
+ { length: steps + 1 },
259
+ (_, step) => -length + length * step / steps
260
+ ) : [-length, -length + tipBevel, 0];
261
+ for (const z of shaftLevels) {
259
262
  const current = ring(z, (angle) => {
260
263
  const phase = ((z / pitch - angle / (2 * Math.PI)) % 1 + 1) % 1;
261
264
  const distance2 = Math.min(phase, 1 - phase);
@@ -472,7 +475,11 @@ function SheetMetal({ color = "#737e8f", ...props }) {
472
475
  }
473
476
 
474
477
  // lib/NemaMotor.tsx
478
+ import jscad3 from "@jscad/modeling";
479
+
480
+ // lib/utils/nemaMotorWireGeometry.ts
475
481
  import jscad2 from "@jscad/modeling";
482
+ import { getNemaMotorReferencePoints } from "@tscircuit/modelprinter";
476
483
 
477
484
  // lib/utils/nemaMotorParameters.ts
478
485
  import { mp as mp2, nemaMotorModelPropsSchema } from "@tscircuit/modelprinter";
@@ -480,6 +487,66 @@ var resolveNemaMotorProps = nemaMotorModelPropsSchema.parse.bind(
480
487
  nemaMotorModelPropsSchema
481
488
  );
482
489
 
490
+ // lib/utils/nemaMotorWireGeometry.ts
491
+ function createNemaMotorWireGeometry(input) {
492
+ const p = resolveNemaMotorProps(input);
493
+ if (p.wireConnection === "none") return [];
494
+ const { position } = getNemaMotorReferencePoints(p).wireside;
495
+ const angle = p.wireSideAngle * Math.PI / 180;
496
+ const place = (geometry) => jscad2.transforms.translate(
497
+ [position.x, position.y, position.z],
498
+ jscad2.transforms.rotateZ(angle, geometry)
499
+ );
500
+ if (p.wireConnection === "stubs") {
501
+ const colors = [
502
+ "#d53f3f",
503
+ "#2463af",
504
+ "#3b934b",
505
+ "#252830",
506
+ "#e5d049",
507
+ "#eeeeee",
508
+ "#ce7432",
509
+ "#803e91"
510
+ ];
511
+ return Array.from({ length: p.wireCount }, (_, i) => ({
512
+ color: colors[i],
513
+ geometry: place(
514
+ jscad2.transforms.translate(
515
+ [
516
+ (p.wireLength - 0.15) / 2,
517
+ (i - (p.wireCount - 1) / 2) * p.wireDiameter * 1.5,
518
+ 0
519
+ ],
520
+ jscad2.transforms.rotateY(
521
+ Math.PI / 2,
522
+ jscad2.primitives.cylinder({
523
+ height: p.wireLength + 0.15,
524
+ radius: p.wireDiameter / 2,
525
+ segments: 24
526
+ })
527
+ )
528
+ )
529
+ )
530
+ }));
531
+ }
532
+ const shell = jscad2.booleans.subtract(
533
+ jscad2.primitives.cuboid({ size: [6.1, 13.9, 4.5], center: [2.95, 0, 0] }),
534
+ jscad2.primitives.cuboid({ size: [5.5, 12.7, 3.3], center: [3.55, 0, 0] })
535
+ );
536
+ return [
537
+ { color: "#eeeeea", geometry: place(shell) },
538
+ ...Array.from({ length: 6 }, (_, i) => ({
539
+ color: "#b8bec6",
540
+ geometry: place(
541
+ jscad2.primitives.cuboid({
542
+ size: [3.4, 0.5, 0.5],
543
+ center: [1.7, (i - 2.5) * 2, 0]
544
+ })
545
+ )
546
+ }))
547
+ ];
548
+ }
549
+
483
550
  // lib/utils/nemaMotorGeometry.ts
484
551
  var circle = (radius, x = 0, y = 0) => Array.from({ length: 96 }, (_, i) => [
485
552
  x + radius * Math.cos(i * Math.PI / 48),
@@ -527,12 +594,34 @@ function createNemaMotorSections(input) {
527
594
  add("frontCap", front, -holeDepth, 0, holes);
528
595
  add("frontCap", front, -p.frontCapLength, -holeDepth);
529
596
  add("body", core, -p.bodyLength + p.rearCapLength, -p.frontCapLength);
530
- add(
531
- "rearCap",
532
- p.mountingHoleThrough ? core : front,
533
- -p.bodyLength,
534
- -p.bodyLength + p.rearCapLength
535
- );
597
+ if (p.backFace === "plain") {
598
+ add(
599
+ "rearCap",
600
+ p.mountingHoleThrough ? core : front,
601
+ -p.bodyLength,
602
+ -p.bodyLength + p.rearCapLength
603
+ );
604
+ } else {
605
+ const halfPitch = p.backFaceHoleSpacing / 2;
606
+ const rearHoles = [-halfPitch, halfPitch].flatMap(
607
+ (x) => [-halfPitch, halfPitch].map(
608
+ (y) => circle(p.backFaceHoleDiameter / 2, x, y)
609
+ )
610
+ );
611
+ add(
612
+ "rearCap",
613
+ front,
614
+ -p.bodyLength,
615
+ -p.bodyLength + p.backFaceHoleDepth,
616
+ rearHoles
617
+ );
618
+ add(
619
+ "rearCap",
620
+ front,
621
+ -p.bodyLength + p.backFaceHoleDepth,
622
+ -p.bodyLength + p.rearCapLength
623
+ );
624
+ }
536
625
  add("pilot", circle(p.pilotDiameter / 2), 0, p.pilotLength);
537
626
  const r = p.shaftDiameter / 2;
538
627
  const round = circle(r);
@@ -557,34 +646,60 @@ function createNemaMotorSections(input) {
557
646
  }
558
647
 
559
648
  // lib/NemaMotor.tsx
649
+ var generalize = jscad3.modifiers.generalize;
560
650
  function NemaMotor({
561
651
  bodyColor = "#242830",
562
652
  capColor = "#aeb5bd",
563
653
  shaftColor = "#b8bec6",
654
+ screwColor = "#626b78",
564
655
  ...props
565
656
  }) {
566
- return /* @__PURE__ */ jsx(Fragment2, { children: createNemaMotorSections(props).map((section, index) => {
567
- const outline = jscad2.geometries.geom2.fromPoints(section.outline);
568
- const profile = section.holes.length ? jscad2.booleans.subtract(
569
- outline,
570
- ...section.holes.map((h2) => jscad2.geometries.geom2.fromPoints(h2))
571
- ) : outline;
572
- const geometry = jscad2.transforms.translate(
573
- [0, 0, section.zMin],
574
- jscad2.extrusions.extrudeLinear(
575
- { height: section.zMax - section.zMin },
576
- profile
577
- )
578
- );
579
- return /* @__PURE__ */ jsx(
580
- Colorize,
581
- {
582
- color: section.name === "body" ? bodyColor : section.name === "shaft" ? shaftColor : capColor,
583
- children: /* @__PURE__ */ jsx(Custom, { geometry })
584
- },
585
- `${section.name}-${index}`
586
- );
587
- }) });
657
+ const p = resolveNemaMotorProps(props);
658
+ const screw = p.backFace === "screws" ? jscad3.transforms.rotateX(
659
+ Math.PI,
660
+ createHexSocketBoltGeom({
661
+ metricSize: p.backFaceScrewSize,
662
+ length: p.backFaceHoleDepth,
663
+ showThreads: false
664
+ })
665
+ ) : void 0;
666
+ const halfPitch = p.backFaceHoleSpacing / 2;
667
+ return /* @__PURE__ */ jsxs(Fragment2, { children: [
668
+ createNemaMotorSections(p).map((section, index) => {
669
+ const outline = jscad3.geometries.geom2.fromPoints(section.outline);
670
+ const profile = section.holes.length ? jscad3.booleans.subtract(
671
+ outline,
672
+ ...section.holes.map((h2) => jscad3.geometries.geom2.fromPoints(h2))
673
+ ) : outline;
674
+ const geometry = jscad3.transforms.translate(
675
+ [0, 0, section.zMin],
676
+ jscad3.extrusions.extrudeLinear(
677
+ { height: section.zMax - section.zMin },
678
+ profile
679
+ )
680
+ );
681
+ return /* @__PURE__ */ jsx(
682
+ Colorize,
683
+ {
684
+ color: section.name === "body" ? bodyColor : section.name === "shaft" ? shaftColor : capColor,
685
+ children: /* @__PURE__ */ jsx(Custom, { geometry: generalize({ simplify: true }, geometry) })
686
+ },
687
+ `${section.name}-${index}`
688
+ );
689
+ }),
690
+ createNemaMotorWireGeometry(p).map(({ geometry, color }, index) => /* @__PURE__ */ jsx(Colorize, { color, children: /* @__PURE__ */ jsx(Custom, { geometry: generalize({ simplify: true }, geometry) }) }, `wire-${index}`)),
691
+ screw && [-halfPitch, halfPitch].flatMap(
692
+ (x) => [-halfPitch, halfPitch].map((y) => /* @__PURE__ */ jsx(Colorize, { color: screwColor, children: /* @__PURE__ */ jsx(
693
+ Custom,
694
+ {
695
+ geometry: jscad3.transforms.translate(
696
+ [x, y, -p.bodyLength],
697
+ generalize({ simplify: true }, screw)
698
+ )
699
+ }
700
+ ) }, `rear-screw-${x}-${y}`))
701
+ )
702
+ ] });
588
703
  }
589
704
  var NEMA8 = (props) => /* @__PURE__ */ jsx(NemaMotor, { ...props, nemaSize: 8 });
590
705
  var NEMA17 = (props) => /* @__PURE__ */ jsx(NemaMotor, { ...props, nemaSize: 17 });
@@ -9414,8 +9529,8 @@ function renderNode(node, colorCtx, renderCtx) {
9414
9529
  }
9415
9530
  return (children ?? []).flatMap((c) => renderNode(c, colorCtx, renderCtx));
9416
9531
  }
9417
- function render(root, jscad3) {
9418
- const geometries = renderNode(root, void 0, { jscad: jscad3 });
9532
+ function render(root, jscad4) {
9533
+ const geometries = renderNode(root, void 0, { jscad: jscad4 });
9419
9534
  return { geometries };
9420
9535
  }
9421
9536
 
@@ -9503,24 +9618,24 @@ function convertCSGToThreeGeom(csg) {
9503
9618
  }
9504
9619
 
9505
9620
  // lib/vanilla/index.ts
9506
- function getJscadModelForFootprint(footprint, jscad3) {
9621
+ function getJscadModelForFootprint(footprint, jscad4) {
9507
9622
  const vnode = h(Footprinter3d, { footprint });
9508
- return render(vnode, jscad3);
9623
+ return render(vnode, jscad4);
9509
9624
  }
9510
- function getJscadModelForFootprintWithPads(footprint, jscad3) {
9625
+ function getJscadModelForFootprintWithPads(footprint, jscad4) {
9511
9626
  const vnode = h(
9512
9627
  Fragment,
9513
9628
  {},
9514
9629
  h(Footprinter3d, { footprint }),
9515
9630
  h(ExtrudedPads, { footprint })
9516
9631
  );
9517
- return render(vnode, jscad3);
9632
+ return render(vnode, jscad4);
9518
9633
  }
9519
- function createJSCADRenderer(jscad3) {
9634
+ function createJSCADRenderer(jscad4) {
9520
9635
  function createJSCADRoot(container) {
9521
9636
  return {
9522
9637
  render(element) {
9523
- const { geometries } = render(element, jscad3);
9638
+ const { geometries } = render(element, jscad4);
9524
9639
  container.splice(0, container.length, ...geometries);
9525
9640
  }
9526
9641
  };