Revit secondary development - using the Dispatcher class to add a progress bar

When the program runs for a long time and then avoids the program from suspended animation, a better way is to add a progress bar. If only your function is currently running, using the Dispatcher class is a simple and good choice.

This is achieved with the wpf window.

public partial class ProgressBarView : Window
    {
        ExternalCommandData m_commandData=null;
        StrightRigidFrameBridgeModel m_model =null;
        Element m_element = null;
        ProgressModel m_ProgressModel;       
        bool applicationCancle =false;
        public ProgressBarView(ExternalCommandData commandData, StrightRigidFrameBridgeModel model,Element elem)
        {
            InitializeComponent();
            m_commandData = commandData;
            m_model = model;
            m_element = element;
            ProgressModel pModel = new ProgressModel();
            m_ProgressModel = pModel;
            this.DataContext = pModel;
            applicationCancle = false;            
        }
        public void StrightRigidFrameBridgeCreater(ExternalCommandData commandData, StrightRigidFrameBridgeModel model, Element elem)
        {
            using (TransactionGroup transGroup = new TransactionGroup(commandData.Application.ActiveUIDocument.Document, "Creat Rebar"))
            {
                transGroup.Start("Creat Stright Rigid Frame Bridge");
                ICollection<ElementId> elementIds = new List<ElementId>() { elem.Id };
            for (int i = 0; i < (model.ListBoxGriderModel.Count - 1); i++)
            {               
                m_ProgressModel.ProgressInfomation = "left" + (model.ListBoxGriderModel.Count - 1 - i-1).ToString() + "sections";
                m_ProgressModel.ProgressValue= double.Parse(i.ToString())/ (model.ListBoxGriderModel.Count - 2) * 100;                          
                System.Windows.Forms.Application.DoEvents();

                BoxGriderModel boxGriderModelI = model.ListBoxGriderModel[i];
                BoxGriderModel boxGriderModelJ = model.ListBoxGriderModel[i + 1];
                #region Assign the family parameters of the table to the corresponding family parameters

                #endregion
                
                    Transaction transaction1 = new Transaction(commandData.Application.ActiveUIDocument.Document);
                    transaction1.Start("Change family parameters");
                    elem.LookupParameter("iH").Set(MillimetersToUnits(boxGriderModelI.XLG)); //The height of the i section of the variable section box girder
                    elem.LookupParameter("iHI5").Set(MillimetersToUnits(boxGriderModelI.DBH)); //The height of the bottom plate of the i-section of the variable-section box girder
                    elem.LookupParameter("iT").Set(MillimetersToUnits(boxGriderModelI.FBH)); //The width of the i-section web of the variable-section box girder
                    elem.LookupParameter("iHI1").Set(MillimetersToUnits(boxGriderModelI.TBH)); //The height of the top plate of the i section of the variable section box girder
                    elem.LookupParameter("jH").Set(MillimetersToUnits(boxGriderModelJ.XLG)); //The height of the i section of the variable section box girder
                    elem.LookupParameter("jHI5").Set(MillimetersToUnits(boxGriderModelJ.DBH)); //The height of the bottom plate of the i section of the variable section box girder
                    elem.LookupParameter("jT").Set(MillimetersToUnits(boxGriderModelJ.FBH)); //Width of web of variable section box girder i section
                    elem.LookupParameter("jHI1").Set(MillimetersToUnits(boxGriderModelJ.TBH)); //The height of the top plate of the i section of the variable section box girder
                    elem.LookupParameter("BeamLength").Set(MillimetersToUnits(boxGriderModelJ.JDCD)); //Variable section box beam segment length
                    elem.LookupParameter("detZ").Set(MillimetersToUnits(boxGriderModelI.SJGC) - MillimetersToUnits(boxGriderModelJ.SJGC)); //The height difference between the two z sections of the variable section box beam               
                    elem.LookupParameter("detY").Set(MillimetersToUnits(boxGriderModelI.Y_Coordinate) - MillimetersToUnits(boxGriderModelJ.Y_Coordinate)); //The height difference between the two z sections of the variable section box beam               
                    transaction1.Commit();

                    #region Put the changed family in the corresponding position
                    Transaction transaction2 = new Transaction(commandData.Application.ActiveUIDocument.Document);
                    transaction2.Start("Copy the family to the corresponding location");
                    XYZ point = new XYZ(MillimetersToUnits(boxGriderModelI.X_Coordinate), MillimetersToUnits(boxGriderModelI.Y_Coordinate), MillimetersToUnits(boxGriderModelI.SJGC));

                    LocationPoint familyInstancePoint = elem.Location as LocationPoint;
                    XYZ tanslationVector = point.Subtract(familyInstancePoint.Point);
                    ElementTransformUtils.CopyElements(commandData.Application.ActiveUIDocument.Document, elementIds, tanslationVector);
                    transaction2.Commit();
                    #endregion

                    if (applicationCancle == true)
                    {
                        break;
                    }
                }
             if(applicationCancle==true)
                    {                    
                    transGroup.RollBack();
                    this.Close();
                    }
             else
                {
                    transGroup.Assimilate();
                }               
            }
        }
        private double MillimetersToUnits(double value)
        {
            return UnitUtils.ConvertToInternalUnits(value, DisplayUnitType.DUT_MILLIMETERS);
        }

        private void window_Loaded(object sender, RoutedEventArgs e)
        {           
            Thread thread = new Thread(excute);
            thread.Start();

        }

        private void excute()
        {
            this.Dispatcher.BeginInvoke(System.Windows.Threading.DispatcherPriority.Normal, (ThreadStart)delegate () { StrightRigidFrameBridgeCreater(m_commandData, m_model, m_element); });
           
        }        

        private void cancelAsyncButton_Click(object sender, RoutedEventArgs e)
        {
            this.Dispatcher.BeginInvoke(System.Windows.Threading.DispatcherPriority.Normal, (ThreadStart)delegate () { applicationCancle = true;});

           
        }
    }
}

The above code uses System.Windows.Forms.Application.DoEvents() to continuously switch the program back and forth between the thread and the main program, the program calculates a part, and then the progress bar updates the progress.

Use the Dispartcher class to pay attention to try catch and close the thread in time.


If you are interested in Revit secondary development and Dyanmo programming, please join the QQ group to communicate: 660319009

For personal inquiries, please add qq: 254033230, I see money, don't bother! ! !


Guess you like

Origin http://43.154.161.224:23101/article/api/json?id=325852939&siteId=291194637