Author Topic: Programming with IronPython  (Read 23699 times)

0 Members and 1 Guest are viewing this topic.

lightname

  • Guest
Programming with IronPython
« on: August 22, 2008, 10:19:15 AM »
Couldn't someone use  IronPython to program AutoCAD?
I've seen examples programming using F# (by Kean Walmsley, http://through-the-interface.typepad.com/).

If yes, could someone post an example?

I know that there are some examples programming Autocad with Python/IronPython, but they don't do any real drawing they only pop up windows or count layers.

I'd like very much like to see an example of drawing a line or a circle.



Glenn R

  • Guest
Re: Programming with IronPython
« Reply #1 on: August 22, 2008, 10:22:35 AM »
'Poping up windows or counting layers' is conceptually no different to drawing a line or circle really.

MickD

  • King Gator
  • Posts: 3636
  • (x-in)->[process]->(y-out) ... simples!
Re: Programming with IronPython
« Reply #2 on: August 22, 2008, 04:47:07 PM »
Have you had a look at tjr's (Tim's) Pyacad.NET yet? It should be just what you're looking for.
It uses IronPython and the acad .net arx managed wrappers.
cheers.
"Programming is really just the mundane aspect of expressing a solution to a problem."
- John Carmack

"Short cuts make long delays,' argued Pippin.”
- J.R.R. Tolkien

It's Alive!

  • Retired
  • Needs a day job
  • Posts: 8703
  • AKA Daniel
Re: Programming with IronPython
« Reply #3 on: August 23, 2008, 02:17:33 PM »
Yes I think it can be done. But one may need to write a few more helper classes in C#.
One issue I found is you can’t open objects for write with ironpython (I don’t know why).
But it would be easy enough for one to write helper functions for adding objects to records or the database

Another issue I found is that there is no casting in Python, so if one were to use a method like
Code: [Select]
tr.GetObject(id , AcDb.OpenMode.ForRead ,False)what type of object does python see? How would one cast from a DbObject to a BlockTableRecord?
Again one could write helper functions to get objects ie GetBlockTableRecord(…);

So in the end, it certainly is possible

maybe someone could look at my attemp and point out my errors

Code: [Select]
#thanks to kwb for the C# code to translate
import System
import Autodesk.AutoCAD.DatabaseServices as AcDb
import Autodesk.AutoCAD.Geometry as AcGe
import Autodesk.AutoCAD.ApplicationServices as AcAp

try:
    ed = AcAp.Application.DocumentManager.MdiActiveDocument.Editor
   
    ed.WriteMessage("\n Hello")
   
    db = AcDb.HostApplicationServices.WorkingDatabase
    tm = db.TransactionManager
    tr = tm.StartTransaction()
    line = AcDb.Line(AcGe.Point3d(0,0,0),AcGe.Point3d(100,100,0))
    id = AcDb.SymbolUtilityServices.GetBlockModelSpaceId(db)

    # fails to open
    # can I cast this way???
    btrArray = System.Array[AcDb.BlockTableRecord]([tr.GetObject(id , AcDb.OpenMode.ForWrite ,False)])
    # btrArray = System.Array[AcDb.BlockTableRecord]([tr.GetObject(id , AcDb.OpenMode.ForRead ,False)])
    # btrArray = System.Array.CreateInstance(AcDb.BlockTableRecord, 1)
    # btrArray[0] = tr.GetObject(id , AcDb.OpenMode.ForRead ,False)

    btrArray[0].AppendEntity(line)
    tr.AddNewlyCreatedDBObject(line, true)
    tr.Commit()
    tr.Dispose()
except:
    tr.Dispose()
    line.Dispose()

tjr

  • Guest
Re: Programming with IronPython
« Reply #4 on: August 23, 2008, 02:46:44 PM »
Looks like I'm going to have to fire up my windows laptop and have a look at this. I don't see what would prevent one from opening the block table for write, I'll have to take a look at that.


Another issue I found is that there is no casting in Python, so if one were to use a method like
Code: [Select]
tr.GetObject(id , AcDb.OpenMode.ForRead ,False)what type of object does python see? How would one cast from a DbObject to a BlockTableRecord?
Try something like this to find out the objects type. If you're using PyAcad.NET it should just write it to the command line.
Code: [Select]
i = tr.GetObject(id , AcDb.OpenMode.ForRead ,False)
print type(i)

tjr

  • Guest
Re: Programming with IronPython
« Reply #5 on: August 23, 2008, 03:55:54 PM »
lightname:

Sorry you weren't pleased with my other examples. You owe me a beer. :)

Warning: This is ugly code that was hacked up very quickly. It's Saturday, I have tons of yard work to do and I don't have the patience to make this look good. But it is functional if you use my PyAcad.NET package.
Code: [Select]
#Draws a circle.
#Note: This code is very sloppy. Just an example of how one would
#      draw a circle. Not good coding style.
import Autodesk.AutoCAD.DatabaseServices as dbs
import Autodesk
import Autodesk.AutoCAD.Geometry as geo

doclock = Autodesk.AutoCAD.ApplicationServices.Application.DocumentManager.MdiActiveDocument.LockDocument()
db = dbs.HostApplicationServices.WorkingDatabase
tm = db.TransactionManager
tr = tm.StartTransaction()
bt = tm.GetObject(dbs.HostApplicationServices.WorkingDatabase.BlockTableId, dbs.OpenMode.ForRead)
btr = tm.GetObject(dbs.HostApplicationServices.WorkingDatabase.CurrentSpaceId, dbs.OpenMode.ForWrite )

circle = dbs.Circle(geo.Point3d(10,10,0),geo.Vector3d.ZAxis, 2)

btr.AppendEntity(circle)
tm.AddNewlyCreatedDBObject(circle, True)

tr.Commit()

btr.Dispose()
bt.Dispose()
tr.Dispose()
tm.Dispose()
db.Dispose()
doclock.Dispose()

tjr

  • Guest
Re: Programming with IronPython
« Reply #6 on: August 23, 2008, 03:58:18 PM »
One issue I found is you can’t open objects for write with ironpython (I don’t know why).
Just a note. I was able to get around this by locking the document. See my code above.

It's Alive!

  • Retired
  • Needs a day job
  • Posts: 8703
  • AKA Daniel
Re: Programming with IronPython
« Reply #7 on: August 24, 2008, 12:52:08 AM »
One issue I found is you can’t open objects for write with ironpython (I don’t know why).
Just a note. I was able to get around this by locking the document. See my code above.

Ah! Excellent  8-)

It's Alive!

  • Retired
  • Needs a day job
  • Posts: 8703
  • AKA Daniel
Re: Programming with IronPython
« Reply #8 on: August 24, 2008, 12:53:53 AM »
my first working Python code  :lol:

Code: [Select]
#thanks to kwb for the C# code to translate
import System
import Autodesk.AutoCAD.DatabaseServices as AcDb
import Autodesk.AutoCAD.Geometry as AcGe
import Autodesk.AutoCAD.ApplicationServices as AcAp

try:
    ed = AcAp.Application.DocumentManager.MdiActiveDocument.Editor
    doclock = AcAp.Application.DocumentManager.MdiActiveDocument.LockDocument()
    db = AcDb.HostApplicationServices.WorkingDatabase
    tm = db.TransactionManager
    tr = tm.StartTransaction()
    line = AcDb.Line(AcGe.Point3d(0,0,0),AcGe.Point3d(100,100,0))
    id = AcDb.SymbolUtilityServices.GetBlockModelSpaceId(db)
    btr = tr.GetObject(id , AcDb.OpenMode.ForWrite ,False)
    btr.AppendEntity(line)
    tr.AddNewlyCreatedDBObject(line, True)
    tr.Commit()
    tr.Dispose()
    doclock.Dispose()
    ed.WriteMessage("\n done")
except:
    tr.Dispose()
    line.Dispose()
    doclock.Dispose()

tjr

  • Guest
Re: Programming with IronPython
« Reply #9 on: August 24, 2008, 02:33:41 AM »
In case it wasn't already know.
Code: [Select]
using Autodesk.AutoCAD.DatabaseServices;

Would translate to:
Code: [Select]
from Autodesk.AutoCAD.DatabaseServices import *

Then you wouldn't have to use the 'AcDb' stuff if you didn't want to. I personally prefer it.

tjr

  • Guest
Re: Programming with IronPython
« Reply #10 on: August 24, 2008, 02:41:18 AM »
my first working Python code  :lol:

Code: [Select]
#thanks to kwb for the C# code to translate
import System
import Autodesk.AutoCAD.DatabaseServices as AcDb
import Autodesk.AutoCAD.Geometry as AcGe
import Autodesk.AutoCAD.ApplicationServices as AcAp

try:
    ed = AcAp.Application.DocumentManager.MdiActiveDocument.Editor
    doclock = AcAp.Application.DocumentManager.MdiActiveDocument.LockDocument()
    db = AcDb.HostApplicationServices.WorkingDatabase
    tm = db.TransactionManager
    tr = tm.StartTransaction()
    line = AcDb.Line(AcGe.Point3d(0,0,0),AcGe.Point3d(100,100,0))
    id = AcDb.SymbolUtilityServices.GetBlockModelSpaceId(db)
    btr = tr.GetObject(id , AcDb.OpenMode.ForWrite ,False)
    btr.AppendEntity(line)
    tr.AddNewlyCreatedDBObject(line, True)
    tr.Commit()
    tr.Dispose()
    doclock.Dispose()
    ed.WriteMessage("\n done")
except:
    tr.Dispose()
    line.Dispose()
    doclock.Dispose()
Dan:

Very nice but you can't you try except like that, it makes it impossible to debug.

It's Alive!

  • Retired
  • Needs a day job
  • Posts: 8703
  • AKA Daniel
Re: Programming with IronPython
« Reply #11 on: August 24, 2008, 03:27:32 AM »
Yeah, I am not sure about how to do this in Python, but in the case of an exception, the transaction must be closed or AutoCAD will crash hard,
doing it the way I did stopped that . Since there using no using statement in Python, maybe someone can post an example of try catch finally

MickD

  • King Gator
  • Posts: 3636
  • (x-in)->[process]->(y-out) ... simples!
Re: Programming with IronPython
« Reply #12 on: August 24, 2008, 05:44:24 AM »
<from the Py doc's> is this what you need?

Code: [Select]
>>> def divide(x, y):
...     try:
...         result = x / y
...     except ZeroDivisionError:
...         print "division by zero!"
...     else:
...         print "result is", result
...     finally:
...         print "executing finally clause"
...
>>> divide(2, 1)
result is 2
executing finally clause
>>> divide(2, 0)
division by zero!
executing finally clause
>>> divide("2", "1")
executing finally clause
Traceback (most recent call last):
  File "<stdin>", line 1, in ?
  File "<stdin>", line 3, in divide
TypeError: unsupported operand type(s) for /: 'str' and 'str'
"Programming is really just the mundane aspect of expressing a solution to a problem."
- John Carmack

"Short cuts make long delays,' argued Pippin.”
- J.R.R. Tolkien

It's Alive!

  • Retired
  • Needs a day job
  • Posts: 8703
  • AKA Daniel
Re: Programming with IronPython
« Reply #13 on: August 24, 2008, 08:00:07 AM »
Cool Thanks, Well now that I can draw a line in AutoCAD with twelve different programming  languages, I guess I need to pick one and get some work done :laugh:

quamper

  • Guest
Re: Programming with IronPython
« Reply #14 on: August 25, 2008, 08:47:58 AM »
Cool Thanks, Well now that I can draw a line in AutoCAD with twelve different programming  languages, I guess I need to pick one and get some work done :laugh:

Here's another one for you to learn how to draw a line in AutoCAD in  http://www.codeplex.com/IronScheme  ;-)

So you can put off getting some work done a little longer.