jscad / OpenJSCAD.org

JSCAD is an open source set of modular, browser and command line tools for creating parametric 2D and 3D designs with JavaScript code. It provides a quick, precise and reproducible method for generating 3D models, and is especially useful for 3D printing applications.
https://openjscad.xyz/
MIT License
2.67k stars 516 forks source link

booleans.intersect fails for an extrude with rotation #1019

Open paulftw opened 2 years ago

paulftw commented 2 years ago

Basically if a twist angle is large enough it breaks booleans.intersect.

Screen Shot 2022-03-03 at 8 53 48 PM

Demo: https://scriptcad.com/paulftw/playground

import {
  booleans,
  extrusions,
  geometries,
  maths,
  primitives,
  transforms,
} from '@jscad/modeling'

export const main = () => {
  const base = booleans.subtract(
    primitives.circle(5),
    transforms.translate([1, 0], primitives.circle(5)),
  )

  const xtr05 = transforms.translate(
    [0, 0, 0.7],
    extrusions.extrudeLinear(
      {
        height: 2,
        twistAngle: 0.5,
      },
      base,
    ),
  )

  const xtr10 = transforms.translate(
    [0, 0, 0.7],
    extrusions.extrudeLinear(
      {
        height: 2,
        twistAngle: 1,
      },
      base,
    ),
  )

  return [
    // Good intersection, 0.5rad
    transforms.translate(
      [0, 0, 0],
      booleans.intersect(xtr05, primitives.cube()),
    ),

    // Bad intersection, 1.0rad
    transforms.translate(
      [5, 0, 0],
      booleans.intersect(xtr10, primitives.cube()),
    ),
  ]
}
z3dev commented 2 years ago

Yeah. Extrusions are tricky sometimes. Have you tried increasing twistSteps ?

paulftw commented 2 years ago

This seems to me like a problem with intersect, not with extrusion.

Upon visual inspection the extrusion looks alright - no holes, no CW polygons, not self intersecting, etc. So basically I'm calling intersect on two seemingly correct 3d geometries, but it returns a messed up result.

If you think the bug is in the extrusion, How do I find it? What should I be looking for?

z3dev commented 2 years ago

Initially, you said…

Basically if a twist angle is large enough it breaks booleans.intersect.

If there are more steps then the walls of the extrusion are smoother and more contiguous. And I suspect that the booleans perform better as well.

I’m not sure there is a bug… if an extrusion is twisted beyond useable geometry then some adjustments should be made. All software has limitations.

z3dev commented 2 years ago

@paulftw I tried the example with twistSteps larger than 1. The results are far better.

const {
  booleans,
  extrusions,
  geometries,
  maths,
  primitives,
  transforms,
} = require('@jscad/modeling')

const main = () => {
  const base = booleans.subtract(
    primitives.circle(5),
    transforms.translate([1, 0], primitives.circle(5)),
  )

  const xtr05 = transforms.translate(
    [0, 0, 0.7],
    extrusions.extrudeLinear(
      {
        height: 2,
        twistAngle: 0.5,
        twistSteps: 10,
      },
      base,
    ),
  )

  const xtr10 = transforms.translate(
    [0, 0, 0.7],
    extrusions.extrudeLinear(
      {
        height: 2,
        twistAngle: 1,
        twistSteps: 10,
      },
      base,
    ),
  )

  return [
    // Good intersection, 0.5rad
    transforms.translate(
      [0, 0, 0],
      booleans.intersect(xtr05, primitives.cube()),
    ),

    // Bad intersection, 1.0rad
    transforms.translate(
      [5, 0, 0],
      booleans.intersect(xtr10, primitives.cube()),
    ),
  ]
}
module.exports = {main}
z3dev commented 2 years ago

@paulftw are you able to continue after making the suggested changes?