Add a Custom Configuration Page

As you design your plugin, you may find that you want some way for the user to set preferences for the plugin. In STK, User Preferences are set using the Preferences panel under the Edit menu. You can add a page for your UI Plugin to this preferences panel.

Add a New User Control to the Project

  1. In the solution explorer, right click the project and select Add, then New Item.
  2. From the list of templates, select User Control.
  3. Give it a descriptive name, such as CustomConfigPage. Click Add.
  4. The newly created control will appear in design mode. Feel free to resize the page, add containers, buttons, text fields, etc. Add at least one textbox, and name it “txtboxDefaultFilePath.” There is no need to add OK, Apply, Cancel, and Help, as these buttons are already on the Preferences panel, outside the borders of your page.
  5. The new class doesn’t have any of our convenient using directives. Add AGI.Ui.Plugins:
    [C#]
    using AGI.Ui.Plugins;
    
    [Visual Basic .NET]
    Imports AGI.Ui.Plugins
    
  6. Now that you have a Config Page, the UI Plugin needs to understand that this is its config page, and should be displayed when the user opens the STK Preferences panel. In the MyCSharpUIPlugin class, locate the IAgUiPlugin interface's OnDisplayConfigurationPage handler and modify it to match the following:
    [C#]
    public void OnDisplayConfigurationPage(IAgUiPluginConfigurationPageBuilder ConfigPageBuilder)
    {
        ConfigPageBuilder.AddCustomUserControlPage(this, this.GetType().Assembly.Location, typeof(CustomConfigPage).FullName, "My UI Plugin Config Page");
    }
    
    [Visual Basic .NET]
    Public Sub OnDisplayConfigurationPage(ConfigPageBuilder As AGI.Ui.Plugins.IAgUiPluginConfigurationPageBuilder) Implements AGI.Ui.Plugins.IAgUiPlugin.OnDisplayConfigurationPage
        ConfigPageBuilder.AddCustomUserControlPage(Me, Me.GetType().Assembly.Location, GetType(CustomConfigPage).FullName, "My UI Plugin Config Page")
    End Sub
    

Build your project, then start up STK. Click the Edit menu, then Preferences. In the left-hand column, you should see your new item, "My UI Plugin Config Page." Click that item, and you should see the config page you designed. At this point, you have a form that takes inputs, but nothings that saves or uses those inputs. That will be covered in the following sections.

Implement the Config Page Actions Interface

Your plugin can launch a config page, but that config page can't communicate any changes back to the parent plugin. You have OK and Cancel buttons, but all they do is close the page. You also have Apply and Help buttons; they don't do anything, either. The missing piece is the implementation of the IAgUiPluginConfigurationPageActions interface, which will allow the config page to communicate with the plugin class.

  1. In the CustomConfigPage class, locate the CustomConfigPage class definition. Add the IAgUiPluginConfigurationPageActions interface:
    [C#]
    public partial class CustomConfigPage : UserControl, IAgUiPluginConfigurationPageActions
    
    [Visual Basic .NET]
    Public Class CustomConfigPage
        Implements IAgUiPluginConfigurationPageActions
    
  2. For C#, right-click the interface (IAgUiPluginConfigurationPageActions). Select Implement Interface, then Implement Interface again. For VB, at the end of the Implements line, hit the Enter key.

    This will implement the IAgUiPluginConfigurationPageActions interface, exposing its members:

    1. OnCreated is called when the user loads the page. This method is a good place to populate the fields on your page with initial values. In this example, a text box on the config page (txtboxDefaultFilePath) is given the initial value of filePath, a property of the MySampleUIPlugin class.
      [C#]
      public class MySampleUIPlugin: IAgUiPlugin, IAgUiPluginCommandTarget
      {
          public string m_filePath = "Sample string";
      
          public string filePath
          {
              get { return m_filePath; }
              set { m_filePath = value; }
          }
      
          ...
      }
      
      
      public partial class CustomConfigPage : UserControl, IAgUiPluginConfigurationPageActions
      {
          IAgUiPluginConfigurationPageSite m_site;
          MySampleUIPlugin m_plugin;
      
          ...
      
          public void OnCreated(IAgUiPluginConfigurationPageSite Site)
          {
              m_site = Site;
              m_plugin = m_site.Plugin as MySampleUIPlugin;
              txtboxDefaultFilePath.Text = m_plugin.filePath;
          }
      
          ...
      }
      
      [Visual Basic .NET]
      Public Class MySampleUIPlugin
          Implements IAgUiPlugin, IAgUiPluginCommandTarget
      
          Dim m_filePath As String = "Sample string"
      
          Public Property filePath() As String
              Get
                  Return m_filePath
              End Get
              Set(ByVal value As String)
                  m_filePath = value
              End Set
          End Property
          
          ...
          
      End Class
      
      
      Public Class CustomConfigPage
          Implements IAgUiPluginConfigurationPageActions
      
          Dim m_site As IAgUiPluginConfigurationPageSite
          Dim m_plugin As MySampleUIPlugin
      
          ...
      
          Public Sub OnCreated(Site As AGI.Ui.Plugins.IAgUiPluginConfigurationPageSite) Implements AGI.Ui.Plugins.IAgUiPluginConfigurationPageActions.OnCreated
              m_site = Site
              m_plugin = m_site.Plugin
              txtBoxDefaultFilePath.Text = m_plugin.filePath
          End Sub
          
          ...
          
      End Class
      
    2. OnCancel is called when the user clicks Cancel, before STK closes the Preferences panel.
    3. OnApply is called when the user clicks Apply or OK.
    4. OnOK is called when the user clicks OK, after OnApply is called and before STK closes the preferences panel.

Build your project, then start up STK. Click the Edit menu, then Preferences, then your config page. The initial value of your filePath string ("Sample string") should appear in the textbox. You can type in the box, but haven't implemented OnOK or OnApply methods to take those edits and pass them back to the plugin filePath property. Feel free to do that now, then rebuild and check your work in STK. User changes to the config page will only apply to the current STK session. To save user changes to the config page after STK is shut down, see the next section.

Note that the Apply button is grayed out by default. To enable the Apply button, you must call Site.SetModified(true). Add event handlers that listen for changes to any of the options on your config page, then use those handlers to set that modified flag to true. When the user clicks OK, Apply, or Cancel, STK will set the flag back to false.

Also note that the Help button is grayed out. To enable the Help button, implement the IAgUiPluginConfigurationPageActions2 interface. IAgUiPluginConfigurationPageActions2 extends IAgUiPluginConfigurationPageActions, meaning it contains all the methods of IAgUiPluginConfigurationPageActions, plus it has the additional method OnHelp. If the plugin implements IAgUiPluginConfigurationPageActions2, the Help button will be enabled. The programmer may use the OnHelp method to provide assistance to the user in any number of forms. For information about loading Microsoft chm (Compiled HTML) Help files, see Link to a .chm Help File.

Save User Preferences

STK does not automatically save any of the values entered on the config page. The programmer has two options for preserving the user preferences from one STK session to the next:

  1. Create and manage a preferences file that the plugin will read when the plugin starts up, and write when the user clicks OK or Apply.
  2. Implement the IAgUtPluginConfig interface, using the AgAttrBuilder to add your fields to the Attribute Scope, which is saved by the STK preferences framework.
The first option will not be discussed here. The second follows.

Change the Class Interface Type

In order for STK to access the attribute scope defined by the MySampleUIPlugin class, the class must expose a dispatch interface to COM clients. To do this, change the ClassInterfaceType from None to AutoDispatch:

[C#]
[ClassInterface(ClassInterfaceType.AutoDispatch)]
[Visual Basic .NET]
ClassInterface(ClassInterfaceType.AutoDispatch)> _

Add References

  1. Right-click References in the Solution Explorer and select Add Reference...
  2. On the COM tab, select AGI AgUtPlugin 10.
  3. When you click OK, AGI.Attr and AGI.Plugin will be added to your project references.
  4. Add the corresponding using directives/imports statements to the MySampleUIPlugin class:
    [C#]
    using AGI.Attr;
    using AGI.Plugin;
    
    [Visual Basic .NET]
    Imports AGI.Attr
    Imports AGI.Plugin
    

Implement the IAgUtPluginConfig Interface

The IAgUtPluginConfig interface provides the ability to create an attribute scope for the plugin. Attributes within that scope will be saved by the STK preferences structure. In this section, we will add the filePath property as an attribute to the scope.

  1. Append the IAgUtPluginConfig interface name to the MySampleUIPlugin class declaration:
    [C#]
    public class MySampleUIPlugin: IAgUiPlugin, IAgUiPluginCommandTarget, IAgUtPluginConfig
    
    [Visual Basic .NET]
    Public Class MySampleUIPlugin
        Implements IAgUiPlugin, IAgUiPluginCommandTarget, IAgUtPluginConfig
    
  2. For C#, right-click the interface (IAgUtPluginConfig). Select Implement Interface, then Implement Interface again. For VB, at the end of the Implements IAgUtPluginConfig line, hit the Enter key.

    This will implement the IAgUtPluginConfig interface, exposing its members.

  3. Declare a class variable representing the attribute scope:
    [C#]
    Object m_scope;
    
    [Visual Basic .NET]
    Dim m_scope As Object
    
  4. Edit the GetPluginConfig method to add the filePath string property to the attribute scope:
    [C#]
    public object GetPluginConfig(AgAttrBuilder pAttrBuilder)
    {
        if (m_scope == null)
        {
            m_scope = pAttrBuilder.NewScope();
            pAttrBuilder.AddStringDispatchProperty(m_scope, "name as string", "description", "filePath", (int)AgEAttrAddFlags.eAddFlagNone);
        }
    
        return m_scope;
    }
    
    [Visual Basic .NET]
    Public Function GetPluginConfig(pAttrBuilder As AgAttrBuilder) As Object Implements AGI.Plugin.IAgUtPluginConfig.GetPluginConfig
        If m_scope Is Nothing Then
            m_scope = pAttrBuilder.NewScope()
            pAttrBuilder.AddStringDispatchProperty(m_scope, "name as string", "description", "filePath", CInt(AgEAttrAddFlags.eAddFlagNone))
        End If
        Return m_scope
    End Function
    
  5. Edit the VerifyPluginConfig method as follows:
    [C#]
    public void VerifyPluginConfig(AgUtPluginConfigVerifyResult pPluginCfgResult)
    {
        pPluginCfgResult.Result = true;
        pPluginCfgResult.Message = "OK";
    }
    
    [Visual Basic .NET]
    Public Sub VerifyPluginConfig(pPluginCfgResult As AgUtPluginConfigVerifyResult) Implements AGI.Plugin.IAgUtPluginConfig.VerifyPluginConfig
        pPluginCfgResult.Result = True
        pPluginCfgResult.Message = "OK"
    End Sub
    
  6. Save and build the project. Start up STK, and note that the string in the preferences panel is the default "Sample string." Change the string, click OK, and shut down STK. Upon reloading STK, the preferences panel should reflect your new string.

The preferences information for your plugin is stored in the same location as the native STK preferences: <STK User Dir>\Config\STK Prefs.xml. If you read through the XML, you'll find the section where the MySampleUIPlugin preferences are defined:

<UiPluginSection Version = "1.0">
    <MyCompany.MySampleUIPlugin>
        <HostSettings Enabled = "TRUE" />
        <UiPluginSettings>
            <SCOPE>
                <VAR name = "name as string">
                    <STRING>&quot;Test String Value&quot;</STRING>
                </VAR>
            </SCOPE>
        </UiPluginSettings>
    </AGI.Dana.VB_Prefs>
</UiPluginSection>

Note that the property was added using the AddStringDispatchProperty method, and in the XML, it's explicitely tagged as a string. Different methods are required to add attributes of different data types. See the IAgAttrBuilder interface definition for more information.




<<Previous

Add a Custom User Control

Related Topics:

STK 11.2.1 Programming Interface