Friday, February 20, 2015

Quick Macro for Duplicating an Existing Sheet and Views

I had someone recently ask me if it was possible to duplicate a sheet and it's views in Revit. It isn't possible within Revit by default, but with a little bit of code, I was able to get a macro that would duplicate the sheet and it's views. Give the macro a try, just make sure you are in a sheet view before running the macro.

Note: the duplicated views and sheets are renamed with "-DUP" since they need to be unique in Revit. You can change this in the code to be anything you want.

public void DuplicateSheet()
{
    UIDocument uidoc = this.ActiveUIDocument;
    Document doc = uidoc.Document;
    ViewSheet vs = doc.ActiveView as ViewSheet;
   
    using(Transaction t = new Transaction(doc, "Duplicate Sheet"))
    {
        t.Start();
   
        FamilyInstance titleblock = new FilteredElementCollector(doc).OfClass(typeof(FamilyInstance))
            .OfCategory(BuiltInCategory.OST_TitleBlocks).Cast<FamilyInstance>()
            .First(q => q.OwnerViewId == vs.Id);

        ViewSheet newsheet = ViewSheet.Create(doc, titleblock.GetTypeId());
        newsheet.SheetNumber = vs.SheetNumber + "-DUP";
        newsheet.Name = vs.Name;
       
        // all views but schedules
        foreach(ElementId eid in vs.GetAllPlacedViews())
        {
            View ev = doc.GetElement(eid) as View;
           
            View newview = null;
           
            // legends
            if (ev.ViewType == ViewType.Legend)
            {
                newview = ev;
            }
            // all non-legend and non-schedule views
            else
            {
                ElementId newviewid = ev.Duplicate(ViewDuplicateOption.WithDetailing);
                newview = doc.GetElement(newviewid) as View;
                newview.Name = ev.Name + "-DUP";
            }
           
            foreach (Viewport vp in new FilteredElementCollector(doc).OfClass(typeof(Viewport)))
            {
                                               
                if (vp.SheetId == vs.Id && vp.ViewId == ev.Id)
                {
                    BoundingBoxXYZ vpbb = vp.get_BoundingBox(vs);
                    XYZ initialCenter = (vpbb.Max + vpbb.Min) / 2;
                   
                    Viewport newvp = Viewport.Create(doc, newsheet.Id, newview.Id, XYZ.Zero);
                   
                    BoundingBoxXYZ newvpbb = newvp.get_BoundingBox(newsheet);
                    XYZ newCenter = (newvpbb.Max + newvpbb.Min) / 2;
                   
                    ElementTransformUtils.MoveElement(doc, newvp.Id, new XYZ(
                        initialCenter.X - newCenter.X,
                        initialCenter.Y - newCenter.Y,
                        0));
                }
                   
            }
           
        }
       
        // schedules
       
        foreach (ScheduleSheetInstance si in (new FilteredElementCollector(doc).OfClass(typeof(ScheduleSheetInstance))))
        {
            if (si.OwnerViewId == vs.Id)
            {
                if (!si.IsTitleblockRevisionSchedule)
                {                           
                    foreach (ViewSchedule vsc in new FilteredElementCollector(doc).OfClass(typeof(ViewSchedule)))
                    {
                        if (si.ScheduleId == vsc.Id)
                        {
                            BoundingBoxXYZ sibb = si.get_BoundingBox(vs);
                            XYZ initialCenter = (sibb.Max + sibb.Min) / 2;
                           
                            ScheduleSheetInstance newssi = ScheduleSheetInstance.Create(doc, newsheet.Id, vsc.Id, XYZ.Zero);
                           
                            BoundingBoxXYZ newsibb = newssi.get_BoundingBox(newsheet);
                            XYZ newCenter = (newsibb.Max + newsibb.Min) / 2;
                           
                            ElementTransformUtils.MoveElement(doc, newssi.Id, new XYZ(
                                initialCenter.X - newCenter.X,
                                initialCenter.Y - newCenter.Y,
                                0));
                        }
                    }
                }

            }
        }
       
   
        t.Commit();
    }
   
}

Wednesday, February 11, 2015

Revit Macro for Mass Importing Shared Parameters

The following was a quick attempt to see if I could mass import a bunch of shared parameters into my projects. Its part of a tool I am building that needed some unique parameters for schedules and tags.

public void ImportSharedParameters()
{
    UIDocument uidoc = this.ActiveUIDocument;
    Document doc = uidoc.Document;
  
    // location of shared parameters file
    string spfile = @"\\corp.ktgy.com\bim\DT\API\Unit Coin\Shared Parameter-KTGY.txt";
  
    using (Transaction t = new Transaction(doc, "Import Shared Parameters"))
    {
        t.Start();
        

        // create a new line for each parameter like this:
       // doc, SharedParametersFile, ParameterName, Category, ParameterGroup, VaryByGroupInstance         CreateProjParameter(doc, spfile, "Building", BuiltInCategory.OST_Rooms, BuiltInParameterGroup.PG_IDENTITY_DATA, true);
        CreateProjParameter(doc, spfile, "Unit Area", BuiltInCategory.OST_Rooms, BuiltInParameterGroup.PG_GENERAL, true);
                      
        t.Commit();
    }
}


public void CreateProjParameter( Document doc, string sharedParameterFile, string parameterName,
                                BuiltInCategory bicategory, BuiltInParameterGroup bipgroup, Boolean varyByGroup)
{
    // load the shared parameters file
    Application.SharedParametersFilename = sharedParameterFile;
  
    // select the category
    Category cat = doc.Settings.Categories.get_Item(bicategory);
    // create a new category set
    CategorySet catset = Application.Create.NewCategorySet();
    // add category to category set
    catset.Insert(cat);
  
    // loaded shared parameter file
    DefinitionFile deffile = Application.OpenSharedParameterFile();
  
    try
    {
        // find the parameter in the shared parameters file
        // by searching each parameter group
        var v = (from DefinitionGroup dg in deffile.Groups
                 from ExternalDefinition d in dg.Definitions
                 where d.Name == parameterName
                 select d);
      
        ExternalDefinition def = v.First();
      
        // bind the parameter to the category and parameter group
        Binding binding = Application.Create.NewInstanceBinding(catset);
        BindingMap map = doc.ParameterBindings;
        map.Insert(def, binding, bipgroup);
      
        // change parameter to be "Values can vary by group instance"
        if(varyByGroup)
        {
            BindingMap grpmap = doc.ParameterBindings;
            DefinitionBindingMapIterator it = grpmap.ForwardIterator();
          
            while (it.MoveNext())
            {
                Definition d = it.Key as Definition;
                if (d.Name == parameterName)
                {
                    InternalDefinition idef = it.Key as InternalDefinition;
                    idef.SetAllowVaryBetweenGroups(doc, true);
                }
            }
        }
                      
    }
    catch (Exception ex)
    {
               TaskDialog.Show("Error", ex.Message);
    }
}

Thursday, January 15, 2015

BIM Consortium Revit Addin Bug Fix Edition

I uploaded a new build of the BIM Consortium Addin today with quite a few bug fixes. The most notable ones being...

  • Delete Unused Views would crash Revit randomly. Tool completely re-written to be more stable
  • Rooms to 3D Views and the Room 3D Tags shouldn't error out when there are un-bounded or non-placed rooms anymore
If you come across any other bugs, make sure to shoot me an email at troygates@gmail.com.


Download HERE 

Monday, July 21, 2014

BIMConsortium Revit Addin Update + New Tools + 2015 Compatible












A new update is available located here: BIMCon_Addin_1.2.zip


Updated
  • Addin now supports both Revit 2014 and 2015
  • Delete Views - Added option to delete all views NOT on a Sheet
















New

3D Room Tags
This tool will place a generic family with 3D text into the center of every room at the specified height above the room's level. Load the included family Room Tag 3D BIMCon.rfa. This family can be modified to what you want it to look like as long as it keeps the same name. I will add an option in the future to pick a family of your own.


















Room to 3D Views
This tool will create four (4) 3D Camera Views for every room in the model. The views are placed at lower-left and upper-right at floor and above ceiling. The heights are adjustable.

* Note: Because of how the API determines a room boundary as a rectangular box, the cameras may be located outside the actual rooms.























Merge Text
This tool is actually two (2) tools, Merge 2 Text and Merge Multiple Text.
















The first one will take two (2) pieces of text and merge them together with several options available.





















The second tool will merge several text elements into the first one selected. Notice that you need to hit ESC to end the selection of elements.

















NOTE:
If you receive an error in Revit about not being able to load the addin, go to the folder where you saved the dll file, right-click the file and go to properties. In the properties dialog click the button to Unblock the file.


Tuesday, June 24, 2014

Revit Lookup 2015 Addin

During my class (BIM Managers Guide to Automating Revit Using Macros) at RTC in Schaumburg (Chicago) last week, I mentioned the Revit Lookup addin. Afterwards several people asked where they could download a compiled version. I compiled the most recent source from https://github.com/jeremytammik/RevitLookup/ and uploaded it to my blog so you can download it (below).

Download
Revit Lookup 2015

Install Instructions
Extract the 2 files to C:\ProgramData\Autodesk\Revit\Addins\2015\


If you are interested in 2013 and 2014 versions you can find them in a blog post from last year: http://revitcoaster.blogspot.com/2013/09/creating-macros-larug-sept-2013.html