Monday, December 08, 2008

Autodesk University 2008 is over with...

Well - I feel guilty... They gave me an "AU Blogger" ribbon for my badge - and then I didn't manage to Blog during the show. It was an incredibly busy week, including:

- Setup of the Altogether Smarter Challenge stations for Avatech (I'd like to throttle somebody at UPS who thinks that 11/21 to 12/1 constitutes 3-day delivery)...

- The Autodesk Developer Network DevDays conference... for my money, the best day of guidance you can get from Autodesk... Although this year there was a little bit more talk and a little bit less specifics than in previous years.

- We launched our new BIMreview application, which helps check your Revit models for standards and practices, to great feedback from Revit users! The crowd was 3-deep for most of the open exhibit time.

- I did my first solo class - CP315-4: Getting Down to BIM, Advanced Revit API to a crowd of perhaps 60-80 people. That went well (the contents should be posted on the AU site this week... after a little while there, I'll release it more broadly).

All in all, though - an incredibly busy week. And I only got to see about 1/3 of the sessions I had wanted to see.

While I can't share the specifics (much of the ADN stuff is under NDA), my general impressions of what's to come is that:

  • Autodesk continues to invest significantly in AutoCAD, even around 3D and other topics which you might imagine that they would delegate to the vertical products.
  • Autodesk continues to find ways to leverage the Media & Entertainment division software into the Design software side of things.

There's not much more I can say until whenever they free us from the blackout...

Oh yeah - and I think most people know it, but 2010 WILL be a new DWG format, and will break many of the existing applications out there (they plan this - only once every three years).

Monday, November 17, 2008

Jeremy Tammik is a MACHINE!

Recently I mentioned that Jeremy Tammik from Autodesk was starting a blog about developing software with Revit... and he's kept it up at a "blistering" pace - one very solid post every other day just about. It's scary.


It's particularly scary for me, since I'm doing an "Advanced Revit API" class at Autodesk University this year. It's a good thing that Jeremy only started recently - otherwise he would have overrun my class content :) within a few months.


But seriously, though - if you're interested in the Revit API, and how to push it beyond the basics, Jeremy's blog is building a wealth of knowledge.



Thursday, October 23, 2008

Revit 64-bit, and getting your applications there.

Well, we've finally updated and posted a new version of our Revit Utilities which support the new 64-bit versions of Revit 2009.





The good news is - if you're using pure Microsoft.NET - you can probably use your existing Add-in DLLs and everything will work just fine. If, on the other hand, you were making use of outside libraries, Win32 DLLs, or other things like that - then you've got some work ahead of you to get the 64-bit equivalents and figure out how to call the right one.





Why does .NET work so nicely?
Because, by default, when you make a .NET DLL it is compiled into an intermediate language called MSIL - and then it goes through the final step at runtime to become a 32-bit or 64-bit application (32-bit applications need 32-bit DLLs, and 64-bit applications, generally, need 64-bit DLLs). But by default, you build your .NET DLLs to run on "Any CPU":




What definitely needs a change? The Installer :(


So you've got your DLL working - and maybe that was easy... but that's really just the beginning. The installer is where it's a bit more of a pain. Here's why:

1. Registry

If you're reading registry keys to find out the location of Revit (so that you could update the REVIT.INI file) - you've got three new things to look for. Unfortunately, the only way to find where Revit is installed is look at the Uninstall registry keys in HKLM\Software\Microsoft\Windows\CurrentVersion\Uninstall.

The new keys for 64-bit Revit are:

  • {D2466208-7348-4214-B01E-7BC8729E2BD3} (Revit 2009 Arch 64)
  • {4A98F976-01B5-40E8-A496-AEFD85C3A446} (Revit 2009 MEP 64)
  • {C4B3B3C3-2EE9-48D3-9BF5-4443F7ECF759} (Revit 2009 Struct 64)


2. Another scenario - 32-bit Revit on a 64-bit OS

While this should become uncommon quickly - I've been AMAZED at how many users worldwide are running a 32-bit Revit on a 64-bit OS. Sure, it gives you access to a couple more GIGs of RAM - but oh, the headaches :).

In terms of our own headaches - the biggest one is that Revit's uninstall registry key lies about where Revit is installed (it's actually installed in the C:\Program Files (x86) folder in this case - but that's not what it says).

Also, when you deal with the Registry in general in this scenario, Windows keeps a separate parallel registry for 32-bit applications versus 64-bit applications (check out HKLM\SOFTWARE\WOW6432Node - and find the parallel registry universe).


All in all, if you're doing pure .NET work - it's mostly installer work to get your stuff onto Revit 64. If you're a commercial developer - get moving, because they're jumping to it like you wouldn't believe!

Thursday, September 11, 2008

Welcome two new Autodesk development blogs

I think it's always a good thing when a knowledge-based community gets bigger and the sources more prolific.

So I'd like to point out two new blogs by Autodesk development experts:

I'm a veteran of a good number of training classes and seminars of both of these gentlemen, and they should be a great addition to the CAD development blogging ecosystem.

If you ever get a chance to meet Brian, you have to ask him to show you one of the more simple but mind-bending demos... I spent years looking at Inventor drawings of 3D parts and assemblies - and one day he shows me a simple application which rotates the view of the drawing in 3D (normally you can only pan/zoom in a "2D" drawing). But it turns out that the "2D" drawing was 3D all along - all of a sudden you could see the 3D parts that were "behind" the 2D drawing, titleblock, etc. Very weird and somewhat psychodelic for people in the CAD world, at least (CAD drawings are supposed to be like digital paper, right?).

-Matt

Monday, August 18, 2008

.NET 3.5 SP1 - an obscure gift

JTBWorld pointed out a small but nice enhancement to the latest Service Pack for Microsoft .NET:

The fact that code executing from a network share now has the same permissions as code executing on your local hard drive.

(Begin Venting)
"What? it didn't before? Why?" - obviously you haven't had the pain of trying to make this work. Microsoft's concern was that code executing from a network share could be a virus, worm, etc - something undesirable. So they made it impossible. OK, so it wasn't impossible - they just made it aggravating. To make this work prior to now, you had to go into the world of CASPOL - Code Access Security POLicy, either through your control panel, your company security policies, or the CASPOL.exe command line tool. Fundamentally, you had to make guidelines for when to trust particular .NET assemblies (based on where they were installed, or a signed publisher cerificate, etc).

The joke is - that these restrictions were only for .NET applications. Any hacker who was using a non-.NET language had no such restrictions.

(End Venting)

Anyway - it's good news that it's a changed behavior. This should make it easier for average CAD Managers, IT managers and developers to support a centralized deployment methodology - whether for Revit, AutoCAD, etc.

(Note: Jimmy didn't even have it posted for a day before this caveat came up - you need to add an "acdbmgd.ini" file to force it to not optimize to .NET 3.5 SP1 work with AutoCAD at all).

Saturday, July 19, 2008

The minimum C# to learn to program Revit?

I received a good question the other day from someone who was interested in learning to program Revit. They had done some C programming years ago, and was somewhat overwhelmed by the size of the "Introduction to C#" kind of books (which do tend to be 3+ inches thick).

So I was trying to explain what the core concepts of C# (or any .NET language, for that matter) that they would need in order to get to the point where they would be "dangerous", as they say.

Here are my thoughts:

Object-Oriented Programming (OOP)
Everything in .NET (as well as everything in the Revit API) is built around objects. So you must understand the fundamentals of how to make and use objects.

  • Class definitions
  • Creating new objects
  • Fields and Properties and Methods
  • Object scope/lifecycle
  • The concept of NULL;
  • User Interface (any UI that you do revolves around OOP)

Basic language features
I originally didn't address this... you'll obviously need to learn the basic language features of whatever language you choose. Declarations, IF statements, dealing with Enumerated types, etc...

Enumerators, For loops and Foreach loops
Much of the Revit API revolves around these concepts for looking up elements or other information. Enumerators (or Iterators) is probably the least intuitive of the bunch.

Code Example:

// To go through all of the elements in the model, one way is to do the following:

ElementIterator ei = commandData.Application.ActiveDocument.Elements;

while (ei.MoveNext())
{
Element e = ei.Current as Element;

// now you do something with Element "e".

}

Arrays/Lists

Maybe it's just me, but almost every Revit application I'm involved with makes significant use of Arrays/Lists - so you may as well get comfortable with them. Personally, I'm a fan of what are called "Generic" Lists - which are lists of a specific type of object.

Code Example:

// if we had to go through all the elements, and find the elements that were "Pinned"

// Make our list object
List pinnedElements = new List();

// go through all the elements (NOTE: this way is far slower than some other alternatives - but reasonable for beginners)
ElementIterator ei = commandData.Application.ActiveDocument.Elements;

while (ei.MoveNext())
{
Element e = ei.Current as Element;

if (e.Pinned) pinnedElements.Add( e ); // if it is pinned, add it to the list
}

// now presumably we do something with all those pinned Elements we found...

Object Casting

I'm not sure if they still call it this in the books - but that's how I learned it. This would be used, for example if you had an "Element" from Revit, but you wanted to determine if it was a "Wall" so that you could get the wall-specific information from it.

There are a few mechanisms which support this kind of goal:

Code Example:

// Let's assume that I have "Element e" from one of our routines above, and we want to determine if it's a Wall, so that we can get the Wall width.

//option 1: direct casting

Wall myWall = (Wall)e; // cast "e" into a Wall.

// The down side of this approach? It throws an exception if "e" is not a wall. Which you could catch, but that's time consuming.

// option 2: testing first using the is

if (e is Wall) myWall = (Wall)e;

// this is OK as an approach... better than option 1 at least.

// option 3: using the AS keyword

Wall myWall = e as Wall;

// the benefit here? it casts it if it is the right type. If it's not? then myWall is NULL (which you'll need to test for).

All the methods described above have pros and cons in terms of writing the code and the performance of the application... So they're not meant to be instructive on either, so much as show you some possibilities.

I hope this will be useful to someone...

-Matt

Thursday, July 03, 2008

Speaking at AU on the Revit API

I (finally) got an invitation to speak at Autodesk University this year on the topic of the Revit API.

CP315-4: Getting Down to BIM: Advanced Revit API

I'd been planning to cover topics such as:

  • Essential Tools
  • Understanding Parameters in Depth
  • Filters: New Searching Mechanisms
  • The Challenges of Phases
  • Extracting Geometry
  • Spotlight on: Room Objects

But I've got some time where I can add or remove topics to cover... Are there other areas of interest out there? I'm sure that there will be a ton of other Revit API classes - particularly introductory and VSTA classes... So I'm interested in anything else people would be interested in hearing about.

I'm also interested in adding one topic of my own - an interactive discussion of "What kind of application are you interested in building?" - to try to answer people's questions about whether the application they're thinking about CAN be built using the API... But I'm not sure if this is the right place for that...

Any other suggestions?

-Matt

Monday, June 16, 2008

The Ribbon UI comes to Inventor


I was at the Autodesk Developer Network Manufacturing DevCamp last week, and one of the interesting things I saw was Autodesk's new Ribbon User Interface for Inventor.

While I haven't been wild about the AutoCAD 2009 Ribbon UI, I really like the way that they've implemented this for Inventor. Something about the way they organized it - and the way that you can still use the keyboard shortcuts works nicely. Also the way that you can easily drop into and out of sketch mode more transparently is nice. Perhaps it's because Inventor is fundamentally more structured in terms of contextual menus than AutoCAD (where you can really do any command at any time) - whereas in Inventor you're definitely in Part mode, Assembly mode and drawing mode (etc).

Why should we like Ribbons?
  • Ribbons group tasks together logically
  • Ribbons make obscure functions more "visible" - commands which are buried in menus and rarely see the light of day for regular users will be used more ("Discoverable", I think they call it).

Available Now

Rather than doing like AutoCAD, where it was released in the 2009 version (a suprise for those who weren't involved in the beta program) - the Inventor team is releasing a "Technology Preview" in the middle of the 2009 version.

You can "safely" sample the functionality and provide feedback by downloading the "extended version" of Inventor, which runs happily side-by-side with regular Inventor.

While they've done some work to have 3rd Party add-ins start working automatically (depending on how you've setup your add-in) - I anticipate that there will still be some amount of trouble on that front. The challenge will be - will customers like it so much that they'll use it in production (in which case the add-ins will have to be updated NOW to support production, rather than waiting for Inventor 2010).

In any case - I'm impressed with how well it's implemented. They obviously put a lot of thought into it.

Video:




Download

http://labs.autodesk.com/technologies/inventor2009_ui/

Tuesday, June 03, 2008

The 2009 Revit Utilities are (finally) posted

It was fun, last year, when we posted our free Revit Utilities for Revit 2008. We got nice press, and generally nice comments.

And then came 2009. It's not that it's hard to port applications over to Revit 2009 - it's straightforward, and if you're not doing too much geometry work I'd call it "cake".

But it's every thing else that needs to be taken care of - particularly because we wanted to have this release support both 2008 and 2009 with the new enhancements. So it's updates to installers, and keeping track of multiple DLLs, multiple registry keys, etc. Even that's not so bad.

The worst part is - trying to get something like this published when it's a free product, but you're buried in customer work. Whether it was developers or application engineers for testing or marketing people - it's tough to put down billable work and get it taken care of. Of course, the 5-10 e-mails I got per day requesting the timeline added a little motivation to my guilt.

Just to make things more complicated, we've been working on some other packaged Revit development ideas (which stole the remainder of our free time).

I usually like to have software available within 30 days of the release of the updated CAD version - so we fell short here (apologies). But here they are - published and enhanced for Revit 2008 & 2009 (all flavors).

  • Room Renumber
  • Door Mark Update
  • Change Case
  • Revit Content Browser (Revit City)
  • Earth Connector for Revit
Best Regards,
Matt

P.S. If you've got feedback, please send to devfeedback (at) avatech.com

Wednesday, March 05, 2008

Revit 2009 API: The AddIn Manager

One of the nice additions to the Revit 2009 SDK is the "AddIn Manager" tool.


As background, for those of you who don't know - Revit still uses a 1990s-era REVIT.INI file, with four lines per command to register your Revit external commands, ie:


ECCount=3
...
ECName3=Door Mark Update
ECDescription3=Revit Door Mark Update Utility
ECClassName3=DoorMarkUpdate.Command
ECAssembly3=C:\projects\Avatech\RevitUtilities\DoorMarkUpdate2009.dll


This, combined with the application startup time for Revit, contribute to some occasional pains in getting external commands set up (whether by developers or CAD Managers).

What's New?

The Add In Manager application is itself a Revit External Command, and is accessed (after installation) on the Tools + External Tools menu:





The AddIn Manager shows you what external commands have been registered with Revit, as well as giving you the ability to Load a new command at Runtime (NO MORE EXITING OUT!) and Saving changes to your REVIT.INI file.


Chuck Han had done something like this a year or so ago - but it was mainly for outside of Revit - not something that you could load into Revit after Revit had started. So this is a welcome addition - anything to make the process go more smoothly for Revit Users and administrators!


By the way, the AddIn Manager also handles External Applications:





-Matt

Revit 2009: The Hidden Feature

In previous years, I've really enjoyed ferretting out those "hidden" features or behaviors of Revit in each new release...

This year, I've been poking and prodding - but I've only managed to turn up one thing which I would call a "Hidden Feature".

Revit URL Support
I noticed as you mouse over files in the new Startup Screen, in the bottom left corner you see not the filename - but a URL:







This made me think - does this mean that Revit supports URLs for files now? That might be interesting...

So I tried it - Using "File + Open", I typed in a URL of a Revit File I posted on a website, i.e.:

http://jennmason.com/RevitTest.rvt

And sure enough - Revit automatically downloaded the file and opened it.

Where did it put it locally? It currently is put in your %TEMP% folder (a previous build was putting it in "My Documents" - I'm not sure of my preference).

What does this all mean? I'm not entirely sure, but as models proliferate over the web (or content - my presumption is that you can load a family this way as well) - that Revit being able to open any URL (HTTP, FILE, FTP, etc) - presents some interesting future opportuntities....

(Update: It appears that FTP does not really work... ah well).


Another interesting quirk - I notice that when you mouse-over the "New" button, it gives you a URL of:

file:///X:/NewProject.start

and the Open option gives you file:///X:/OpenProject.start.

I haven't delved into what's going on here... Is this some kind of HTML application that we're actually in? What happens if you actually have an X: drive?

Anyway - this hidden feature seems to inspire as many questions as answers... Have you discovered any "hidden features"? Drop a comment here and let people know!


-Matt

Thursday, February 28, 2008

Revit 2009 API: Parameter Improvements

As I've mentioned elsewhere, you can't overstate the importance of Parameters in the Revit API... It probably represents 40% of everything you can do, and it's integral in every application I can think of. So it's nice to see Autodesk continuing to try to improve it.

Background
In Revit, there are three kinds of parameters:

  • Built-In Parameters (there are some 2,272 of these in Revit 2009 - and you'd mostly recognize them from the properties dialogs for each element - but not all of them).
  • Project Parameters (created by the user, in the model).
  • Shared Parameters (created by the user, often by importing them from a shared parameter file - which can work across models)

From the API perspective, however, I'd say that there are only two - Built-in and not built-in parameters (there are some slight differences from the API between Project and Shared - but I'd call them minor for most usual purposes).

Parameter Access

If you were trying to get the value of a built-in parameter, it was pretty easy:

Parameter myWallHeight =
wallElement.get_Parameter( BuiltInParameters.WALL_USER_HEIGHT_PARAM );

Easy for built-in parameters. For non-built-in parameters, it's a different story. The only way to find the parameter was to iterate through the list of parameters in Element.Parameters and try to match on a Parameter.Definition.Name. It was noticeably slow if you were doing it across a whole model.

In 2009, two different improvements were introduced, with I believe the intent of improving the performance of parameter access:

The ParametersMap member of the element class has an array of all the "visible"** parameters on an element - and you're able to index one parameter out by name, for example:

Parameter myFireRating =
wallElement.ParametersMap.get_Item("MyFireRating");

conversely, you can get the same now by:

Parameter myFireRating =
wallElement.get_Parameter( "MyFireRating" );

I haven't wrapped my head around the advantages of the ParametersMap method - but I can tell you one of the advantages of the Element.get_Parameter( String paramName ) approach:

While all of the approaches are case-sensitive on the parameter name (so be careful), the Element.get_Parameter approach returns a NULL if there's no match - whereas the ParametersMap approach throws an Exception if there's no match.

TypeOfStorage

One tricky thing when you're trying to write something generic is anticipating what "data type" one of the 2,272 BuiltIn Parameters will be. You can't actually figure it out until you can find an element which HAS that parameter assigned to it. In 2009, Autodesk has added:

Document.TypeOfStorage( BuiltInParameter );

So you can just ask what the data type is for STAIRS_ATTR_BALUSTER_SPACING_TYPE (or any other obscure parameter) without needing to track down an actual usage of it.

It's forward progress.

One Last Little GUID...

One other small thing (although for a certain small number of you - this is absolutely critical). When you use a Shared Parameter File and create a parameter from it, it creates what is called a GUID for the parameter. For the un-initiated among you - that's programmer-speak for Globally-Unique-IDentifier - a random mix of letters and numbers which are statistically guaranteed to pretty much never ever happen again. It looks something like this:

{3F2504E0-4F89-11D3-9A0C-0305E82C3301}

the trick is, that the GUID lived in the shared parameter file, and when you imported the shared parameter file into the NEXT Revit model, your "MyFireRating" parameter would have the same GUID in both models. This is important - if you lost your Shared Parameter file, or if you just arbitrarily created another "MyFireRating" parameter in a second model - it was not the same parameter... It was a different parameter that happened to have the same name, but some bad things happened if you tried to schedule things, etc (this is extremely common in Revit Family Development - if you want the same parameter in all your families, it has to have the same GUID).

Sorry for all the backstory - here's the payoff. Prior to 2009, once you imported the parameter - the original GUID was hidden forever... If you lost your original file, you were done.

But thanks to a quiet little enhancement in 2009, you can now go into the ExternalDefinition of any shared parameter, and see the GUID property. So take heart! those of you who thought you'd have to remodel half your content because you lost your shared parameter file (because you didn't know you needed it) - you may still be saved!

-Matt

P.S. Speaking of Visible Parameters... That's a good post for another day. First, because it is possible to have "Invisible" shared parameters... but I was actually referring to another aspect. All the Parameters that are listed in the Parameters (or ParametersMap) collection - that's not really all of them, you know? There's more...........

Revit 2009 API: VSTA: Here Comes the Neighborhood

Historical Commentary (skip unless you're bored!)


It's strange to see, looking back, how the API grows in tandem with each product.


In the AutoCAD world, there was LISP pretty darn close to the beginning (I wasn't there - so I can't rattle off the exact version number it appeared like some of my compatriots can). And look AutoCAD now - there's LISP, VBA, ARX and AutoCAD.NET (and that's an over simplification as well as leaving out some of the more obscure APIs).


In Autodesk Inventor, the API (C++ and COM/VBA) came out around Inventor 5.0 (roughly?) - and has gone from under-powered to very powerful (dropping the C++ support along the way).


Revit went from no API to a Microsoft.NET API... A sort of "walled-garden" which somehow still seemed to exclude the masses of people who might be interested in automation.



Changes Ahead?


Well - all that is about it change - sort of. Revit 2009 introduces Microsoft VSTA - that's Visual Studio Tools for Applications - the next generation follow-on to VBA (Visual Basic for Applications).




Autodesk talks a lot about "democratizing technology" - and nothing has democratized programming like VBA (and LISP). It really enabled technically savvy people to experiment with programming in a friendly environment, which was tightly tied to the CAD system. VSTA should do the same thing - although it's got its differences.


But weren't there already free ways to...?


For a while, there was a price obstacle - if you wanted to develop for Revit, most people thought you needed to fork out $800-$1200 USD for Microsoft Visual Studio. While there were technically other low-cost options, it was a conceptual barrier as much as anything.


In 2005, Microsoft introduced the free "Express Edition" of Visual Studio, which enabled users to develop software without the upfront costs (with some limitations - like limited or no ability to debug things at runtime - an invaluable capability).


I would still argue, however, that there were significant hurdles there - whether it was getting Visual Studio loaded, or the arcane way that Revit external applications are included into Revit via a REVIT.INI file. VSTA will remove many of the logistical obstacles.


It's Like VBA!


VSTA (once installed - it's one of the "Additional Products" available on the Revit DVD) - enables you to write and run "Macros". You develop inside of the VSTA IDE (Integrated Development Environment) - a nice, light version of Visual Studio which provides Intellisense (where you just need to type the first letter or two and it offers you all the choices for what you were trying to do). Like VBA, you're able to step through or set breakpoints in your projects to debug them.


Also like VBA, the macros can be stored either externally or within a document. The document approach lets the code travel with your Revit model! There are some neat things that you can do with that (so long as you're not worried about your code getting away from you).




It's Not Like VBA!



Here's where things get different...


The language is not exactly like Visual Basic / VBA. You write your macros using your choice of either Visual Basic.NET or C# (pronounced C-Sharp).


While Visual Basic.NET is incrementally more challenging than VBA - the good news is that there are many books, courses, and online content to help you. The great part about including C# as well is that there is also a wealth of online content (as well as Revit SDK samples) in C# - and these samples can typically be pasted in with only minor modifications - so VSTA is not a "second-class citizen" as VBA sometimes was.


The Content is the Same...


One key thing to understand - it's all the same Revit API. With only minor differences, the API that is available in VSTA is exactly what is available to traditional Microsoft.NET developers for Revit applications - so there's very little holding you back.


Here Comes the Neighborhood


When anything gets "democratized" like this - there's an occasional sense of unease amongst the previous members of the exclusive club - that it's not quite as special now that everyone can do it. I personally am fighting this off - on the theory that this will accelerate the Revit API development going forward. The more users who are interested and aware of what the Revit API can do, the more attention Autodesk will pay to extending their capabilities.


Where to Get Started?


There are several areas to learn about to begin your quest:


- VSTA itself


- Visual Basic.NET or C# Language


- Revit API development (general)


VSTA - there have been some AU sessions on VSTA in the past, which you can access at AU Online if you attended those AUs. You can also visit the Microsoft VSTA developer center (although take note that Revit 2009 ships with VSTA 1.0 (which corresponds to Visual Studio 2005) - Microsoft is currently touting the forthcoming VSTA 2.0 / Visual Studio 2008).


Visual Basic.NET - There are probably hundreds of books and tens of thousands of online articles and other content... You have to pick what works for you.


Revit API development - You can download the Revit SDK from here. (although the 2009 link is not posted as of this writing). This will include samples (both traditional, as well as some VSTA). Finally, Autodesk Developer Network has published one of its DeveloperTV episodes on the same site to give you a brief overview of Revit development.


Online/In-Person classes - Avatech Solutions (who I work for) is considering providing online and in-person classes for people who want to learn to program Revit using VSTA. If you're interested in something like this, contact us at ( devfeedback (at) avat.com ).


In closing


To all you VBA developers or otherwise talented tinkerers - welcome to the world of Revit development!


-Matt







Revit 2009 API: New Creationism

In the beginning, there was the API - and you could create virtually nothing. Then came the basic elements, then the structural elements... Release by release, Autodesk is slowly making progress to the point where you can make a wide variety of elements through the API.

Every year people want to know - "what new element types can I create that I couldn't create in the past?".



What's Newly Possible to Create in 2009?


  • Area

  • AreaViewPlan

  • AreaTag

  • AreaBoundaryLine

  • Space (MEP)

  • SpaceTag

  • SpaceBoundaryLine

  • RoomBoundaryLine

  • CurtainSystem

  • ExtrusionRoof

  • FootPrintRoof

  • Gutter

  • Fascia

  • FoundationWall

  • Electrical System (MEP)

  • SlabEdge

  • SpotCoordinate

  • SpotElevation

  • Truss

  • Zone (MEP)

  • Wire (MEP)

So that's a good set of new elements, right?

While it's not necessarily enough to generate an entire design from scratch, I've always been of the opinion that with a system like Revit you're better off with the "template" approach for "end-to-end" automation anyway.

There's definitely enough there to make some intelligent tools to automate specific aspects of the design.


Batch Creation


If you tried creating a large number of elements in 2008 or before, you may have noticed that it was rather, well, slow. Avatech once tried to automate a point cloud into Revit 2008 - and I think the application is still running many months later :). Autodesk improved on this during 2008 with the introduction of a SuspendUpdate object, which addressed part of the problem (the problem that Autodesk was fully updating the Revit model after each element was created). This was improved again in 2008 SP2.


In 2009, Autodesk has gone down a different path to help with performance. They have introduced a number of new methods which can batch create a variety of specific types of elements.
  • Family Instances

  • Rooms

  • Spaces

  • Text Notes

  • Walls (Profiled or Rectangular).

The new methods take a List of data to create each element.


For example, the NewRooms() method looks like this:


List<Autodesk.Revit.Creation.RoomCreationData> roomData =
new List<Autodesk.Revit.Creation.RoomCreationData>();

// get the current view's level
Level myLevel = doc.ActiveView.GenLevel;

// create arbitrary rooms at 10 foot intervals
// (I hope there are walls there to separate!).


for (int i=0; i < color="#3366ff">Autodesk.Revit.Creation.RoomCreationData
(myLevel, new UV(i * 10.0, 0))
);
}


ElementSet rooms = doc.Create.NewRooms( roomData );


//////////////////////////


All in all, there's some good additions to Revit's creation-ability.


-Matt


Revit 2009 API: Rooms for Improvement

Whether you're working in pure architectural development, or particularly if you're involved in doing energy analysis work - Room objects are VERY, VERY important.


The 2009 API provides a variety of modest enhancements to rooms which improve what you can do with rooms and their related objects:


Room.ClosedShell



If you've ever wanted to get a better handle on the analytical geometry of a room than you could get with just the room boundaries (sloped ceilings, anyone?).




The 2009 API adds support for getting the ClosedShell geometry of a room. This geometry is much like getting the solid geometry of an element - it returns something that behaves like an Autodesk.Geometry.Solid - it has faces and edges that you can traverse.



PlanCircuits are Working...




2008 added support for a concept that it took me a long time to get my arms around (thanks to limited documentation, nudge, nudge). A document has a collection of "PlanTopologies" - one for every combination of Level and Phase (i.e. "Level 1, New Construction"). For each PlanTopology there are a number of openings defined by the walls where rooms might exist. Each opening is called a "PlanCircuit" - while you can't find out as much as you might like about a PlanCircuit (the area, the number of sides, etc).


Anyway - there was a property for 2008 called PlanCircuit.IsRoomLocated - which could tell you if a room existed... That said, from the time I tried it in mid 2008 until the 2009 alpha - it never worked. In fact, it threw an exception if you even tried to touch it.


Now it's working - and you can use it for a variety of things - mostly determining if there are rooms placed in all of the openings that there should be. There's even a NewRoom() method which takes a PlanCircuit as an input.


Tagging Is Improved



When room tagging was added in 2008 - it worked great - as long as you only had one view of a given Level/Phase. This was remedied in 2008 SP3 with a NewRoomTag() method where you can specify which view the tag should reside in - that said, bad things happened if you tried to build with SP3 and try that method in 2008 SP2 or lower - so it's nicer now that it's in a General Availability version of the Revit Software.


From Room / To Room



I've heard a variety of people complaining to me about the nature of the From Room / To Room in 2009. If you're not familiar with it - when a door (or window for that matter) is placed it immediately gets a From Room and To Room designation. This is usually based upon its initial orientation (which room it opens into) - however, it never appears to change (even if you flip the door direction).


One of the Revit Product Managers told me that it has historical roots in the lockset and which side that goes to - but I'm sure that was cold comfort to people who just wanted it to be based on the direction that it opens.


While the underlying behavior has not changed - it is now possible to programmatically change the From/To Room. We'll probably add this to our "Door Mark Update" utility in 2009.



Room.UnPlace()

It's now possible to "unplace" a room - which moves the room into an unplaced state (similar to adding new rooms via the schedule which have not been placed yet). The Rooms can be placed into another spot based on X,Y location or PlanCircuit.


Interactive Change


While this isn't an API change - it is something I very much appreciate. If you wanted to understand the room height, the best trick was usually to create a Section view - then turn on visibility of Rooms, as well as Room -> Interior Fills and References. The problem in 2008 was that while you could see them perfectly - you couldn't pick or otherwise change them.


In 2009, you can not only pick the rooms in Section View, you can take an drag the height of the room to a new level.


Base Level Offset

This is both an interactive aspect and an API aspect - in the past there was only a height offset from the "upper level". Now there is both an "upper level" offset and "lower level offset".


Calculation Settings


Another nice thing if you're doing Energy or MEP calculations - you can now programmatically set the Room Volume Calculation Settings (Areas or Volumes, as well as the wall boundary option). This is identical to the Settings -> Room and Area Calculations dialog box.


Whew!


While there are few earth-shaking things in here - there's a lot of incremental progress... and for people in the right functional areas, it's huge.


-Matt

Revit 2009 API: Searching Improves

One of the areas which is nice to see Autodesk's continuing investments in is Searching within a Revit model.

Searching is a fundamental activity - almost every Revit application that exists, whether it's just to look up a symbol or whether it's a full-blown analysis application needs to scan the model looking for specific elements.

There were already a few different methods of searching within the model - GuyR and I had a spirited discussion about them recently on the AUGI board.... and Guy developed a test application to perform a speed test of the three ways...

The test involves scanning an aribitary Revit model looking for either Walls or Walls and Rooms, using all the different methods available.

In Revit 2008, these were the results:



































Case 1Case 2










  • Bad: Iterating through each element - testing for the category to match
  • Better: Testing the .NET Type of each element, looking for the right ones.

  • MyBest: (Guy's Best): The same as better - but don't even cast down to a Revit Element to save some cycles.

  • ElementFilterIterator: Use the get_Elements( type ) method to get all the elements in one call.

While I have historically preferred the ElementFilterIterator approach, Guy's method is faster - particularly if you're looking for more than one type. If you are looking for more than one type (as shown in case #2 - in Guy's method you only have to iterate through once - whereas ElementFilterIterator is almost twice as slow). ElementFilterIterator also has another quirk - it does not handle subclass types - so if you ask for "View", you're not going to get "View3D" or "ViewSheet"...

Important Note: As a side note on a pure "Category" approach - remember that asking for Walls will give you both "Walls" and "Wall Styles"... So I think it's likely that you'll almost always need to screen by "Type", not just by "Category".

2009 Rolls in...

So when 2009 came across my desk, I was curious to see what had changed. Autodesk had promised some performance enhancements to searching - what form would they take? I modified Guy's application to support the two new searching mechanisms - and I figured that we'd re-test the others, because it was said that they could improve as well.

The new Filtering mechanisms

Revit 2009 introduces the concept of "filters" which can be used to define the criteria for finding elements - this includes searching by:

  • Category
  • Type
  • Family
  • InstanceUsage
  • Material
  • Parameter Value
  • Structural Type
  • Symbol
  • Wall Usage

What's more, you can combine filters using the LogicAND, LogicNOT, and LogicOR filters. So you could, with one call, look for Doors made of a particular material (OK, Material is a tricky one - perhaps that's a bad example).

What does it look like?

// get the categories

Category _wallCat = _doc.Settings.Categories.get_Item( BuiltInCategory.OST_Walls );
Category _roomCat = _doc.Settings.Categories.get_Item( BuiltInCategory.OST_Rooms );


//make the filter
CategoryFilter wallFilter = _app.Create.Filter.NewCategoryFilter(_wallCat);
CategoryFilter roomFilter = _app.Create.Filter.NewCategoryFilter(_roomCat);

// put the filters together
Filter myFilter =
_app.Create.Filter.NewLogicOrFilter(wallFilter, roomFilter);

ElementIterator esi = _document.get_Elements(myFilter);

So how did things turn out in 2009?

































Case 1Case 2







So what has changed?

Strangely - Guy's best approach consistently comes up slightly slower than his "better" approach - that I can't explain. The ElementFilterIterator approach performs about the same - even though it has been significantly changed - it now uses an ElementIterator instead, and it supports SubTypes.

The most interesting changes are for the new mechanisms - Filter Criteria based searching. While we didn't explore all of them - we can see that:


  • Type-based searching was roughtly the same as the ElementFilterIterator approach

  • The Category search absolutely SMOKED everything else - particularly when looking for two categorys (walls and rooms).

Summary

All in all, there are some mechanism that are still fast - but if performance is a concern, you'll definitely want to check out the new Filter approach to getting elements.

I'll try to post the updated sourcecode for this shortly so that you can try it out for yourself.


WARNING:


Your mileage may vary. There seemed to be a great deal of variations in the runs each time they were run.

Revit 2009 API: What's New?

Welcome to another fun episode of discovering what's new in the Revit API. The 2009 edition presents us with a long, long list of enhancements - and while most of people's long-standing complaints have not been addressed - there's certainly something in there that will make you happy individually.

This is the first of a variety of postings I'll write on the API and what's new in 2009. In the other articles, I'll go into further detail... in this one, I'll summarize the highlights - as well as cover some of the features that don't fall neatly into one of the other articles.

Some of the topics we'll cover are:

Beyond those in-depth topics, you can look forward to:

Printer/Paper Settings


The 2008 API introduced printing capabilities, which was great - however, they didn't have time to get the printer settings/paper settings in - so you could only print to whatever the default settings were... making this not so useful in practice.

2009 adds full support for Printers and Paper Sizes - almost every option on the Print Dialog is supported - and special support is offered for virtual printers (like DWF and PDF).

Exporting


While 2008 introduced DWF and DWG export support, 2009 introduces support for export of GBXML (for Green Building Studio, and others) and FBX (for 3DSMax - and others)- both with a good list of options available during export.

IsModified


You can now determine if a given document has been modified since it was last saved (useful if you're writing a Data Management system, or if you just want to know if you need to save before you exit).

External Applications


It is now possible to see, from the application level, all of the registered applications inside of Revit. While it's hard for me to imagine what you can use it for beyond writing an "Add-In Manager" - I'm sure there's something...

Selection StatusPrompt

If you tried adding selection to one of your applications - well, let's just say it wasn't very "smooth" as User Interfaces go. A good step in the right direction is the new Document.Selection.StatusBarTip property, which lets you put text which appears in the status bar (as well as a tooltip on the mouse - just like regular Revit!). This makes it a little easier to tell people what you want them to select (or how they "get out of it" - hint: click on Nothing).

Summary


All in all, there's a lot to wrap your head around - Come back for more details as the months progress...


-Matt

Let the floodgates open...

I have received clearance to start talking about the Revit API in 2009 - my wait is over!

I'll start posting the pieces that I've got queued up now, and there's a few more to finish - there's a lot to talk about.

-Matt

Thursday, February 21, 2008

Argh. I don't understand the rules!

Todd wrote:
"Time to get another post up there buddy. I'm waiting to hear exciting news about customizing Revit 2009. "

This is my favorite time of year. The new product release season is when I have the most interesting stuff to say about what's coming in the next release - and what it means for you.

That said - there is an aspect of this which always drives me bananas - timing. Depending on what you read and who you ask, I am allowed to start talking about the 2009 products somewhere between February 12th and April 2nd - with potential penalties if I talk too early.

February 12th - Autodesk's World Press Day, where they publicize the products.
March 25th - Marketing Launch Day (where resellers and ISVs are supposed to be able to do outbound marketing communication about 2009 - prior to that, you're only supposed to be responding to inbound queries...)

Autodesk Developer Network publishes one set of guidelines - the beta testing agreement says something else entirely about the dates where you can discuss it, and when I ping Product Managers directly on the topic - it all seems different.

It's obvious that the world has changed though - people started blogging about all the new features instantly... Maybe that's OK? Maybe that's just how the world works today in the blog-centric world... But as someone who would prefer not to be shut out of future beta testing - it's frustrating to be told "wait until April 2nd"... At the same time, no one that I talk to seems sure - so it's all still being worked out.

So anyway - I've got a raft of posts all queued up and ready to go - but I'm waiting for the go ahead to be able to post them...

-Matt