应用范围:EventsMonitor

Revit平台:所有

Revit版本:2011.0

首次发布日期:2010.0

编程语言:c#

技能水平:中等

类别:基础知识

类型:ExternalApplication

主题:追踪事件

简介:

此示例演示如何订阅受控制的应用程序级别事件。

相关类:

Autodesk.Revit.UI.IExternalCommand

Autodesk.Revit.UI.IExternamApplication

Autodesk.Revit.DB.Events

项目文件:

Command.cs

这个文件包含类Command,它实现了IExternalCommand,并用于检索事件设置以帮助用户更改其选择。

 

ExternalApplication.cs

这个文件包含一个类ExternalApplication,它实现了IExternalApplication接口,并提供了示例的一个条目。这个类控制其他函数类,并在本示例中起桥梁作用。它还创建了一个自定义面板“事件监视器”,在OnStartup方法中包含一个名为“Set Events”的按钮。

 

EventManager.cs

这个文件包含一个类AppEventManager,它实现了所有事件处理程序方法。该类是应用程序事件的管理器。在这个类中,您可以根据所选择的内容订阅和删除事件。

 

LogManager.cs

这个文件包含一个LogManager类,它实现了写日志文件和生成事件信息以显示在信息窗口中的所有操作。

 

EventInfoWindows.cs

该文件包含一个表单类InformationWindows,它由一个DataGridView组成,用于向用户显示Revit事件历史日志。事件日志包括事件时间、事件名称和事件类型。

 

EventSettingForm.cs

这个文件包含一个表单类,它由CheckedList控件组成,为用户提供关于订阅哪些事件的选项。

 

JournalProcessor.cs

这个文件包含一个类JournalProcessor,它可以帮助自动测试这个示例。这个类在UI弹出之前检查外部xml文件,并帮助入口方法来控制它是在玩日志还是在UI中操作。这个类还可以帮助将所选事件列表转储到外部xml文件或日志文件中,并从这些文件中检索事件列表。如果你只是对如何使用事件感兴趣,你可以跳过这堂课和其他相关的句子。

描述:

Revit应用程序启动时,示例弹出一个名为“事件跟踪设置”的对话框。用户在这个对话框中做出选择,并跟踪他选择的事件。同时创建一个带有按钮的自定义面板。此按钮用于检索开头显示的设置对话框,以便用户更改最后的选择。所有订阅的事件都显示在InformationWindows中,包括它们的名称、类型和触发时间。

此示例将根据用户在事件设置窗口中选择的内容订阅事件。

此示例在引发相应事件时在非模态窗口中列出事件信息,如时间、名称和类型等。

产品说明:

1.Debug模式下构建此示例,并使用此示例的.addin注册您的.addin

2.Revit运行。将出现“事件设置”对话框。

3.选择您想要跟踪的任何事件。例如,您可以尝试选择DocumentSavingDocumentsSaved事件。按“确定”按钮,进入“事件”信息窗口。打开并保存一个文档,然后一个日志项将出现在Events信息窗口中,并被写入EventsMonitor.log文件中。

4.然后,如果您想要更改要跟踪的另一个事件,您可以按“EventsMonitor”面板中的“Set Events”按钮。系统将再次出现“事件设置”对话框。

:

1.注意,一些条件编译指令(#if)在样本的源代码中被使用,它们被用于不同的目的;请确保在调试模式下构建此示例,以使示例工作如上所述,在发布模式下构建示例仅用于回归测试目的。

源代码:

完整的源代码请加入QQ群649037449,在群文件中下载RevitSDK.exe,解压后在文件夹中搜索本文中应用程序名称即可获得完整源码

EventManager.cs

//
// (C) Copyright 2003-2019 by Autodesk, Inc.
//
// Permission to use, copy, modify, and distribute this software in
// object code form for any purpose and without fee is hereby granted,
// provided that the above copyright notice appears in all copies and
// that both that copyright notice and the limited warranty and
// restricted rights notice below appear in all supporting
// documentation.
//
// AUTODESK PROVIDES THIS PROGRAM "AS IS" AND WITH ALL FAULTS.
// AUTODESK SPECIFICALLY DISCLAIMS ANY IMPLIED WARRANTY OF
// MERCHANTABILITY OR FITNESS FOR A PARTICULAR USE. AUTODESK, INC.
// DOES NOT WARRANT THAT THE OPERATION OF THE PROGRAM WILL BE
// UNINTERRUPTED OR ERROR FREE.
//
// Use, duplication, or disclosure by the U.S. Government is subject to
// restrictions set forth in FAR 52.227-19 (Commercial Computer
// Software - Restricted Rights) and DFAR 252.227-7013(c)(1)(ii)
// (Rights in Technical Data and Computer Software), as applicable.
//

using System;
using System.Data;
using System.Collections.Generic;
using System.Text;
using System.Diagnostics;

using Autodesk.Revit;
using Autodesk.Revit.UI;
using Autodesk.Revit.DB.Events;
using Autodesk.Revit.UI.Events;
using Autodesk.Revit.ApplicationServices;

namespace Revit.SDK.Samples.EventsMonitor.CS
{
    /// <summary>
    /// This class is a manager for application events.
    /// In this class, user can subscribe and remove the events according to what he select.
    /// This class used the controlled Application as the sender.
    /// If you want to use Application or Document as the sender, the usage is same.
    /// "+=" is used to register event and "-=" is used to remove event.
    /// </summary>
    public class EventManager
    {
        #region Class Member Variables
        /// <summary>
        /// Revit application
        /// </summary> 
        private UIControlledApplication m_app;

        /// <summary>
        /// This list is used to store what user select last time.
        /// </summary> 
        private List<String> historySelection;
        #endregion

        #region Class Constructor
        /// <summary>
        /// Prevent the compiler from generating a default constructor.
        /// </summary>
        private EventManager()
        {
            // none any codes, just declare it as private to obey the .Net design rule
        }

        /// <summary>
        /// Constructor for application event manager.
        /// </summary>
        /// <param name="app"></param>
        public EventManager(UIControlledApplication app)
        {
            m_app = app;
            historySelection = new List<string>();
        }
        #endregion

        #region Class Methods
        /// <summary>
        /// A public method used to update the events subscription
        /// </summary>
        /// <param name="selection"></param>
        public void Update(List<String> selection)
        {
            // If event has been in history list and not in current selection,
            // it means user doesn't select this event again, and it should be move.
            foreach (String eventname in historySelection)
            {
                if (!selection.Contains(eventname))
                {
                    subtractEvents(eventname);
                }
            }

            // Contrarily,if event has been in current selection and not in history list,
            // it means this event should be subscribed.
            foreach (String eventname in selection)
            {
                if (!historySelection.Contains(eventname))
                {
                    addEvents(eventname);
                }
            }

            // generate the history list.
            historySelection.Clear();
            foreach (String eventname in selection)
            {
                historySelection.Add(eventname);
            }
        }

        /// <summary>
        /// Register event according to event name.
        /// The generic handler app_eventsHandlerMethod will be subscribed to this event.
        /// </summary>
        /// <param name="eventName"></param>
        private void addEvents(String eventName)
        {
            switch (eventName)
            {
                case "DocumentCreating":
                    m_app.ControlledApplication.DocumentCreating += new EventHandler<DocumentCreatingEventArgs>(app_eventsHandlerMethod);
                    break;
                case "DocumentCreated":
                    m_app.ControlledApplication.DocumentCreated += new EventHandler<DocumentCreatedEventArgs>(app_eventsHandlerMethod);
                    break;
                case "DocumentOpening":
                    m_app.ControlledApplication.DocumentOpening += new EventHandler<DocumentOpeningEventArgs>(app_eventsHandlerMethod);
                    break;
                case "DocumentOpened":
                    m_app.ControlledApplication.DocumentOpened += new EventHandler<DocumentOpenedEventArgs>(app_eventsHandlerMethod);
                    break;
                case "DocumentClosing":
                    m_app.ControlledApplication.DocumentClosing += new EventHandler<DocumentClosingEventArgs>(app_eventsHandlerMethod);
                    break;
                case "DocumentClosed":
                    m_app.ControlledApplication.DocumentClosed += new EventHandler<DocumentClosedEventArgs>(app_eventsHandlerMethod);
                    break;
                case "DocumentSavedAs":
                    m_app.ControlledApplication.DocumentSavedAs += new EventHandler<DocumentSavedAsEventArgs>(app_eventsHandlerMethod);
                    break;
                case "DocumentSavingAs":
                    m_app.ControlledApplication.DocumentSavingAs += new EventHandler<DocumentSavingAsEventArgs>(app_eventsHandlerMethod);
                    break;
                case "DocumentSaving":
                    m_app.ControlledApplication.DocumentSaving += new EventHandler<DocumentSavingEventArgs>(app_eventsHandlerMethod);
                    break;
                case "DocumentSaved":
                    m_app.ControlledApplication.DocumentSaved += new EventHandler<DocumentSavedEventArgs>(app_eventsHandlerMethod);
                    break;
                case "DocumentSynchronizingWithCentral":
                    m_app.ControlledApplication.DocumentSynchronizingWithCentral += new EventHandler<DocumentSynchronizingWithCentralEventArgs>(app_eventsHandlerMethod);
                    break;
                case "DocumentSynchronizedWithCentral":
                    m_app.ControlledApplication.DocumentSynchronizedWithCentral += new EventHandler<DocumentSynchronizedWithCentralEventArgs>(app_eventsHandlerMethod);
                    break;
                case "FileExporting":
                    m_app.ControlledApplication.FileExporting += new EventHandler<FileExportingEventArgs>(app_eventsHandlerMethod);
                    break;
                case "FileExported":
                    m_app.ControlledApplication.FileExported += new EventHandler<FileExportedEventArgs>(app_eventsHandlerMethod);
                    break;
                case "FileImporting":
                    m_app.ControlledApplication.FileImporting += new EventHandler<FileImportingEventArgs>(app_eventsHandlerMethod);
                    break;
                case "FileImported":
                    m_app.ControlledApplication.FileImported += new EventHandler<FileImportedEventArgs>(app_eventsHandlerMethod);
                    break;
                case "DocumentPrinting":
                    m_app.ControlledApplication.DocumentPrinting += new EventHandler<DocumentPrintingEventArgs>(app_eventsHandlerMethod);
                    break;
                case "DocumentPrinted":
                    m_app.ControlledApplication.DocumentPrinted += new EventHandler<DocumentPrintedEventArgs>(app_eventsHandlerMethod);
                    break;
                case "ViewPrinting":
                    m_app.ControlledApplication.ViewPrinting += new EventHandler<ViewPrintingEventArgs>(app_eventsHandlerMethod);
                    break;
                case "ViewPrinted":
                    m_app.ControlledApplication.ViewPrinted += new EventHandler<ViewPrintedEventArgs>(app_eventsHandlerMethod);
                    break;
                case "ViewActivating":
                    m_app.ViewActivating += new EventHandler<ViewActivatingEventArgs>(app_eventsHandlerMethod);
                    break;
                case "ViewActivated":
                    m_app.ViewActivated += new EventHandler<ViewActivatedEventArgs>(app_eventsHandlerMethod);
                    break;
               case "ProgressChanged":
                    m_app.ControlledApplication.ProgressChanged += new EventHandler<ProgressChangedEventArgs>(app_eventsHandlerMethod);
                    break;
            }
        }

        /// <summary>
        /// Remove registered event by its name.
        /// </summary>
        /// <param name="eventName">Event name to be subtracted.</param>
        private void subtractEvents(String eventName)
        {
            switch (eventName)
            {
                case "DocumentCreating":
                    m_app.ControlledApplication.DocumentCreating -= app_eventsHandlerMethod;
                    break;
                case "DocumentCreated":
                    m_app.ControlledApplication.DocumentCreated -= app_eventsHandlerMethod;
                    break;
                case "DocumentOpening":
                    m_app.ControlledApplication.DocumentOpening -= app_eventsHandlerMethod;
                    break;
                case "DocumentOpened":
                    m_app.ControlledApplication.DocumentOpened -= app_eventsHandlerMethod;
                    break;
                case "DocumentClosing":
                    m_app.ControlledApplication.DocumentClosing -= app_eventsHandlerMethod;
                    break;
                case "DocumentClosed":
                    m_app.ControlledApplication.DocumentClosed -= app_eventsHandlerMethod;
                    break;
                case "DocumentSavedAs":
                    m_app.ControlledApplication.DocumentSavedAs -= app_eventsHandlerMethod;
                    break;
                case "DocumentSavingAs":
                    m_app.ControlledApplication.DocumentSavingAs -= app_eventsHandlerMethod;
                    break;
                case "DocumentSaving":
                    m_app.ControlledApplication.DocumentSaving -= app_eventsHandlerMethod;
                    break;
                case "DocumentSaved":
                    m_app.ControlledApplication.DocumentSaved -= app_eventsHandlerMethod;
                    break;
                case "DocumentSynchronizingWithCentral":
                    m_app.ControlledApplication.DocumentSynchronizingWithCentral -= app_eventsHandlerMethod;
                    break;
                case "DocumentSynchronizedWithCentral":
                    m_app.ControlledApplication.DocumentSynchronizedWithCentral -= app_eventsHandlerMethod;
                    break;
                case "FileExporting":
                    m_app.ControlledApplication.FileExporting -= app_eventsHandlerMethod;
                    break;
                case "FileExported":
                    m_app.ControlledApplication.FileExported -= app_eventsHandlerMethod;
                    break;
                case "FileImporting":
                    m_app.ControlledApplication.FileImporting -= app_eventsHandlerMethod;
                    break;
                case "FileImported":
                    m_app.ControlledApplication.FileImported -= app_eventsHandlerMethod;
                    break;
                case "DocumentPrinting":
                    m_app.ControlledApplication.DocumentPrinting -= app_eventsHandlerMethod;
                    break;
                case "DocumentPrinted":
                    m_app.ControlledApplication.DocumentPrinted -= app_eventsHandlerMethod;
                    break;
                case "ViewPrinting":
                    m_app.ControlledApplication.ViewPrinting -= app_eventsHandlerMethod;
                    break;
                case "ViewPrinted":
                    m_app.ControlledApplication.ViewPrinted -= app_eventsHandlerMethod;
                    break;
                case "ViewActivating":
                    m_app.ViewActivating -= app_eventsHandlerMethod;
                    break;
                case "ViewActivated":
                    m_app.ViewActivated -= app_eventsHandlerMethod;
                    break;
               case "ProgressChanged":
                    m_app.ControlledApplication.ProgressChanged -= app_eventsHandlerMethod;
                    break;

            }
        }

        /// <summary>
        /// Generic event handler can be subscribed to any events.
        /// It will dump events information(sender and EventArgs) to log window and log file
        /// </summary>
        /// <param name="obj"></param>
        /// <param name="args"></param>
        public void app_eventsHandlerMethod(Object obj, EventArgs args)
        {
            // generate event information and set to information window 
            // to track what event be touch off.
            ExternalApplication.EventLogManager.TrackEvent(obj, args);
            // write log file.
            ExternalApplication.EventLogManager.WriteLogFile(obj, args);
        }

        #endregion
    }
}

ExternalApplication.cs

//
// (C) Copyright 2003-2019 by Autodesk, Inc.
//
// Permission to use, copy, modify, and distribute this software in
// object code form for any purpose and without fee is hereby granted,
// provided that the above copyright notice appears in all copies and
// that both that copyright notice and the limited warranty and
// restricted rights notice below appear in all supporting
// documentation.
//
// AUTODESK PROVIDES THIS PROGRAM "AS IS" AND WITH ALL FAULTS.
// AUTODESK SPECIFICALLY DISCLAIMS ANY IMPLIED WARRANTY OF
// MERCHANTABILITY OR FITNESS FOR A PARTICULAR USE. AUTODESK, INC.
// DOES NOT WARRANT THAT THE OPERATION OF THE PROGRAM WILL BE
// UNINTERRUPTED OR ERROR FREE.
//
// Use, duplication, or disclosure by the U.S. Government is subject to
// restrictions set forth in FAR 52.227-19 (Commercial Computer
// Software - Restricted Rights) and DFAR 252.227-7013(c)(1)(ii)
// (Rights in Technical Data and Computer Software), as applicable.
//


using System;
using System.Collections.Generic;
using System.Text;
using System.Windows.Forms;
using System.Diagnostics;

using Autodesk.Revit;
using Autodesk.Revit.UI;
using Autodesk.Revit.ApplicationServices;

namespace Revit.SDK.Samples.EventsMonitor.CS
{
    /// <summary>
    /// A class inherits IExternalApplication interface and provide an entry of the sample.
    /// This class controls other function class and plays the bridge role in this sample.
    /// It create a custom menu "Track Revit Events" of which the corresponding 
    /// external command is the command in this project.
    /// </summary>
    [Autodesk.Revit.Attributes.Transaction(Autodesk.Revit.Attributes.TransactionMode.Manual)]
    [Autodesk.Revit.Attributes.Regeneration(Autodesk.Revit.Attributes.RegenerationOption.Manual)]
    [Autodesk.Revit.Attributes.Journaling(Autodesk.Revit.Attributes.JournalingMode.NoCommandData)]
    public class ExternalApplication : IExternalApplication
    {
        #region Class Member Variables
        /// <summary>
        /// A controlled application used to register the events. Because all trigger points
        /// in this sample come from UI, all events in application level must be registered 
        /// to ControlledApplication. If the trigger point is from API, user can register it 
        /// to Application or Document according to what level it is in. But then, 
        /// the syntax is the same in these three cases.
        /// </summary>
        private static UIControlledApplication m_ctrlApp;

        /// <summary>
        /// A common object used to write the log file and generate the data table 
        /// for event information.
        /// </summary>
        private static LogManager m_logManager;

        /// <summary>
        /// The window is used to show events' information.
        /// </summary>
        private static EventsInfoWindows m_infWindows;

        /// <summary>
        /// The window is used to choose what event to be subscribed.
        /// </summary>
        private static EventsSettingForm m_settingDialog;

        /// <summary>
        /// This list is used to store what user selected.
        /// It can be got from the selectionDialog.
        /// </summary>
        private static List<String> m_appEventsSelection;

        /// <summary>
        /// This object is used to manager the events in application level.
        /// It can be updated according to what user select.
        /// </summary>
        private static EventManager m_appEventMgr;

        // These #if directives within file are used to compile project in different purpose:
        // . Build project with Release mode for regression test,
        // . Build project with Debug mode for manual run
#if !(Debug || DEBUG)
        /// <summary>
        /// This object is used to make the sample can be autotest.
        /// It can dump the event list to file or commandData.Data
        /// and also can retrieval the list from file and commandData.Data.
        /// If you just pay attention to how to use events, 
        /// please skip over this class and related sentence.
        /// </summary>
        private static JournalProcessor m_journalProcessor;
#endif
        #endregion

        #region Class Static Property
        /// <summary>
        /// Property to get and set private member variable of InfoWindows
        /// </summary>
        public static EventsInfoWindows InfoWindows
        {
            get
            {
                if (null == m_infWindows)
                {
                    m_infWindows = new EventsInfoWindows(EventLogManager);
                }
                return m_infWindows;
            }
            set
            {
                m_infWindows = value;
            }
        }

        /// <summary>
        /// Property to get private member variable of SeletionDialog
        /// </summary>
        public static EventsSettingForm SettingDialog
        {
            get
            {
                if (null == m_settingDialog)
                {
                    m_settingDialog = new EventsSettingForm();
                }
                return m_settingDialog;
            }
        }

        /// <summary>
        /// Property to get and set private member variable of log data
        /// </summary>
        public static LogManager EventLogManager
        {
            get
            {
                if (null == m_logManager)
                {
                    m_logManager = new LogManager();
                }
                return m_logManager;
            }
        }

        /// <summary>
        /// Property to get and set private member variable of application events selection.
        /// </summary>
        public static List<String> ApplicationEvents
        {
            get
            {
                if (null == m_appEventsSelection)
                {
                    m_appEventsSelection = new List<string>();
                }
                return m_appEventsSelection;
            }
            set
            {
                m_appEventsSelection = value;
            }
        }

        /// <summary>
        /// Property to get private member variable of application events manager.
        /// </summary>
        public static EventManager AppEventMgr
        {
            get
            {
                if (null == m_appEventMgr)
                {
                    m_appEventMgr = new EventManager(m_ctrlApp);
                }
                return m_appEventMgr;
            }
        }

#if !(Debug || DEBUG)
        /// <summary>
        /// Property to get private member variable of journal processor.
        /// </summary>
        public static JournalProcessor JnlProcessor
        {
            get
            {
                if (null == m_journalProcessor)
                {
                    m_journalProcessor = new JournalProcessor();
                }
                return m_journalProcessor;
            }
        }
#endif
        #endregion

        #region IExternalApplication Members

        /// <summary>
        /// Implement this method to implement the external application which should be called when 
        /// Revit starts before a file or default template is actually loaded.
        /// </summary>
        /// <param name="application">An object that is passed to the external application 
        /// which contains the controlled application.</param> 
        /// <returns>Return the status of the external application. 
        /// A result of Succeeded means that the external application successfully started. 
        /// Cancelled can be used to signify that the user cancelled the external operation at 
        /// some point.
        /// If false is returned then Revit should inform the user that the external application 
        /// failed to load and the release the internal reference.</returns>
        public Autodesk.Revit.UI.Result OnStartup(UIControlledApplication application)
        {
            // initialize member variables.
            m_ctrlApp = application;
            m_logManager = new LogManager();
            m_infWindows = new EventsInfoWindows(m_logManager);
            m_settingDialog = new EventsSettingForm();
            m_appEventsSelection = new List<string>();
            m_appEventMgr = new EventManager(m_ctrlApp);

#if !(Debug || DEBUG)
            m_journalProcessor = new JournalProcessor();
#endif

            try
            {
#if !(Debug || DEBUG)
                // playing journal.
                if (m_journalProcessor.IsReplay)
                {
                    m_appEventsSelection = m_journalProcessor.EventsList;
                }
                
                // running the sample form UI.
                else
                {
#endif
                    m_settingDialog.ShowDialog();
                    if (DialogResult.OK == m_settingDialog.DialogResult)
                    {
                        //get what user select.
                        m_appEventsSelection = m_settingDialog.AppSelectionList;
                    }

#if !(Debug || DEBUG)
                    // dump what user select to a file in order to autotesting.
                    m_journalProcessor.DumpEventsListToFile(m_appEventsSelection);
                }
#endif
                
                // update the events according to the selection.
                m_appEventMgr.Update(m_appEventsSelection);

                // track the selected events by showing the information in the information windows.
                m_infWindows.Show();
              
                // add menu item in Revit menu bar to provide an approach to 
                // retrieve events setting form. User can change his choices 
                // by calling the setting form again.
                AddCustomPanel(application);
            }
            catch (Exception)
            {
                return Autodesk.Revit.UI.Result.Failed;
            }

            return Autodesk.Revit.UI.Result.Succeeded;
        }

        /// <summary>
        /// Implement this method to implement the external application which should be called when 
        /// Revit is about to exit,Any documents must have been closed before this method is called.
        /// </summary>
        /// <param name="application">An object that is passed to the external application 
        /// which contains the controlled application.</param>
        /// <returns>Return the status of the external application. 
        /// A result of Succeeded means that the external application successfully shutdown. 
        /// Cancelled can be used to signify that the user cancelled the external operation at 
        /// some point.
        /// If false is returned then the Revit user should be warned of the failure of the external 
        /// application to shut down correctly.</returns>
        public Autodesk.Revit.UI.Result OnShutdown(UIControlledApplication application)
        {
            // dispose some resource.
            Dispose();
            return Autodesk.Revit.UI.Result.Succeeded;
        }
        #endregion

        #region Class Methods
        /// <summary>
        /// Dispose some resource.
        /// </summary>
        public static void Dispose()
        {
            if (m_infWindows != null)
            {
                m_infWindows.Close();
                m_infWindows = null;
            }
            if (m_settingDialog != null)
            {
                m_settingDialog.Close();
                m_settingDialog = null;
            }
            m_appEventMgr = null;
            m_logManager.CloseLogFile();
            m_logManager = null;
        }

        /// <summary>
        /// Add custom menu.
        /// </summary>
        static private void AddCustomPanel(UIControlledApplication application)
        {
            // create a panel named "Events Monitor";
            string panelName = "Events Monitor";
            // create a button on the panel.
            RibbonPanel ribbonPanelPushButtons = application.CreateRibbonPanel(panelName);
            PushButtonData pushButtonData = new PushButtonData("EventsSetting", 
                "Set Events", System.Reflection.Assembly.GetExecutingAssembly().Location, 
                "Revit.SDK.Samples.EventsMonitor.CS.Command");
            PushButton pushButtonCreateWall = ribbonPanelPushButtons.AddItem(pushButtonData)as PushButton;
            pushButtonCreateWall.ToolTip = "Setting Events";
  
        }
        #endregion
    }
}

JournalProcessor.cs

//
// (C) Copyright 2003-2019 by Autodesk, Inc.
//
// Permission to use, copy, modify, and distribute this software in
// object code form for any purpose and without fee is hereby granted,
// provided that the above copyright notice appears in all copies and
// that both that copyright notice and the limited warranty and
// restricted rights notice below appear in all supporting
// documentation.
//
// AUTODESK PROVIDES THIS PROGRAM "AS IS" AND WITH ALL FAULTS.
// AUTODESK SPECIFICALLY DISCLAIMS ANY IMPLIED WARRANTY OF
// MERCHANTABILITY OR FITNESS FOR A PARTICULAR USE. AUTODESK, INC.
// DOES NOT WARRANT THAT THE OPERATION OF THE PROGRAM WILL BE
// UNINTERRUPTED OR ERROR FREE.
//
// Use, duplication, or disclosure by the U.S. Government is subject to
// restrictions set forth in FAR 52.227-19 (Commercial Computer
// Software - Restricted Rights) and DFAR 252.227-7013(c)(1)(ii)
// (Rights in Technical Data and Computer Software), as applicable.
//

using System;
using System.IO;
using System.Data;
using System.Collections.Generic;
using System.Text;
using System.Diagnostics;
using System.Reflection;
using System.Xml.Serialization;

using Autodesk.Revit;
using Autodesk.Revit.DB.Events;

namespace Revit.SDK.Samples.EventsMonitor.CS
{
    /// <summary>
    /// This class is implemented to make sample autotest.
    /// It checks whether the external file exists or not.
    /// The sample can control the UI's display by this judgement.
    /// It can dump the seleted event list to file or commandData.Data
    /// and also can retrieve the list from file and commandData.Data.
    /// </summary>
    public class JournalProcessor
    {
        #region Class Member Variables
        /// <summary>
        /// xml file name.
        /// </summary>
        private string m_xmlFile;

        /// <summary>
        /// xml serializer.
        /// </summary>
        private XmlSerializer m_xs;

        /// <summary>
        /// using UI or playing journal.
        /// </summary>
        private bool m_isReplay;

        /// <summary>
        /// events deserialized from xml file.
        /// </summary>
        private List<String> m_eventsInFile;

        /// <summary>
        /// direcotory of xml file.
        /// </summary>
        private string m_directory;
        #endregion

        #region Class Property
        /// <summary>
        /// Property to get private member variables to check the stauts is playing or recording.
        /// </summary>
        public bool IsReplay
        {
            get
            {
                return m_isReplay;
            }
        }

        /// <summary>
        /// Property to get private member variables of Event list.
        /// </summary>
        public List<String> EventsList
        {
            get
            {
                return m_eventsInFile;
            }
        }
        #endregion

        #region Class Constructor and Destructor
        /// <summary>
        /// Constructor without argument.
        /// </summary>
        public JournalProcessor()
        {
            m_xs = new XmlSerializer(typeof(List<String>));
            m_directory = Path.GetDirectoryName(System.Reflection.Assembly.GetExecutingAssembly().Location);
            m_xmlFile = Path.Combine(m_directory,"Current.xml");
            
            // if the external file is exist, it means playing journal now. No Setting Dialog will pop up.
            m_isReplay = CheckFileExistence();

            // get event list from xml file.
            GetEventsListFromFile();
        }
        #endregion

        #region Class Methods
        /// <summary>
        /// Check whether the xml file is exist or not.
        /// </summary>
        /// <returns></returns>
        private bool CheckFileExistence()
        {
            return File.Exists(m_xmlFile) ? true : false;
        }

        /// <summary>
        /// Get the event list from xml file.
        /// This method is used in ExternalApplication.
        /// </summary>
        private void GetEventsListFromFile()
        {
            if (m_isReplay)
            {
                Stream stream = new FileStream(m_xmlFile, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
                m_eventsInFile = (List<String>)m_xs.Deserialize(stream);
                stream.Close();
            }
            else
            {
                m_eventsInFile = new List<string>();
            }
        }

        /// <summary>
        /// Dump the selected event list to xml file.
        /// This method is used in ExternalApplication.
        /// </summary>
        /// <param name="eventList"></param>
        public void DumpEventsListToFile(List<String> eventList)
        {
            if (!m_isReplay)
            {
                string fileName =  DateTime.Now.ToString("yyyyMMdd") + ".xml";
                string tempFile =Path.Combine(m_directory ,fileName);
                Stream stream = new FileStream(tempFile, FileMode.OpenOrCreate, FileAccess.ReadWrite, FileShare.ReadWrite);
                m_xs.Serialize(stream, eventList);
                stream.Close();
            }
        }

        /// <summary>
        /// Get event list from commandData.Data.
        /// This method is used in ExternalCommmand.
        /// </summary>
        /// <param name="data"></param>
        /// <returns></returns>
        public List<String> GetEventsListFromJournalData(IDictionary<String, String> data)
        {
            List<String> eventList = new List<string>();
            foreach (KeyValuePair<string, string> kvp in data)
            {
               eventList.Add(kvp.Key);
            }
            return eventList;
        }

        /// <summary>
        /// Dump the selected event list to commandData.Data.
        /// This method is used in ExternalCommand.
        /// </summary>
        /// <param name="eventList"></param>
        /// <param name="data"></param>
        public void DumpEventListToJournalData(List<String> eventList, ref IDictionary<String, String> data)
        {
            foreach (String eventname in eventList)
            {
                data.Add(eventname, "1");
            }
        }
        #endregion
    }
}
 

LogManager.cs

//
// (C) Copyright 2003-2019 by Autodesk, Inc.
//
// Permission to use, copy, modify, and distribute this software in
// object code form for any purpose and without fee is hereby granted,
// provided that the above copyright notice appears in all copies and
// that both that copyright notice and the limited warranty and
// restricted rights notice below appear in all supporting
// documentation.
//
// AUTODESK PROVIDES THIS PROGRAM "AS IS" AND WITH ALL FAULTS.
// AUTODESK SPECIFICALLY DISCLAIMS ANY IMPLIED WARRANTY OF
// MERCHANTABILITY OR FITNESS FOR A PARTICULAR USE. AUTODESK, INC.
// DOES NOT WARRANT THAT THE OPERATION OF THE PROGRAM WILL BE
// UNINTERRUPTED OR ERROR FREE.
//
// Use, duplication, or disclosure by the U.S. Government is subject to
// restrictions set forth in FAR 52.227-19 (Commercial Computer
// Software - Restricted Rights) and DFAR 252.227-7013(c)(1)(ii)
// (Rights in Technical Data and Computer Software), as applicable.
//

using System;
using System.IO;
using System.Data;
using System.Collections.Generic;
using System.Text;
using System.Diagnostics;
using System.Reflection;

using Autodesk.Revit;
using Autodesk.Revit.DB.Events;

namespace Revit.SDK.Samples.EventsMonitor.CS
{
    /// <summary>
    /// This class implements all operators about writing log file and generating event 
    /// information for showing in the information window. This class is not the main one 
    /// just a assistant in this sample. If you just want to learn how to use Revit events,
    /// please pay more attention to EventManager class.
    /// </summary>
    public class LogManager
    {
        #region Class Member Variables
        /// <summary>
        /// data table for information windows.
        /// </summary>
        private DataTable m_eventsLog;

        /// <summary>
        /// add a trace listener.
        /// </summary>
        private TraceListener m_txtListener;

        /// <summary>
        /// path of temp file and log file
        /// </summary>
        private string m_filePath = Path.GetDirectoryName(System.Reflection.Assembly.GetExecutingAssembly().Location);

        /// <summary>
        /// a temp file to record log and before revit closed the temp file will be change to log file.
        /// This strategy can make the log file alway can be accessable.
        /// </summary>
        private string m_tempFile;
        #endregion

        #region Class Property
        /// <summary>
        /// Property to get and set private member variables of Event log information.
        /// </summary>
        public DataTable EventsLog
        {
            get
            {
                return m_eventsLog;
            }
        }
        #endregion

        #region Class Constructor and Destructor
        /// <summary>
        /// Constructor without argument.
        /// </summary>
        public LogManager()
        {
            //m_filePath = ;
            CreateLogFile();
            m_eventsLog = CreateEventsLogTable();
        }

        #endregion

        #region Class Methods
        /// <summary>
        /// Create a log file to track the subscribed events' work process.
        /// </summary>
        private void CreateLogFile()
        {
            m_tempFile = Path.Combine(m_filePath, "Temp.log");
            if (File.Exists(m_tempFile)) File.Delete(m_tempFile);
            m_txtListener = new TextWriterTraceListener(m_tempFile);
            Trace.Listeners.Add(m_txtListener);
        }

        /// <summary>
        /// Close the log file and remove the corresponding listener.
        /// </summary>
        public void CloseLogFile()
        {
            Trace.Flush();
            Trace.Listeners.Remove(m_txtListener);
            Trace.Close();
            m_txtListener.Close();

            string log = Path.Combine(m_filePath, "EventsMonitor.log");
            if (File.Exists(log)) File.Delete(log);
            File.Copy(m_tempFile, log);
            File.Delete(m_tempFile);
        }

        /// <summary>
        /// Generate a data table with four columns for display in window
        /// </summary>
        /// <returns>The DataTable to be displayed in window</returns>
        private DataTable CreateEventsLogTable()
        {
            // create a new dataTable
            DataTable eventsInfoLogTable = new DataTable("EventsLogInfoTable");

            // Create a "Time" column
            DataColumn timeColumn = new DataColumn("Time", typeof(System.String));
            timeColumn.Caption = "Time";
            eventsInfoLogTable.Columns.Add(timeColumn);

            // Create a "Event" column
            DataColumn eventColum = new DataColumn("Event", typeof(System.String));
            eventColum.Caption = "Event";
            eventsInfoLogTable.Columns.Add(eventColum);

            // Create a "Type" column
            DataColumn typeColum = new DataColumn("Type", typeof(System.String));
            typeColum.Caption = "Type";
            eventsInfoLogTable.Columns.Add(typeColum);

            // return this data table 
            return eventsInfoLogTable;
        }

        /// <summary>
        /// When any event which has been subscribed is fired, log its information.
        /// the information includes: machine name, user, time and event
        /// </summary>
        /// <param name="sender"> Event sender.</param>
        /// <param name="args">EventArgs of this event.</param>
        public void TrackEvent(Object sender, EventArgs args)
        {
            DataRow newRow = m_eventsLog.NewRow();

            // set the relative information of this event into the table.
            newRow["Time"] = System.DateTime.Now.ToString();
            newRow["Event"] = GetEventsName(args.GetType());
            newRow["Type"] = sender.GetType().ToString();

            m_eventsLog.Rows.Add(newRow);
        }

        /// <summary>
        /// Write log to file, event name and type will be dumped
        /// </summary>
        /// <param name="sender">Event sender.</param>
        /// <param name="args">EventArgs of this event.</param>
        public void WriteLogFile(Object sender, EventArgs args)
        {
            Trace.WriteLine("*********************************************************");
            if (null == args)
            {
                return;
            }
            // get this eventArgs's runtime type.
            Type type = args.GetType();
            String eventName = GetEventsName(type);
            Trace.WriteLine("Raised " + sender.GetType().ToString() + "." + eventName);
            Trace.WriteLine("---------------------------------------------------------");
            
            // 1: output sender's information
            Trace.WriteLine("  Start to dump Sender and EventAgrs of Event...\n");
            if (null != sender)
            {
                // output the type of sender
                Trace.WriteLine("    [Event Sender]: " + sender.GetType().FullName);
            }
            else
            {
                Trace.WriteLine("      Sender is null, it's unexpected!!!");
            }

            // 2: Output event argument
            // get all properties info of this argument.
            PropertyInfo[] propertyInfos = type.GetProperties();

            // output some typical property's name and value. (for example, Cancelable, Cancel,etc)
            foreach (PropertyInfo propertyInfo in propertyInfos)
            {
                try
                {
                    if (!propertyInfo.CanRead)
                    {
                        continue;
                    }
                    else
                    {
                        Object propertyValue;
                        String propertyName = propertyInfo.Name;
                        switch(propertyName)
                        {
                            case "Document":
                            case "Cancellable":
                            case "Cancel":
                            case "Status":
                            case "DocumentType":
                            case "Format":
                            propertyValue = propertyInfo.GetValue(args, null);
                            // Dump current property value
                            Trace.WriteLine("    [Property]: " + propertyInfo.Name);
                            Trace.WriteLine("    [Value]: " + propertyValue.ToString());
                            break;
                        }
                    }
                }
                catch (Exception ex)
                {
                    // Unexpected exception
                    Trace.WriteLine("    [Property Exception]: " + propertyInfo.Name + ", " + ex.Message);
                }
            }
        }

        /// <summary>
        /// Get event name from its EventArgs, without namespace prefix
        /// </summary>
        /// <param name="type">Generic event type.</param>
        /// <returns></returns>
        private String GetEventsName(Type type)
        {
            String argName = type.ToString();
            String tail = "EventArgs";
            String head = "Autodesk.Revit.DB.Events.";
            int firstIndex = head.Length;
            int length = argName.Length - head.Length - tail.Length;
            String eventName = argName.Substring(firstIndex, length);
            return eventName;
        }
        #endregion
    }
}

EventsInfoWindows.cs

//
// (C) Copyright 2003-2019 by Autodesk, Inc.
//
// Permission to use, copy, modify, and distribute this software in
// object code form for any purpose and without fee is hereby granted,
// provided that the above copyright notice appears in all copies and
// that both that copyright notice and the limited warranty and
// restricted rights notice below appear in all supporting
// documentation.
//
// AUTODESK PROVIDES THIS PROGRAM "AS IS" AND WITH ALL FAULTS.
// AUTODESK SPECIFICALLY DISCLAIMS ANY IMPLIED WARRANTY OF
// MERCHANTABILITY OR FITNESS FOR A PARTICULAR USE. AUTODESK, INC.
// DOES NOT WARRANT THAT THE OPERATION OF THE PROGRAM WILL BE
// UNINTERRUPTED OR ERROR FREE.
//
// Use, duplication, or disclosure by the U.S. Government is subject to
// restrictions set forth in FAR 52.227-19 (Commercial Computer
// Software - Restricted Rights) and DFAR 252.227-7013(c)(1)(ii)
// (Rights in Technical Data and Computer Software), as applicable.
//

 
namespace Revit.SDK.Samples.EventsMonitor.CS
{
    partial class EventsInfoWindows
    {
        /// <summary>
        /// Required designer variable.
        /// </summary>
        private System.ComponentModel.IContainer components = null;

        /// <summary>
        /// Clean up any resources being used.
        /// </summary>
        /// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
        protected override void Dispose(bool disposing)
        {
            if (disposing && (components != null))
            {
                components.Dispose();
            }
            base.Dispose(disposing);
        }

        #region Windows Form Designer generated code

        /// <summary>
        /// Required method for Designer support - do not modify
        /// the contents of this method with the code editor.
        /// </summary>
        private void InitializeComponent()
        {
            this.appEventsLogDataGridView = new System.Windows.Forms.DataGridView();
            this.timeColumn = new System.Windows.Forms.DataGridViewTextBoxColumn();
            this.eventColumn = new System.Windows.Forms.DataGridViewTextBoxColumn();
            this.typeColumn = new System.Windows.Forms.DataGridViewTextBoxColumn();
            ((System.ComponentModel.ISupportInitialize)(this.appEventsLogDataGridView)).BeginInit();
            this.SuspendLayout();
            // 
            // appEventsLogDataGridView
            // 
            this.appEventsLogDataGridView.AllowUserToAddRows = false;
            this.appEventsLogDataGridView.AllowUserToDeleteRows = false;
            this.appEventsLogDataGridView.BorderStyle = System.Windows.Forms.BorderStyle.Fixed3D;
            this.appEventsLogDataGridView.ColumnHeadersHeightSizeMode = System.Windows.Forms.DataGridViewColumnHeadersHeightSizeMode.AutoSize;
            this.appEventsLogDataGridView.Columns.AddRange(new System.Windows.Forms.DataGridViewColumn[] {
            this.timeColumn,
            this.eventColumn,
            this.typeColumn});
            this.appEventsLogDataGridView.Dock = System.Windows.Forms.DockStyle.Fill;
            this.appEventsLogDataGridView.Location = new System.Drawing.Point(0, 0);
            this.appEventsLogDataGridView.Margin = new System.Windows.Forms.Padding(2);
            this.appEventsLogDataGridView.Name = "appEventsLogDataGridView";
            this.appEventsLogDataGridView.ReadOnly = true;
            this.appEventsLogDataGridView.RowHeadersVisible = false;
            this.appEventsLogDataGridView.RowTemplate.Height = 24;
            this.appEventsLogDataGridView.SelectionMode = System.Windows.Forms.DataGridViewSelectionMode.FullRowSelect;
            this.appEventsLogDataGridView.Size = new System.Drawing.Size(475, 116);
            this.appEventsLogDataGridView.TabIndex = 0;
            this.appEventsLogDataGridView.RowsAdded += new System.Windows.Forms.DataGridViewRowsAddedEventHandler(this.appEventsLogDataGridView_RowsAdded);
            // 
            // timeColumn
            // 
            this.timeColumn.HeaderText = "Time";
            this.timeColumn.Name = "timeColumn";
            this.timeColumn.ReadOnly = true;
            this.timeColumn.Width = 120;
            // 
            // eventColumn
            // 
            this.eventColumn.HeaderText = "Event";
            this.eventColumn.Name = "eventColumn";
            this.eventColumn.ReadOnly = true;
            this.eventColumn.Width = 150;
            // 
            // typeColumn
            // 
            this.typeColumn.HeaderText = "Type";
            this.typeColumn.Name = "typeColumn";
            this.typeColumn.ReadOnly = true;
            this.typeColumn.Width = 200;
            // 
            // EventsInfoWindows
            // 
            this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F);
            this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
            this.ClientSize = new System.Drawing.Size(475, 116);
            this.Controls.Add(this.appEventsLogDataGridView);
            this.FormBorderStyle = System.Windows.Forms.FormBorderStyle.SizableToolWindow;
            this.Margin = new System.Windows.Forms.Padding(2);
            this.MaximizeBox = false;
            this.MinimizeBox = false;
            this.Name = "EventsInfoWindows";
            this.ShowIcon = false;
            this.ShowInTaskbar = false;
            this.Text = "Events History";
            this.TopMost = true;
            this.Shown += new System.EventHandler(this.applicationEventsInfoWindows_Shown);
            this.FormClosed += new System.Windows.Forms.FormClosedEventHandler(this.InformationWindows_FormClosed);
            ((System.ComponentModel.ISupportInitialize)(this.appEventsLogDataGridView)).EndInit();
            this.ResumeLayout(false);

        }

        #endregion

        private System.Windows.Forms.DataGridView appEventsLogDataGridView;
        private System.Windows.Forms.DataGridViewTextBoxColumn timeColumn;
        private System.Windows.Forms.DataGridViewTextBoxColumn eventColumn;
        private System.Windows.Forms.DataGridViewTextBoxColumn typeColumn;
    }
}

EventsSettingForm.cs

namespace Revit.SDK.Samples.EventsMonitor.CS
{
    partial class EventsSettingForm
    {
        /// <summary>
        /// Required designer variable.
        /// </summary>
        private System.ComponentModel.IContainer components = null;

        /// <summary>
        /// Clean up any resources being used.
        /// </summary>
        /// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
        protected override void Dispose(bool disposing)
        {
            if (disposing && (components != null))
            {
                components.Dispose();
            }
            base.Dispose(disposing);
        }

        #region Windows Form Designer generated code

        /// <summary>
        /// Required method for Designer support - do not modify
        /// the contents of this method with the code editor.
        /// </summary>
        private void InitializeComponent()
        {
            this.FinishToggle = new System.Windows.Forms.Button();
            this.checkAllButton = new System.Windows.Forms.Button();
            this.checkNoneButton = new System.Windows.Forms.Button();
            this.cancelButton = new System.Windows.Forms.Button();
            this.AppEventsCheckedList = new System.Windows.Forms.CheckedListBox();
            this.groupBox1 = new System.Windows.Forms.GroupBox();
            this.SuspendLayout();
            // 
            // FinishToggle
            // 
            this.FinishToggle.DialogResult = System.Windows.Forms.DialogResult.OK;
            this.FinishToggle.Location = new System.Drawing.Point(232, 225);
            this.FinishToggle.Name = "FinishToggle";
            this.FinishToggle.Size = new System.Drawing.Size(75, 23);
            this.FinishToggle.TabIndex = 1;
            this.FinishToggle.Text = "&OK";
            this.FinishToggle.UseVisualStyleBackColor = true;
            this.FinishToggle.Click += new System.EventHandler(this.FinishToggle_Click);
            // 
            // checkAllButton
            // 
            this.checkAllButton.Location = new System.Drawing.Point(317, 7);
            this.checkAllButton.Name = "checkAllButton";
            this.checkAllButton.Size = new System.Drawing.Size(75, 23);
            this.checkAllButton.TabIndex = 3;
            this.checkAllButton.Text = "&Select All";
            this.checkAllButton.UseVisualStyleBackColor = true;
            this.checkAllButton.Click += new System.EventHandler(this.checkAllButton_Click);
            // 
            // checkNoneButton
            // 
            this.checkNoneButton.Location = new System.Drawing.Point(317, 47);
            this.checkNoneButton.Name = "checkNoneButton";
            this.checkNoneButton.Size = new System.Drawing.Size(75, 23);
            this.checkNoneButton.TabIndex = 4;
            this.checkNoneButton.Text = "&Unselect All";
            this.checkNoneButton.UseVisualStyleBackColor = true;
            this.checkNoneButton.Click += new System.EventHandler(this.checkNoneButton_Click);
            // 
            // cancelButton
            // 
            this.cancelButton.Location = new System.Drawing.Point(317, 225);
            this.cancelButton.Name = "cancelButton";
            this.cancelButton.Size = new System.Drawing.Size(75, 23);
            this.cancelButton.TabIndex = 4;
            this.cancelButton.Text = "&Cancel";
            this.cancelButton.UseVisualStyleBackColor = true;
            this.cancelButton.Click += new System.EventHandler(this.cancelButton_Click);
            // 
            // AppEventsCheckedList
            // 
            this.AppEventsCheckedList.CheckOnClick = true;
            this.AppEventsCheckedList.FormattingEnabled = true;
            this.AppEventsCheckedList.Items.AddRange(new object[] {
            "DocumentCreating",
            "DocumentCreated",
            "DocumentOpening",
            "DocumentOpened",
            "DocumentClosing",
            "DocumentClosed",
            "DocumentSavingAs",
            "DocumentSavedAs",
            "DocumentSaving",
            "DocumentSaved",
            "FileExporting",
            "FileExported",
            "FileImporting",
            "FileImported",
            "DocumentPrinting",
            "DocumentPrinted",
            "ViewPrinting",
            "ViewPrinted",
            "ViewActivating",
            "ViewActivated",
            "DocumentSynchronizingWithCentral",
            "DocumentSynchronizedWithCentral",
            "ProgressChanged"});
            this.AppEventsCheckedList.Location = new System.Drawing.Point(7, 7);
            this.AppEventsCheckedList.Name = "AppEventsCheckedList";
            this.AppEventsCheckedList.Size = new System.Drawing.Size(304, 199);
            this.AppEventsCheckedList.TabIndex = 2;
            // 
            // groupBox1
            // 
            this.groupBox1.BackColor = System.Drawing.SystemColors.ActiveCaptionText;
            this.groupBox1.Location = new System.Drawing.Point(0, 218);
            this.groupBox1.Name = "groupBox1";
            this.groupBox1.Size = new System.Drawing.Size(406, 1);
            this.groupBox1.TabIndex = 5;
            this.groupBox1.TabStop = false;
            // 
            // ToggleForm
            // 
            this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F);
            this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
            this.ClientSize = new System.Drawing.Size(400, 254);
            this.Controls.Add(this.AppEventsCheckedList);
            this.Controls.Add(this.groupBox1);
            this.Controls.Add(this.checkAllButton);
            this.Controls.Add(this.FinishToggle);
            this.Controls.Add(this.checkNoneButton);
            this.Controls.Add(this.cancelButton);
            this.FormBorderStyle = System.Windows.Forms.FormBorderStyle.FixedDialog;
            this.MaximizeBox = false;
            this.MinimizeBox = false;
            this.Name = "ToggleForm";
            this.ShowInTaskbar = false;
            this.Text = "Events Tracking Setting";
            this.FormClosed += new System.Windows.Forms.FormClosedEventHandler(this.ToggleForm_FormClosed);
            this.ResumeLayout(false);

        }

        #endregion

        private System.Windows.Forms.Button FinishToggle;
        private System.Windows.Forms.Button checkAllButton;
        private System.Windows.Forms.Button checkNoneButton;
        private System.Windows.Forms.Button cancelButton;
        private System.Windows.Forms.CheckedListBox AppEventsCheckedList;
        private System.Windows.Forms.GroupBox groupBox1;

    }
}