This is Jeremy Tammik's Typepad Profile.
Join Typepad and start following Jeremy Tammik's activity
Join Now!
Already a member? Sign In
Jeremy Tammik
Switzerland
Interests: rock climbing
Recent Activity
We make further enhancements to the on-going project to determine gross and net areas and volumes, obviously a fundamental issue to BIM. And I have more news to share as well: Playing with my WebGL viewer WebGL Developers meetup in... Continue reading
Posted 2 days ago at The Building Coder
Dear Jordi, I am very glad it works for you now! Thank you for your appreciation! I will do my best. Have you checked out my new, second, blog yet? http://the3dwebcoder.typepad.com I hope that is of interest to you as well! Cheers, Jeremy
1 reply
:-)
1 reply
Dear Arnošt, Thank you very much for the warning! For my purposes, just viewing with zero precision or fidelity requirements, I am perfectly happy with this. For all other uses, take heed, my friends! Cheers, Jeremy.
1 reply
Dear Dale, Look here now: http://thebuildingcoder.typepad.com/blog/2015/04/exporting-3d-element-geometry-to-a-webgl-viewer.html Did I promise too much? More coming :-) Cheers, Jeremy.
Toggle Commented 5 days ago on WebGL 101 – Getting Started at The 3D Web Coder
Image
Yesterday, I discussed how to get started with WebGL and demonstrated a simple 3D viewer making use of the Tiny WebGL helper Library TWGL. Today, I present the TwglExport Revit add-in to select an individual element and populate the viewer... Continue reading
Posted 5 days ago at The Building Coder
Dear Jordi, In theory, it might be ever so slightly more efficient to use this instead: Line axeX = Line.CreateBound( XYZ.Zero, XYZ.BasisX ); Line axeY = Line.CreateBound( XYZ.Zero, XYZ.BasisY ); Line axeZ = Line.CreateBound( XYZ.Zero, XYZ.BasisZ ); The last one, axeZ, is the one I was thinking of, yes. Glad to hear you have found a solution. Yup, if you are working with very large coordinates, it will indeed often help to move the whole problem closer to the origin. Cheers, Jeremy.
1 reply
Dear Madhu, I have not the slightest idea what macro you are talking about, so I cannot help with that. Are you aware of the AvoidObstruction SDK sample? That is of course not a macro, but an add-in. It is discussed in numerous earlier posts on The Building Coder and its implementation is explained in its readme file ReadMe_AvoidObstruction.rtf. Cheers, Jeremy.
1 reply
Dear Håkon, I raised an issue for your suggestions: https://github.com/jeremytammik/SpatialElementGeometryCalculator/issues/1 Cheers, Jeremy.
1 reply
Dear Geert, I hope and believe that the SpatialElementGeometryCalculator class can answer all of the questions you raise. Can you please take a look at the following much more recent discussion and let us know whether that helps solve them and addresses all your needs? http://thebuildingcoder.typepad.com/blog/2015/03/findinserts-retrieves-all-openings-in-all-wall-types.html e553e16897883301b7c7789a82970b Please also note the relevant additional questions raised and addressed there in the comment by Håkon Clausen. I hope this helps. Cheers, Jeremy.
Toggle Commented 5 days ago on Room and Wall Adjacency at The Building Coder
1 reply
Dear Håkon, Those sound like two absolutely valid points, and your solution to fix them looks very promising to me. I see that you added some other functionality that you do not explicitly mention, such as a dictionary of the affected walls. Could you possibly fork the SpatialElementGeometryCalculator GitHub repository, add your changes to that, and create a pull request for me to merge them back in to take a closer look at? https://github.com/jeremytammik/SpatialElementGeometryCalculator I think your improvements are very important and will be of great interest to others as well. Thank you! Cheers, Jeremy.
1 reply
Image
Alexander Ignatovich, Александр Игнатович, of Investicionnaya Venchurnaya Companiya, took another and deeper look at The Building Coder sample external command CmdWallProfile that I originally implemented in 2008 to retrieve the wall elevation profile and my colleague Katsuaki Takamizawa modified to... Continue reading
Posted Apr 10, 2015 at The Building Coder
Image
Yesterday, I implemented and published a simple Node.js web server to display an SVG polygon. In that post, you can define the polygon path manually in a text box and invoke the web server by clicking a button. Obviously, the... Continue reading
Posted Apr 9, 2015 at The Building Coder
Image
Lots of stuff going on; I have a hard time keeping up. Due to popular request, I updated the RvtVa3c readme. I am continuing to answer issues on the Revit API discussion forum as well as ADN cases. I am... Continue reading
Posted Apr 8, 2015 at The Building Coder
Dear Matt, I am very glad to hear it! Thank you for letting us know. Cheers, Jeremy.
Toggle Commented Apr 7, 2015 on List All Import Instances at The Building Coder
1 reply
Dear Jordi, Wow, how nice, luck you. I love Brittany! You are forced to specify a rotation axis when you call the ElementTransformUtils.RotateElements method. That axis will always determine the axis of rotation, including the center point of the rotation, so it should give you absolutely all you need. What axis are you specifying? To rotate in the XY plane around the origin, you can use a line from the origin, (0,0,0) = XYZ.Zero, to an arbitrary point on the Z axis, e.g. (0,0,1) = XYZ.BasisZ. Cheers, Jeremy.
1 reply
Dear Locost7, The StructuralConnectionType element id is probably not generated randomly. Instead, I imagine that Revit is generating a new StructuralConnectionType element for you, and that is its element id. You can check this by using the element lister: http://thebuildingcoder.typepad.com/blog/2014/09/debugging-and-maintaining-the-image-relationship.html#2 You can also simply snoop the current database in RevitLookup and manually check whether a new StructuralConnectionType element has been added. If the newly generated StructuralConnectionType element is identical to another StructuralConnectionType element that you already have in your project and would like to reuse, you can probably do so through the following steps: 1. Make a note of the newly generated element id X. 2. Determine the element id Y of the StructuralConnectionType that you would like to reuse for your new moment connection type Z. 3. Assign Y to Z, e.g. using the Element.ChangeTypeId method. 4. Delete X, e.g. using the Document.Delete method. I hope this helps. Please let us know how you end up solving this. Thank you! Cheers, Jeremy.
Toggle Commented Apr 7, 2015 on ElementId Parameter Value at The Building Coder
1 reply
Image
I hope you had a wonderful time over Easter. I returned from my team meeting and subsequent brief holiday in the snow and am confronted with a long list of unanswered Revit API discussion forum issues. I answered a dozen... Continue reading
Posted Apr 7, 2015 at The Building Coder
Image
Here is an illuminating explanation by Arnošt Löbel and Martin Schmid on some Revit API development trends that have already been underway for a couple of releases. Before I get to them, a quick report from our ADN team meeting:... Continue reading
Posted Apr 2, 2015 at The Building Coder
Image
Have you ever wondered whether you have any duplicate imported CAD instances in your model? My colleague Nikolay Shulga from the Revit development team implemented a nice little end user utility to answer this question. By the way, Nikolay and... Continue reading
Posted Apr 1, 2015 at The Building Coder
Dear Modar, Please be aware that a Revit element may display completely differently in different views, e.g. plan, elevation, 3D, section, etc. The bounding box has to include the extents of all possible views. If you wish to obtain more accurate limits on the element extents, you might retrieve, parse and tessellate the 3D geometry and calculate the maximum and minimum points of all the vertices produced. The concrete setout points add-in shows how to determine all geometry vertices: http://thebuildingcoder.typepad.com/blog/2014/11/concrete-setout-points-for-revit-structure-2015.html I implemented a whole bunch of utility classes and methods to retrieve and sort unique vertices from element geometry here in the past. This discussion mentions a few of them: http://thebuildingcoder.typepad.com/blog/2012/03/melbourne-day-two.html#2 I hope this helps. Cheers, Jeremy.
1 reply
Image
The placement of family instances can sometimes be a tricky topic in the Revit API. Programmatically, this is always achieved using the NewFamilyInstance method. However, this method provides 13 different overloads to choose from, which can be a non-trivial task:... Continue reading
Posted Mar 31, 2015 at The Building Coder
Dear Vilo, Right you are. Well, well... Thank you for the clarification! Cheers, Jeremy.
1 reply
Dear Ammar, 1. Check in the Visual Studio debugger what type your variable 'elm' really has. That may clarify a lot. 2. No need to submit to ADN. Submitting to the Revit API discussion forum achieves exactly the same thing. Unsolved ADN member requests are automatically escalated to ADN after a little while. Cheers, Jeremy.
1 reply
Dear Dave, Thank you for your comments, which I will reinterpret as constructive questions that raise interesting issues which help illustrate some API design principles and future trends important and worthwhile understanding. I asked Arnošt Löbel for an in-depth explanation, and he replies: Boy, is that a loaded question of what? Where do I start? I am afraid I cannot give a satisfactory answer and be brief at the same time. I’ll try to answer in stages for that very reason. A) Very brief explanation We tend to use functions which take or return element Ids rather then element objects because: It’s faster It’s safer It’s consistent and ties directly to what Revit does internally B) Detailed and boring explanation When we originally exposed the API (2005?), there was no direct link between the API and internal Revit code. That had turned out to be a maintenance nightmare. As the API has developed from tiny to large and huge we have realised we simply cannot maintain two parallel hierarchies. That’s why we have developed a framework which allows us to generate the public API directly from the internal native code. Now, basically, what we Revit programmers see, the API programmer gets. Sometime we add certain public method for the API programmer’s convenience, but the majority of the API is pretty much a mirror of Revit internal classes and interfaces. This applies both to the case of methods using Ids as well as the originally used element creating factories. For the latter, it’s very straightforward: We simply do not have such factories internally and we would not like having them. We believe that element creation is easier when it lives with the element class itself. It is also discoverable better that way. As for the element Ids - it has been part of Revit coding standard pretty much since ever. I mentioned that the main reasons are safety and speed. We often can do with just element Ids because that allows us to use elements without loading them to memory. For example, if I am looking for certain kind of a view, I can quickly get a list of their Ids, test what they are without expanding them (this is a fast test), and then only get the view I need. That mean I would be expanding one potential element only instead of, say, some hundred of view elements. The safety aspect has to do with the fact that element objects can become inaccessible when deleted (naturally) or undone or redone. Such operations are not always obvious or visible to the internal programmer who holds a pointer to an element, which leads to very undesirable problem of dangling, invalid pointers. If the programmer uses the element's Id instead, however, then operations on the element are safe. All the programmer needs to do is to test if the element obtained for the given Id is NULL or not. Yes, it is somehow less convenient, but it is incomparably safer with almost no performance penalty. We have made internal element lookup so fast, that it is practically instant. C) The case of Pipe creation On top of the above explanation, there is more about this API that perhaps deserves further explanation. I would need to talk to the MEP team to be certain, but I have seen the pattern in other APIs, thus I assume my guess will be very close to what the MEP folks would tell me. The changes the user see in 2015 are due to our continuing effort to separate Revit UI layer from the underlying model, to which we typically refer to as Revit DB. Without going into great details, the separation between those two should be such that the DB does not know about the UI, while the UI can know about the DB. Makes sense? So, even though it is not apparent when looking at the original pre-2015 pipe creation, the method (which is obviously a DB method) used to reach out to the UI layer to fetch the current type a pipe would be created with if the creation started via the UI. That, for us, is no longer acceptable and it is not how Revit works internally. The original pipe-creation method did what it did because it was written manually and did nor reflect Revit internals. With our effort of tying the API tightly with Revit internals, such approach is no longer possible. The API programmer now needs to do what Revit programmers do too, which is: If there is UI, find out via the UI interface what the current type is and use that. If UI is not accessible (for whatever reason), the programmer simply must know what type is to be used. I hope my answers are satisfactory. I realise they are not the briefest, but I tried my best. Many thanks to Arnošt for his detailed explanation! I hope this helps. Cheers, Jeremy.
1 reply