Electrical Settings and Lighting Fixtures

Here are two recent questions on

electrical settings of distribution systems

and

family instances for lighting fixtures

handled by Saikat Bhattacharya and Joe Ye, respectively.

By the way, this is a special occasion, namely the 200th post to The Building Coder.
I will resist the temptation to declare this as a birthday post like I did

post number 100
,
because the first real annual birthday of The Building Coder is coming up quite soon now anyway, and we don’t want to exaggerate, do we?

Reading and Writing the Electrical Settings of Distribution Systems

Question:
Is there any way to use the Revit API to read and write the data under Electrical Settings, e.g. the Distribution System rows?

Answer:
To do a quick check, I used the RvtMgdDbg tool and found out that the active document contains a DistributionSysType container which lists all the distribution systems available from the user interface.
Here are the electrical settings displayed in the user interface:

Electrical Settings

Here, we have selected the DistributionSysType instance using
RvtMgdDbg
to show the same information as the user interface as accessed through the API:

DistributionSysType in RvtMgdDbg

Thus, the DistributionSysType class might be what you looking for.

Creating Hosted Family Instances for Lighting Fixtures

Question:
I am loading a batch of lighting fixtures using .NET but I am having some issues.
I programmatically set the host to be the ceiling by using parameters showing that the host is the ceiling when the fixture is loaded.
However, the properties of the resulting fixture do not reflect this.
Also, the fixture created cannot be copied.
In sum, the properties of the fixtures are not the same as the properties of a fixture created manually and inserted by Revit itself.
I used the following code to load the fixture:


FamilyInstance inst
= doc.Create.NewFamilyInstance(
location, symbol, ceil,
StructuralType.NonStructural );

In this call, location is the location of the fixture.
I set its Z coordinate to zero in order to inherit the host elevation, but this does not work.
Symbol is the family symbol to be inserted, and ceil the selected host ceiling.

Answer:
I reproduced the issue.
Using your method, I found the created light fixture is located above the ceiling, although the Z elevation is the same.
The host property is null, as is the parameter value of HOST_ID_PARAM.
So I think the issue is caused by the level setting.

I changed the code to use another override of NewFamilyInstance, which takes the level as an argument:


Document.NewFamilyInstance(
XYZ,
FamilySymbol,
Element,
Level,
StructuralType )

The lighting fixture now has a valid host property. Here is the updated code for the Execute method of the external command:


Application app = commandData.Application;
Document doc = app.ActiveDocument;
 
Autodesk.Revit.Creation.Filter cf
  = app.Create.Filter;
 
// get a lighting fixture family symbol:
 
Filter f1 = cf.NewTypeFilter(
  typeof( FamilySymbol ) );
 
Filter f2 = cf.NewCategoryFilter(
  BuiltInCategory.OST_LightingFixtures );
 
Filter f = cf.NewLogicAndFilter( f1, f2 );
 
List<Element> symbols = new List<Element>();
doc.get_Elements( f, symbols );
 
FamilySymbol sym = null;
 
foreach( Element elem in symbols )
{
  sym = elem as FamilySymbol; // get the first one.
  break;
}
 
if( null == sym )
{
  message = "No lighting fixture symbol found.";
  return CmdResult.Failed;
}
 
// pick the ceiling:
 
doc.Selection.StatusbarTip
  = "Please select ceiling to host lighting fixture";
 
doc.Selection.PickOne();
 
Element ceiling = null;
 
foreach( Element elem in doc.Selection.Elements )
{
  ceiling = elem as Element;
  break;
}
 
// get the level 1:
 
ElementIterator it = doc.get_Elements(
  typeof( Level ) );
 
Level level = null;
 
while( it.MoveNext() )
{
  level = it.Current as Level;
 
  if( level.Name.Equals( "Level 1" ) )
    break;
}
 
if( null == level )
{
  message = "Level 1 not found.";
  return CmdResult.Failed;
}
 
// create the family instance:
 
XYZ p = app.Create.NewXYZ( -43, 28, 0 );
 
FamilyInstance instLight
  = doc.Create.NewFamilyInstance(
    p, sym, ceiling, level,
    StructuralType.NonStructural );
 
return CmdResult.Succeeded;

Thank you very much Joe and Saikat for these answers!


Comments

12 responses to “Electrical Settings and Lighting Fixtures”

  1. Mira Saad Avatar
    Mira Saad

    Hi Jeremy,
    this is a very usueful code if you want to create a new instance and pick a host for it.
    however, i am not finding a way to re-host a given fixture through code.
    Is there is a way to call the command “Pick new host” (Vertical face, reference plane..)via API?
    Please advise as soon as possible on the way to rehost a fixture through code. (to nearest element that intersects it)
    Regards

  2. Dear Mira,
    Thank you, glad you like it.
    Unfortunately, I do not see a direct way to programmatically rehost a family instance such as an electrical fixture to a given host, e.g. a wall element.
    The only workaround I can think of would be to note the location and family symbol of the family instance, delete it, and create a new one by calling the NewFamilyInstance method with the overload taking the host element argument, using the location and the symbol information extracted from the existing instance before its deletion.
    This will create an identical fixture with the host information included.
    Cheers, Jeremy.

  3. Mona Akkoush Avatar
    Mona Akkoush

    Hi Jeremy,
    I tried this workaround & it works great if the host element is in the same file as the lighting fixture.
    On the other hand, if the host element which is a wall in my case, is in a linked revit document, then am not able to host the new family instance on the wall’s face.
    I tried to retrieve the wall’s faces, but the faces array returned zero elements as the wall is in a linked file.
    Please can you advise on how to create a new family instance hosted on the face of a wall found in a linked document..
    Thanks a lot.

  4. Dear Mona,
    Oh dear, with linked files it is a lot trickier. I don’t even know if you can host the fixture at all on a wall in a linked file. Is that possible even through the user interface? If not, then it will probably not be possible through the API either.
    Cheers, Jeremy.

  5. Mona Akkoush Avatar
    Mona Akkoush

    Hi Jeremy,
    In Revit, you can host a fixture on the face of a wall in a Revit architectural linked file. Kindly note that I was able to get the side face of the wall where the fixture will be hosted using “HostObjectUtils.GetSideFaces(wall element, ShellLayerType.Exterior)”.
    Yet, when using the method “NewFamilyInstance(wall element side face as FACE, wall element location curve as Line, fixture symbol as FamilySymbol)” to host the new fixture on the face of the wall element, I get the following error “The Reference of the input face is null.If the face was obtained from Element.Geometry, make sure to turn on the option ComputeReferences”. I have checked the reference object in the code & it was not null & the ComputeReferences was set to true.
    Please advise..
    Best Regards,

  6. Dear Mona,
    I am sorry to say I cannot do much more off-hand since this will probably require some research to answer. Please submit an ADN DevHelp Online case for this. Thank you!
    Cheers, Jeremy.

  7. Mona Akkoush Avatar
    Mona Akkoush

    Hi Jeremy,
    Thanks a lot, I submitted my case to DevHelp.
    An aside question, any idea why the retrieved Face object might have a null Reference, taking into consideration that the face is a side-face of a wall found in a linked file.
    Thanks in advance,
    Best Regards,

  8. Dear Mona,
    Thank you for submitting the case!
    I would say that the problem may be that it is in a linked file :-)
    Sorry.
    Cheers, Jeremy.

  9. hi jeremy i tried this code and i can’t seem
    to make it work
    can u send it to me in c# project format
    thanks
    ahmedattia2010@hotmail.com

  10. Autodesk.Revit.Creation.Filter
    is not recognized by vc#
    ?????????????

  11. sorry for too many posts but i noticed
    that some of this functions are not in revit
    2010 api can’t you update the example to revit 2011 api
    thanks

  12. after some work i realized this is not exactly
    what i want my project was to copy
    an ( already loaded lighting fixture) by selecting it
    and then selecting the point where it will
    be copied and develop it later to lighting distribution plugin
    the problem is i can’t find a function of copy or anything similar and i don’t know if i must provide a host programatically or not but your code for selecting ceiling will work i guess n
    now if u can help i’ll greatly appreciate it
    thanx a lot
    ahmed.attiaali@ecgsa.com

Leave a Reply to Mona AkkoushCancel reply

Discover more from Autodesk Developer Blog

Subscribe now to keep reading and get access to the full archive.

Continue reading