Results 1 to 5 of 5

Thread: How to create a simple copy-paste macro

  1. #1
    I could stop if I wanted to
    Join Date
    2009-01
    Posts
    345
    Login to Give a bone
    0

    Default How to create a simple copy-paste macro

    This will be my first attempt using Macros in Revit and my first attempt at writing computer code. I am looking to fix the following problem with my model: We have 1000+ errors that read "elements have duplicate 'mark' values". The reason we get this error is that we set up our tags to use the 'mark' and 'type mark' values, for example AH-4 has type mark = AH and mark = 4, so AH-4 and EF-4 have the same 'mark' value. People keep telling me that these errors are slowing down the model. I don't know if that's true or not but until I fix it they'll keep saying it so I need to fix the errors.

    I'm going to do this by creating a new project parameter 'new mark' and switching our tags to reference this instead of 'mark'. Then I will need to do two things with the help of some macros:

    1) copy the 'mark' values of every element into the 'new mark' parameter
    2) create a new 'mark' value for each element that has a duplicate 'mark' value in some other element

    Both of these tasks could be accomplished using a schedule. I am familiar with how macros work in excel, and could do something similar to make these changes in Revit. The first macro would need to do the following within a schedule:

    1- Start at cell A-1
    2- Copy contents of cell ('mark' value)
    3- Move to the cell to the right
    4- Paste contents of clipboard (into the 'new mark' parameter)
    5- Move down one cell and one cell to the left
    6- Repeat from step 2

    The second macro, which defines new mark values for the duplicates, would need to do the following:

    1- Start at cell A-1 ('mark' value for the first element)
    2- Replace cell contents with numerical value X
    3- Move to the cell below
    4- Replace cell contents with numerical value X+1
    5- Repeat from step 3

    Any idea where I could go to figure out how to do this?

  2. #2
    Member
    Join Date
    2010-06
    Location
    Brisbane, Australia
    Posts
    25
    Login to Give a bone
    0

    Default Re: How to create a simple copy-paste macro

    I don't think the API supports schedules.

    Sounds like what you need to do is retrieve the relevant elements, copy the mark parameter's value to the 'new mark' parameter and finally update the original mark parameter's value.

    I haven't tested the following code snippets but they should point you in the right direction.

    To get the relevant elements you need to use a FilteredElementCollector:

    Code:
                // Get the document
                var document = this.ActiveUIDocument.Document;
                // Create a collector for the current document
                var collector = new FilteredElementCollector(document);
                // Get all FamilyInstance elements
                var elements = collector.OfClass(typeof(FamilyInstance)).ToElements().Cast<FamilyInstance>().ToArray();
    This just gets all FamilyInstance elements, but you could modify the filtering to retrieve whatever elements you require. For more info about filtering, install the SDK and take a look at chapter 6 of the developer guide.

    Next, sort the elements by their Mark so you can iterate over them and renumber as necessary.

    Code:
                // Sort the elements by their mark value
                // Note that this assumes that the Mark parameter is stored as a string and that it contains integer values, if not then this will fail
                var sortedElements = elements.OrderBy(e => int.Parse(e.get_Parameter("Mark").AsString())).ToArray();
    Finally, you need to start a transaction so you can update the parameters. Then iterate over the sorted elements, copy / update the mark and then commit the transaction.

    Code:
                // Start a transaction
                var transaction = new Transaction(document, "Copy Marks");
                transaction.Start();
                try
                {
                    // Setup dictionary to track mark values
                    var elementsByMark = new Dictionary<int, FamilyInstance>();
                    // Process each element
                    foreach (var element in sortedElements)
                    {
                        // Get the parameters
                        var mark    = element.get_Parameter("Mark");
                        var newMark = element.get_Parameter("New Mark");
    
                        // Copy the value from Mark to New Mark
                        newMark.Set(mark.AsString());
    
                        // Update Mark to ensure uniqueness
                        var markValue = int.Parse(mark.AsString());
                        while (elementsByMark.ContainsKey(markValue))
                        {
                            markValue++;
                        }
                        mark.Set(markValue.ToString());
                        elementsByMark.Add(markValue, element);
                    }
                    transaction.Commit();
                }
                catch (Exception)
                {
                    transaction.RollBack();
                    throw;
                }

  3. #3
    I could stop if I wanted to
    Join Date
    2007-02
    Location
    Alexandra, New Zealand
    Posts
    237
    Login to Give a bone
    0

    Default Re: How to create a simple copy-paste macro

    msiebert is right on the money with his code there.

    If you wanted to short cut the process you could download our element renumber tool that will do just what you are after. It can renumber all elements by catagory at once.

    Check it out here http://revitfb.blogspot.com/2011/05/...2012-free.html and the best part is its free

    Cheers

    Phillip

  4. #4
    I could stop if I wanted to
    Join Date
    2009-01
    Posts
    345
    Login to Give a bone
    0

    Default Re: How to create a simple copy-paste macro

    Thanks guys.

    msiebert,
    If I understand what you're saying correctly (which likely isn't the case) this code will renumber the mark values for the elements that I select through the filter. Correct? Before i do this I would have to copy the "mark" values into the "new mark" parameter for every element. Do you know how I might accomplish that?

    Philip,
    Is that plug-in compatible with Revit 2011?

  5. #5
    Member
    Join Date
    2010-06
    Location
    Brisbane, Australia
    Posts
    25
    Login to Give a bone
    0

    Default Re: How to create a simple copy-paste macro

    The above code should copy the Mark to New Mark before updating the Mark value.

    Take a look at the following lines:

    Code:
                        // Get the parameters
                        var mark    = element.get_Parameter("Mark");
                        var newMark = element.get_Parameter("New Mark");
    
                        // Copy the value from Mark to New Mark
                        newMark.Set(mark.AsString());

Similar Threads

  1. Macro recorder/ simple language for editing (like VBA)
    By Wish List System in forum Revit Architecture - Wish List
    Replies: 1
    Last Post: 2014-11-14, 03:48 AM
  2. Replies: 0
    Last Post: 2013-09-25, 02:23 AM
  3. Right-click copy, paste, paste aligned
    By revit.wishlist1942 in forum Revit Architecture - Wish List
    Replies: 0
    Last Post: 2008-07-04, 11:39 AM
  4. Simple Macro
    By matt_jlt in forum VBA/COM Interop
    Replies: 1
    Last Post: 2007-08-08, 02:19 PM
  5. Simple Macro
    By matt_jlt in forum Inventor - General
    Replies: 0
    Last Post: 2007-08-08, 11:19 AM

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •