Home > The CATIA Object Model > Measuring Mass and Inertia

Measuring Mass and Inertia

October 27, 2010 Leave a comment Go to comments

You have probably used the Inertia measure function in CATIA to get mass and inertia measures but did you know that you can automate those measurements as well?  The inertia object that you may use in your programs works just like the interactive command and provides all the same capabilities you are used to.  In this article, I will show how to program with the inertia object and as usual I will provide sample code and some handy reusable functions.

What is not covered in this article

Before we get started, I want to point out that this article is meant to show you how to program mass and inertia measurements.  I will not explain what inertia is or what the various values mean.  There are plenty of engineering resources out there to do that.  Also, the inertia measure can give strange or even incorrect results depending on how you use it.  However, these behaviors are exactly the same when you program the measures as when you perform the interactively so be sure to take some time and understand how the tool works.  Below I quickly listed a few of the things that can affect the result (this is not a complete list):

  • Whether or not a material is applied in the part
  • Where the material is applied in the part
  • Whether the part is visualization mode vs. design mode
  • Whether an individual feature or a body/geometrical set is measured
  • Proper use of surfacic mass in the case of a surface measurement

A quick caution about the future availability of some API’s

Some of the techniques that I will show in this article have special notes in the help documentation stating that they will be deprecated in a future release.  However, the documentation has said that for a long time.  For now, I confirmed that they work in V5R18 and V5R20 but you should still take this into consideration because it could potentially render your program useless in the future.  Specifically, the API that I am referring to is the Inertias object.  This object is used to get inertia information from specific objects within a CATPart as opposed to measuring the entire CATPart.

What information does the Inertia object provide?

The values you are able to measure are listed below along with their units.

Property Units
Mass kg
Density kg/m3 (solid/volume)  kg/m2 (surface)
Position of the center of gravity m
Inertia matrix kgm2
Principal axes kgm2
Principal moments kgm2

Measuring a part or product as a whole

CATIA V5 allows you to measure the inertia of a single part or a product.  In the case of a product, a single set of values are returned that reflect all of the child parts at all levels below that product in the assembly.  This means there is no need to individually measure all of the child parts.

Here is a handy reusable function that will retrieve an Inertia object for a product.

Function GetProductInertia(ByRef iProd As Product) As Inertia

  'If successful, this function will return an inertia object
  'Otherwise, Nothing is returned (you should check the return value)

  Dim objInertia As Inertia

  On Error Resume Next

  Set objInertia = iProd.ReferenceProduct.GetTechnologicalObject("Inertia")
  If Err.Number = 0 Then
    Set GetProductInertia = objInertia
  Else
    Set GetProductInertia = Nothing
End If

End Function

Now lets look at how to use this function in an assembly.  In the example below, you should select any product or part instance in the assembly then run this code.

Sub Test_GetProductInertia_AssyExample()

  'Select a product first, then run this sub.

  Dim objProd As Product

  Set objProd = CATIA.ActiveDocument.Selection.Item2(1).Value
  Set objInertia = GetProductInertia(objProd)
  If Not (objInertia Is Nothing) Then
    'Retrieve the mass just to show it worked
    MsgBox objInertia.Mass
  Else
    MsgBox "The Inertia could not be retrieved!"
  End If

End Sub

You can actually use the same function when a part is open in it’s own window.  You are probably thinking that is no product to reference when the part is open in it’s own window!  Not true!  Every part always has a reference product associated with it that you just don’t see when it is open in its own window. That reference product is used to create an instance when that part is inserted into a product.  So all we need to do is access it and pass it to our handy function.

Sub Test_GetProductInertia_PartInOwnWindowExample()

  Set objProd = CATIA.ActiveDocument.Product
  Set objInertia = GetProductInertia(objProd)
  If Not (objInertia Is Nothing) Then
    'Retrieve the mass just to show it worked
    MsgBox objInertia.Mass
  Else
    MsgBox "The Inertia could not be retrieved!"
  End If

End Sub

Measuring geometry inside a part

Before covering this technique, I just want to again mention that the ability to retrieve an Inertia object on a specific item within a part is made possible by the Inertias object.  This currently works fine through V5R20 but the help documentation states that it is going to be deprecated in a future release so beware.

The help documentation really does not give you any indication of what types of objects within a part can be measured.  Because of this, the common belief out there is that you just can’t measure the inertia of specific geometry inside a part.  Like many, I was stumped as well until I did a project where I needed this functionality so I did a LOT of trial and error and figured out how it works.

What I found is that you can only measure the inertia of a body or a geometrical set.  If you pass any other kind of geometry to create an Inertia object, it will fail.  Measuring the inertia of a body makes perfect sense because the body really encompasses the complete shape of that solid.  However, measuring the inertia of a geometrical set probably doesn’t make a whole lot of sense unless that set only contains one surface.  Sometimes that may be the case but what kind of work around can we create to measure a specific surface?  I developed a solution for that.  I have to admit it is not very elegant, but it works like a charm.  Below, I will tackle each of these cases individually.

Measuring the inertia of a body

This case is very straightforward and easy.  As always, I like to develop reusable functions so I built one to retrieve the inertia of a body as shown below.

Function GetBodyInertia(ByRef iPart As Part, ByRef iBody As Body) As Inertia

  'If successful, this function will return an inertia object

  Dim objSPAWorkbench As Workbench
  Dim objInertia As Inertia

  On Error Resume Next

  Set objSPAWorkbench = iPart.Parent.GetWorkbench("SPAWorkbench")
  Set objInertia = objSPAWorkbench.Inertias.Add(iBody)
  If Err.Number = 0 Then
    Set GetBodyInertia = objInertia
  Else
    Set GetBodyInertia = Nothing
  End If

End Function

Now let’s look at an example use case.  In this example, I assume a part is open in it’s own window and the main PartBody contains some solid geometry.

Sub Test_GetBodyInertia()

  'Assume a part is open in it's own window
  'We will get the inertia of the main PartBody

  Dim objPart As Part
  Dim objBody As Body
  Dim objInertia As Inertia

  Set objPart = CATIA.ActiveDocument.Part
  Set objBody = objPart.MainBody
  Set objInertia = GetBodyInertia(objPart, objBody)

  If Not (objInertia Is Nothing) Then
    'Retrieve the mass just to show it worked
    MsgBox objInertia.Mass
  Else
    MsgBox "The Inertia could not be retrieved!"
  End If

End Sub

Measuring the inertia of a geometrical set

This case is almost identical to the case for a body listed above.  Again, I have developed a reusable function as shown below.

Function GetGeoSetInertia(ByRef iPart As Part, _
                           ByRef iGeoSet As HybridBody) As Inertia

  'If successful, this function will return an inertia object

  Dim objSPAWorkbench As Workbench
  Dim objInertia As Inertia

  On Error Resume Next

  Set objSPAWorkbench = iPart.Parent.GetWorkbench("SPAWorkbench")
  Set objInertia = objSPAWorkbench.Inertias.Add(iGeoSet)

  If Err.Number = 0 Then
    Set GetGeoSetInertia = objInertia
  Else
    Set GetGeoSetInertia = Nothing
  End If

End Function

Now let’s look at an example use case.  In this example, I assume a part is open in it’s own window and I will retrieve the inertia of the first geometrical set (make sure it has some surface data in it).

Sub Test_GetGeoSetInertia()

  'Assume a part is open in it's own window
  'We will get the inertia of the first geometrical set in the part

  Dim objPart As Part
  Dim objGeoSet As HybridBody
  Dim objInertia As Inertia

  Set objPart = CATIA.ActiveDocument.Part
  Set objGeoSet = objPart.HybridBodies.Item(1)

  Set objInertia = GetGeoSetInertia(objPart, objGeoSet)
  If Not (objInertia Is Nothing) Then
    'Retrieve the mass just to show it worked
    MsgBox objInertia.Mass
  Else
    MsgBox "The Inertia could not be retrieved!"
  End If

End Sub

Measuring the inertia of a specific surface

As I mentioned earlier, you can only measure the inertia of a body or geometrical set so I had to improvise a bit and create a workaround here.  This certainly is not beautiful but it works quite well.  Essentially, you just pass the surface to be measured and I create a temporary geometrical set in the part then create a join of that surface in that temporary geometrical set.  This way, there is only one surface in the set and the calculations will be correct (as always, you should confirm/set the material density being used as well – see discussion later in this article).

Function GetSurfInertia(ByRef iPart As Part, ByRef iSurf As HybridShape, _
                          ByRef oGeoSet As HybridBody) As Inertia

  'If successful, this function will return an inertia object
  'iSurf must be a surface
  'oGeoSet is the temp geo set that is created by this function (returned thru the variable passed in)
  'This geo set cannot be deleted until you are done with the inertia object or else calls to the 
  'Inertia object will fail.  You should delete the temp geo set at that point

  Dim objRef As Reference
  Dim intType As Integer
  Dim objHB As HybridBody
  Dim objJoin As HybridShapeAssemble
  Dim objSPAWorkbench As Workbench
  Dim objInertia As Inertia

  'Make sure some geometry was passed in
  If Not (iSurf Is Nothing) Then

    'Ensure the HybridShape is in fact a surface
    Set objRef = iPart.CreateReferenceFromObject(iSurf)
    intType = iPart.HybridShapeFactory.GetGeometricalFeatureType(objRef)

    If intType = 5 Then  '5=surface

      'Create a new geo set in the part and a join of the surf
      Set objHB = iPart.HybridBodies.Add
      objHB.Name = "Temp_ForInertiaMeasure"

      'Create a join of the surface
      Set objJoin = iPart.HybridShapeFactory.AddNewJoin(objRef, objRef)
      objJoin.RemoveElement 2
      iPart.UpdateObject objJoin

      'Append the join to the temp geo set
      objHB.AppendHybridShape objJoin

      'Create an inertia object from the temp geo set
      On Error Resume Next
      Set objSPAWorkbench = iPart.Parent.GetWorkbench("SPAWorkbench")
      Set objInertia = objSPAWorkbench.Inertias.Add(objHB)
      If Err.Number = 0 Then

        'Return the Inertia object
        Set GetSurfInertia = objInertia

        'Return the geo set that was created
        Set oGeoSet = objHB

        Exit Function

      End If

    End If

  End If

  'If got to here it failed so just return nothing
  Set GetSurfInertia = Nothing

End Function

Now let’s look at an example use case.  In this example, I assume a part is open in it’s own window and I simply search for all surfaces in the part and retrieve an inertia object for the first one found.

Sub Test_GetSurfInertia()

  'Assume a part is open in it's own window
  'We will get the inertia of the first surface found in the first geometrical set

  Dim objSurf As HybridShape
  Dim objPart As Part
  Dim objGeoSet As HybridBody
  Dim objInertia As Inertia

  'Get the surface then retrieve it's inertia 
  Set objSurf = objSel.Item2(1).Value
  Set objPart = CATIA.ActiveDocument.Part
  Set objInertia = GetSurfInertia(objPart, objSurf, objGeoSet)

  'If an Inertia object was returned, get the mass
  If Not (objInertia Is Nothing) Then
    'Retrieve the mass just to show it worked
    MsgBox objInertia.Mass
  Else
    MsgBox "The Inertia could not be retrieved!"
  End If

  'Make sure to delete the temp geo set once you
  'are done making all calls to the Inertia object
  objPart.HybridShapeFactory.DeleteObjectForDatum _
  objPart.CreateReferenceFromObject(objGeoSet)

End Sub

Other comments

  • The Inertia object has a density property that is read/write.  This means that when you retrieve an Inertia object you can check the density that is applied and if that value is not correct, you can set it to whatever you want.  Any measured values you retrieve from the Inertia object after setting the density will reflect the new value.
  • In the above examples, I only retrieve the value of the mass property just to show that the Inertia object was successfully defined.  However, you can also retrieve the position of the center of gravity, the inertia matrix, the principal axes and the principal moments.  These methods all require a properly dimensioned array to be passed in.  Consult the help documentation for the Inertia class to get details on how to dimension the arrays and use these methods.
About these ads
  1. x.klein
    October 28, 2010 at 12:41 am

    this are always very good explanation and very usefull , GREAT !

  2. grzechu
    October 28, 2010 at 1:54 am

    Great topic, great job! As always

  3. JoshH
    October 28, 2010 at 6:43 pm

    Very helpful topic. I currently use similar functions, but plan to revise my code with some of the functions above coupled with XML to export the information. Thanks.

  4. yeff
    March 9, 2011 at 10:59 pm

    very useful topic,thx!

  5. Pavel_R
    July 21, 2011 at 2:59 am

    Great, great, great!!!

  6. babic
    September 12, 2011 at 7:58 am

    Hi all.
    I would like to ask you about possibility to send some information as are: moment of inertia, volume, mass, etc from CATIA to excel ore some other program.
    I am looking forward to hearing from you.

    • September 18, 2011 at 10:32 pm

      Hi babic,

      We have developed a software solution called Inertia 360 to automate mass properties calculations in CATIA V5. Here is the link for more information:

      http://www.mecanicasolutions.com/index.php/services/software-development/inertia-360/

      A paper is also available that was published by SAWE (Society of Allied Weight Engineers) that provides greater detail. Please let me know if you would like to receive a copy.

      Please feel free to contact us with any questions.

  7. samani
    September 29, 2011 at 3:45 am

    hi
    thanks a lot for your great article
    I have a question about calculating center of gravity.
    you calculated mass with “.Mass”
    how I can calculate center of gravity?? I also tried “.CenterOfGravity” and “.GX” and “.CenterOfGravity.Gx” , but none of them was a proper object for calculating CoG

  8. September 30, 2011 at 10:14 am

    Try this…

    Dim varCoords(2) As Variant
    objMeasurable.GetCOG(varCoords)

    • Shashank Bassi
      January 17, 2013 at 1:23 pm

      Set objRef = objPart.CreateReferenceFromObject(objPart.MainBody)
      Set objSPAWkb = objDoc.GetWorkbench(“SPAWorkbench”)
      Set objMeasurable = objSPAWkb.GetMeasurable(objRef)
      Dim varCoords(2) As Variant
      objMeasurable.GetCOG (varCoords)
      Dim q As Long
      q = varCoords(2)
      MsgBox “CG is” & q

      its taking 0 as value of q
      can you reply
      thanks

  9. babic
    October 5, 2011 at 4:52 am

    Yes it would be great if You could send me a copy Angelo.

  10. babic
    October 5, 2011 at 4:53 am

    miodragmbm@yahoo.co.uk is my e-mail adress

  11. babic
    October 5, 2011 at 5:00 am

    I would like to know how to access to Ixx, volume, space, etc in CATIA.
    How are they defined in VBA and how I can send some of this information in excel or some other program.
    Thanks a loot.

  12. Madhu
    February 29, 2012 at 11:49 pm

    Can anybody help in getting surface area of a hole;
    please check before you suggest: the surface area measured at the surface of the hole is accurate, if you measure at the hole feature in the tree it will give the wrong value “surface area of closed cylinder formed by the hole surface”.
    the below code gives “surface area of the closed cylinder”;
    Set op = CATIA.ActiveDocument.Part
    set h= op.MainBody.shapes

    for i=1 to h.count
    hname=h.item(i).name
    If (Left(UCase(hname), 4) = “HOLE”) Then
    Set oR = op.CreateReferenceFromObject(h.item(i))
    Set osw = CATIA.ActiveDocument.GetWorkbench(“SPAWorkbench”)
    Set om = osw.GetMeasurable(oR)
    MsgBox “area=” &om.Area
    next

    • March 2, 2012 at 10:05 pm

      So to clarify, are you are trying to get the total area of all the faces inside the resulting hole made by the hole feature?

  13. Saima
    July 16, 2012 at 9:20 pm

    I am very new user of scripting in VBA. Can anyone explain me i need to to write from scratch how can i do it for my CAT part.

    I`ll very thank full to you.

  14. Babs
    July 19, 2012 at 8:19 am

    Great Job!!!!!

  15. Dave
    September 10, 2012 at 1:46 pm

    This is all very useful. However, when trying copying in your examples for Inertia measurements, I encountered what for me has been an ongoing headache in VBA programming. When I run the code example, the compiler hangs up on the definition of the most basic object types. For example, it does not like the line:

    Function GetBodyInertia(ByRef iPart As Part, ByRef iBody As Body) as Inertia

    and it is complaining that the “Part” and “Body” types are undefined user types. I know that this is because I am missing a required Object Library in my references, but my frusturation arises from the fact that there seems to be no documentation to tell me which of the many dozens of available libraries contain the required definitions. What is more, if (out of desperation) I try to simply load all libraries in the references dialog, many of them conflict with a “Name conflicts with existing module, project, or object library” error. I probably have many unneeded libraries already loaded, but I honestly don’t know which I dare unload for fear of making my existing VBA projects inoperable. Am I missing something obvious here? Your sample programs are very clear and I see no reason why they shouldn’t run on any V5 system, especially without failing on such basic types as “Part”, “Body”, “Workbench” etc.
    Is there a basic set of V5 object libraries which should be loaded first, followed by more specialized ones? Or is this all indicative of some other problem?

    • September 11, 2012 at 9:26 pm

      My best guess is maybe the type libraries aren’t registered correctly on your system, perhaps because of multiple CATIA installs or something? I know that if you install one version of CATIA then install a different one as well on the same system, the newer one’s libraries will be correctly registered but the old version will not be. To be sure they are registered correctly, you might want to run the regserver command.

      Open a command window and change to the directory where the CATIA exe is located something like this…
      cd “D:\Program Files\Dassault Systemes\B20\win_b64\code\bin”
      then type CNEXT.exe /regserver

      I think there is a an msi file called vba6.msi or something similar on the installation cds that you can run too. Sorry I don’t have CATIA in front of me now and I haven’t used that msi for probably over 10yrs so its hard to remember! Good luck.

      • Dave
        September 12, 2012 at 1:26 pm

        I will keep the regserver and vba6.msi advice in mind, but in the meantime I may have solved my problem in another way. I had more than one Macro Library loaded in my editor, and when I switched from the failing library to another one (which always worked), and then tried your code in a new module, it all worked fine. So I unloaded the failed library file, and I haven’t had a problem since. Is it possible that the references of two or more macro libraries can interfere with each other?

  16. Florian
    May 27, 2013 at 1:21 pm

    Hi, I would like display mass and inertia in the tree. I have tried unsuccessfully… Anyone know how can i do that ? When you measure the mass and inertia with the application, this function create some parameters under product. (CATIA.ActiveProduct.parameters) But if i try to create a parameter like this (with the same name). It create a non specific parameter. I don’t know how can i do. Do you have any idea to put the measure in the tree ?

    Sorry for my bad level in English.

    • May 29, 2013 at 8:24 pm

      You cannot create measures that remain in the tree using scripting. You can perform most of those measurements in a script but the measured values are gone after the script is finished executing (nothing remains in tree). For mass, it is possible to create a mass parameter in the tree then valuate it with a formula…maybe that helps solve your problem. -Mike

      • Florian
        May 30, 2013 at 12:53 pm

        Thank you for this information. It doesn’t solve my problem but at least i have a confirmation :). Thank you Mike

  17. santosh
    October 2, 2013 at 2:36 pm

    Hi,
    I am intersted to do my carrer in CatiaV5 customisation. For that what are the prerequisites. Do i need to learn C or VB is sufficient?
    Please suggest me a book, site from where I can get required information. Thank you in advance.

  18. little fish
    February 16, 2014 at 9:30 pm

    can you tell me?
    objSel.Item2(1).Value ————–> what objSel ??i don’t know define it!!!
    Thanks !!!

    • February 27, 2014 at 9:17 pm

      Ahhh…sorry about that! It is the selection object and it should have been assigned like I show below. To test the code, just select the items manually then run the sub.
      Set objSel = CATIA.ActiveDocument.Selection

  19. LVE
    May 6, 2014 at 3:29 am

    Hi,

    Dim coord As Variant
    inertie1.GetCOGPosition (coord)

    Dim zz As Double

    zz = coord(3)

    MsgBox (zz)

    It returns 0 Why ??

  1. No trackbacks yet.

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

Follow

Get every new post delivered to your Inbox.

Join 146 other followers

%d bloggers like this: