sketch.offset behaving weird

sketch.offset behaving weird

ksautodesk5MA6Q
Explorer Explorer
287 Views
1 Reply
Message 1 of 2

sketch.offset behaving weird

ksautodesk5MA6Q
Explorer
Explorer

I'm trying to create a sketch using the API and stumble upon 2 problems when using the sketch.offset function.

 

First: no matter which dirPoint I use (or whether I use positive or negative offset value), the created lines always go to the outside of the rectangle lines I pass in.

Second: my first tests revealed an order of the returned lines, but sometimes the wrong line is chosen to place the circle at the end (running script 5 to 7 times shows this).

 

Here's the commented script code (extracted from my add-on, but shows same behavior here):

How can I create an offset to the inside of the baseRect?

How can I ensure to pick the leftmost edge of the (inner, i.e. offset) rectangle (best without having to loop through lines and check coordinates min/max).

 

#Author-
#Description-

import adsk.core, adsk.fusion, adsk.cam, traceback

BORDER = 0.05
HOLE_DIAMETER = 0.15

DIM_DISTANCE = 0.2

def run(context):
    ui = None
    try:
        app = adsk.core.Application.get()
        design = app.activeProduct
        targetComponent = design.rootComponent

        constructionPlane = targetComponent.xYConstructionPlane
        sketches: adsk.fusion.Sketches = targetComponent.sketches
        sketch: adsk.fusion.Sketch = sketches.add(constructionPlane)
        baseOrigin = sketch.modelToSketchSpace(adsk.core.Point3D.create(0, 0, 0))

        length = 3.5
        depth = 1.1

        lines = sketch.sketchCurves.sketchLines
        baseRect: adsk.fusion.SketchLineList = lines.addTwoPointRectangle(
            baseOrigin,
            adsk.core.Point3D.create(baseOrigin.x + length, baseOrigin.y + depth, 0)
        )
        sketch.geometricConstraints.addHorizontal(baseRect.item(0))
        sketch.geometricConstraints.addHorizontal(baseRect.item(2))
        sketch.geometricConstraints.addVertical(baseRect.item(1))
        sketch.geometricConstraints.addVertical(baseRect.item(3))
        sketch.geometricConstraints.addCoincident(baseRect.item(0).startSketchPoint, sketch.originPoint)
        sketch.sketchDimensions.addDistanceDimension(
            baseRect.item(0).startSketchPoint,
            baseRect.item(0).endSketchPoint,
            adsk.fusion.DimensionOrientations.HorizontalDimensionOrientation,
            adsk.core.Point3D.create(length/2, -DIM_DISTANCE, 0)
        )
        sketch.sketchDimensions.addDistanceDimension(
            baseRect.item(1).startSketchPoint,
            baseRect.item(1).endSketchPoint,
            adsk.fusion.DimensionOrientations.VerticalDimensionOrientation,
            adsk.core.Point3D.create(length + DIM_DISTANCE, depth/2, 0)
        )

        # create mirror axis to get midpoint and for later use
        mirrorLine = lines.addByTwoPoints(
            adsk.core.Point3D.create(length / 2, 0, 0),
            adsk.core.Point3D.create(length / 2, depth, 0),
        )
        mirrorLine.isConstruction = True
        sketch.geometricConstraints.addMidPoint(mirrorLine.startSketchPoint, baseRect.item(0))
        sketch.geometricConstraints.addMidPoint(mirrorLine.endSketchPoint, baseRect.item(2))
        mirrorLineMidPoint = createMidPoint(sketch, mirrorLine)

        # This works so far

        # create offset for base rect
        objs = adsk.core.ObjectCollection.create()
        [objs.add(l) for l in baseRect]

        # PROBLEM 1: no matter which dirPoint I use, no matter whether I use BORDER or -BORDER,
        #            the offset is always created to the outside, but I want inside.
        dirPoint = mirrorLineMidPoint.geometry # my most obvious value
        # dirPoint = adsk.core.Point3D.create( 1,  0.5, 0)
        # dirPoint = adsk.core.Point3D.create(-1, 0.5, 0)
        offsetLines = sketch.offset(objs, dirPoint, BORDER)
        # first tests reveal:
        # item(0) = bottom, 1 = top, 2 = left, 3 = right
        leftOffsetLine = offsetLines.item(2)
        leftOffsetMidPoint = createMidPoint(sketch, leftOffsetLine)

        # create circle
        # PROBLEM 2: sometimes the circle is created with center on top rectangle line,
        #            most of the times correctly on the left line.
        #            Why does offsetLines.item(2) not always refer to the same line?
        circles = sketch.sketchCurves.sketchCircles
        leftCircle = circles.addByCenterRadius(leftOffsetMidPoint.geometry, HOLE_DIAMETER / 2)
        sketch.sketchDimensions.addDiameterDimension(leftCircle,
                                                    adsk.core.Point3D.create(leftOffsetMidPoint.geometry.x + HOLE_DIAMETER / 2,
                                                                            leftOffsetMidPoint.geometry.y + HOLE_DIAMETER / 2,
                                                                            0))
        sketch.geometricConstraints.addCoincident(leftCircle.centerSketchPoint, leftOffsetLine)

    except:
        if ui:
            ui.messageBox('Failed:\n{}'.format(traceback.format_exc()))

def createMidPoint(sketch: adsk.fusion.Sketch, curve: adsk.fusion.SketchCurve, point: adsk.core.Point3D = None) -> adsk.fusion.SketchPoint:
    if point is None:
        if type(curve) is adsk.fusion.SketchLine:
            point = adsk.core.Point3D.create(
                (curve.startSketchPoint.geometry.x + curve.endSketchPoint.geometry.x) / 2,
                (curve.startSketchPoint.geometry.y + curve.endSketchPoint.geometry.y) / 2,
                (curve.startSketchPoint.geometry.z + curve.endSketchPoint.geometry.z) / 2
            )
        else:
            raise TypeError("curve must be a SketchLine if point is not given")

    midPoint = sketch.sketchPoints.add(point)
    sketch.geometricConstraints.addMidPoint(midPoint, curve)
    return midPoint

 

 

0 Likes
288 Views
1 Reply
Reply (1)
Message 2 of 2

kandennti
Mentor
Mentor

Hi @ksautodesk5MA6Q -San.

 

Tried it, fixed two places.
However, I cannot figure out the cause of any of them.

・・・
        # first tests reveal:
        # item(0) = bottom, 1 = top, 2 = left, 3 = right
        leftOffsetLine = offsetLines.item(2)
        leftOffsetMidPoint = createMidPoint(sketch, leftOffsetLine)

        # create circle
        # PROBLEM 2: sometimes the circle is created with center on top rectangle line,
        #            most of the times correctly on the left line.
        #            Why does offsetLines.item(2) not always refer to the same line?
        circles = sketch.sketchCurves.sketchCircles
        leftCircle = circles.addByCenterRadius(leftOffsetMidPoint.geometry, HOLE_DIAMETER / 2)
        sketch.sketchDimensions.addDiameterDimension(leftCircle,
                                                    adsk.core.Point3D.create(leftOffsetMidPoint.geometry.x + HOLE_DIAMETER / 2,
                                                                            leftOffsetMidPoint.geometry.y + HOLE_DIAMETER / 2,
                                                                            0))
        # sketch.geometricConstraints.addCoincident(
        #     leftCircle.centerSketchPoint, leftOffsetLine)

    except:
        if ui:
            ui.messageBox('Failed:\n{}'.format(traceback.format_exc()))

def createMidPoint(
        sketch: adsk.fusion.Sketch,
        curve: adsk.fusion.SketchCurve,
        point: adsk.core.Point3D = None
) -> adsk.fusion.SketchPoint:

    if point is None:
        if type(curve) is adsk.fusion.SketchLine:
            # point = adsk.core.Point3D.create(
            #     (curve.startSketchPoint.geometry.x + curve.endSketchPoint.geometry.x) / 2,
            #     (curve.startSketchPoint.geometry.y + curve.endSketchPoint.geometry.y) / 2,
            #     (curve.startSketchPoint.geometry.z + curve.endSketchPoint.geometry.z) / 2
            # )
            point = adsk.core.Point3D.create(0, 0, 0)
        else:
            raise TypeError("curve must be a SketchLine if point is not given")

    midPoint = sketch.sketchPoints.add(point)
    sketch.geometricConstraints.addMidPoint(midPoint, curve)
    return midPoint
・・・

As for the addCoincident method, it is incomplete because I cannot find any other way.

 

After executing the macro, Coincident in the GUI and dragging the circle with the mouse, the offset line moved outward.

1.png

 

I have a feeling this is not just an API problem.

0 Likes