Community
Fusion API and Scripts
Got a new add-in to share? Need something specialized to be scripted? Ask questions or share what you’ve discovered with the community.
cancel
Showing results for 
Show  only  | Search instead for 
Did you mean: 

Creating A Sweep Feature without a Guide Line F360 API Error

2 REPLIES 2
SOLVED
Reply
Message 1 of 3
jakedbirk
160 Views, 2 Replies

Creating A Sweep Feature without a Guide Line F360 API Error

Hello, 

I am having a problem using the API to sweep a profile along a path without a guideline which does not through any errors using the GUI. 

 

This script will eventually be moved to my Add-In and is supposed to take a 2D profile, angle it to match the pitch of a staircase and sweep the profile along the path to create a returned mitered handrail. I've attached a picture of me using the GUI to make the final sweep. 

I've been getting errors but I cannot determine why. I've already spent a good amount of time playing around with the script over the course of a few days and don't seem to be getting very far. 

 

The troublesome part of this script begins on line 100.

Also: this script uses a 2d.dxf file which is a very important part of the final outcome (where the user should be able to select from a list of GUI-created profiles.  So I've attached the script folder with that file. 


Code Snipet:

 

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

def run(context):
    ui = None
    try:
        app = adsk.core.Application.get()
        ui  = app.userInterface
        design = adsk.fusion.Design.cast(app.activeProduct)

        #Pull A Function I Use in Other Parts of My Add-in
        def addInchSketchPoint(sk: adsk.fusion.Sketch, x: float, y: float, z: float) -> adsk.fusion.SketchPoint: #This Function Was Written By Brian Etkins
            pnt = adsk.core.Point3D.create(x * 2.54, y * 2.54, z * 2.54)
            return sk.sketchPoints.add(pnt)

        #Pull Up File Name: 
        pathProfile = os.path.join(os.path.dirname(os.path.abspath(__file__)), 'resources/3dData/','profile2x4.dxf')
        
        #Info Pulled From Flight & User
        unitRise = 8
        unitRun = 10
        treadOverhang = 1.25
        topOfRailHeight = 36
        railFromWall = 1.25
        riseCount = 15
        
        #Calculated Variables
        slope = math.atan(unitRise/unitRun)
        zIncreaseOverhang = math.tan(slope)*treadOverhang
        
        #Info Pulled From Profile (How exactly this happens is TBD (Maybe Bounding Box is a Good Idea))
        profileHeight = 1.5
        profileWidth = 3.5
        
        #Grabbing the Root Component 
        compRoot = design.rootComponent

        #import manager 
        importMgr = app.importManager
        impOptionsProfile = importMgr.createDXF2DImportOptions(pathProfile,compRoot.xYConstructionPlane) #NOTE: Although this sketch ends up in the 
        importMgr.importToTarget(impOptionsProfile,compRoot)

        #Grab the sketch and create an object collection with all of its objects
        sketch = compRoot.sketches.item(compRoot.sketches.count-1) 
        all = adsk.core.ObjectCollection.create()
        for c in sketch.sketchCurves:
            all.add(c)
        for p in sketch.sketchPoints:
            all.add(p)

        #First Rotation along X axis 
        axis = sketch.xDirection #Grabs vector (1,0,0) (in the sketch)
        axis.transformBy(sketch.transform) #Makes the vector (1,0,0) compared to the root component
        origin = sketch.origin #Grabs the sketch origin
        origin.transformBy(sketch.transform) #Makes sure its the root component origin
        mat = adsk.core.Matrix3D.create()
        mat.setToRotation(math.pi /2, axis, origin)
        sketch.move(all, mat)

        #Rotation Along Z Axis (Sketch is now effectively placed in the yZPlane but all the math is consitent with yZ plane)
        axis = adsk.core.Vector3D.create(0,0,1)
        axis.transformBy(sketch.transform)
        origin = sketch.origin
        origin.transformBy(sketch.transform)
        mat = adsk.core.Matrix3D.create()
        mat.setToRotation(math.pi/2,axis,origin)
        sketch.move(all,mat)

        #Rotation to Rake Angle
        axis = sketch.xDirection #Grabs vector (1,0,0) (in the sketch)
        axis.transformBy(sketch.transform) #Makes the vector (1,0,0) compared to the root component
        origin = sketch.origin #Grabs the sketch origin
        origin.transformBy(sketch.transform) #Makes sure its the root component origin
        mat = adsk.core.Matrix3D.create()
        mat.setToRotation(slope, axis, origin)
        sketch.move(all, mat)


        #Raise Sketch to TopOfRailHeight above Nosing Line
        vectorRaiseSketch = adsk.core.Vector3D.create(0,-treadOverhang*2.54,unitRise*2.54+topOfRailHeight*2.54) 
        transform = adsk.core.Matrix3D.create()
        transform.translation = vectorRaiseSketch
        sketch.move(all,transform)

        #Pull Centroid From Rail Profile
        profileRail = sketch.profiles.item(sketch.profiles.count -1 )
        profRailY = profileRail.areaProperties().centroid.y

        #Calculate Point Values
        xOffsetOuter = 0
        xOffsetInner = profileWidth/2+railFromWall

        #Create Points for Rail 
        pointRailBottom = addInchSketchPoint(sketch,xOffsetOuter,0,unitRise+topOfRailHeight+zIncreaseOverhang)
        pointRailMiterBottom = addInchSketchPoint(sketch,xOffsetInner,0,unitRise+topOfRailHeight+zIncreaseOverhang)
        pointRailMiterTop = addInchSketchPoint(sketch,xOffsetInner,pointRailMiterBottom.geometry.y/2.54 + (riseCount-1)*unitRun,pointRailMiterBottom.geometry.z/2.54 + (riseCount-1)*unitRise)
        pointRailTop = addInchSketchPoint(sketch,xOffsetOuter,pointRailMiterTop.geometry.y/2.54,pointRailMiterTop.geometry.z/2.54)
        #Create Lines Connecting Points 
        lineBottomMiter = sketch.sketchCurves.sketchLines.addByTwoPoints(pointRailBottom,pointRailMiterBottom)
        lineMiddleRail = sketch.sketchCurves.sketchLines.addByTwoPoints(pointRailMiterBottom,pointRailMiterTop)
        lineTopMiter = sketch.sketchCurves.sketchLines.addByTwoPoints(pointRailMiterTop,pointRailTop)


        

        #TODO: Add Sweep
        col = adsk.core.ObjectCollection.create()
        col.add(lineBottomMiter)
        col.add(lineMiddleRail)
        col.add(lineTopMiter)   

        path = adsk.fusion.Path.create(col,True)
    

        inpSweep = compRoot.features.sweepFeatures.createInput(profileRail,path,3)

        inpSweep.guideRail = None

        compRoot.features.sweepFeatures.add(inpSweep)
        
    except:
        if ui:
            ui.messageBox('Failed:\n{}'.format(traceback.format_exc()))

 

 

 

birkmaij_0-1692988562554.png

 

Thank You for Reading & Helping!

2 REPLIES 2
Message 2 of 3
Jorge_Jaramillo
in reply to: jakedbirk

Hi @jakedbirk ,

 

In this post https://forums.autodesk.com/t5/fusion-360-api-and-scripts/error-when-creating-a-sweep/td-p/11735184

@BrianEkins found the problem.

 

So, you just need to copy line 85 into 113 and your code will run.

It is a kind of bug if you get the profile before you make the path.

 

Regards,

Jorge Jaramillo

Software Engineer

 

Message 3 of 3
jakedbirk
in reply to: Jorge_Jaramillo

Thank you so much, that solution worked like a charm!

Perhaps Autodesk should not this error in the documentation to help other programmers in the future.

Also thank you again to @BrianEkins who always seems to play a role in the solutions to my F360 API problems!

Can't find what you're looking for? Ask the community or share your knowledge.

Post to forums  

Autodesk DevCon in Munich May 28-29th


Autodesk Design & Make Report