The Credential Input Form
Now, take a look at the credential form. Open it in its default state by launching the demo application and selecting the Change button on the main form (see Figure 2
|Figure 3. The ConnectionStringManager Control: This exploded view describes each embedded sub-control. Exposed properties let you set the access level of each of these sub-controls individually.|
Contrary to what you might expect, there are only three controls on the credential form—a ConnectionStringManager, an OK button, and a Cancel button. The paucity of controls means you need very little custom code to implement a similar form in your own projects; it's quick and easy to instrument, because the ConnectionStringManager control handles displaying, arranging, and populating all the sub-controls that users interact with. Before discussing how to create and connect such a form though, consider the exploded view of the ConnectionStringManager control shown in Figure 3
, which individually delineates each sub-control within the ConnectionStringManager. You have the ability to adjust the access level of each sub-control.
By default, all sub-controls have the access level set to Edit
; this corresponds to the Credential Mode of Full Access
on the main form (Figure 1
). The other Credential Mode options on the main form selectively adjust the access level of all the input fields in various combinations. Besides the input fields, there are several accessory sub-controls (shown in blue in Figure 3
). The Accessories section on the main form provides individual checkboxes that display or hide three of these sub-controls. You can hide the fourth—the descriptive label—by setting the label to an empty string.
Choosing to make the test button/status indicator visible gives users a convenient way to check their credentials without leaving the form. The test button's color provides immediate visual feedback. It starts out gray (status disabled), and turns orange (status unknown) only after users have entered data in all the appropriate fields. Of course, the list of "appropriate fields" varies based on what a user has selected. For example, if users select Oracle as the database type then they must enter a username, password, and server, but because Oracle does not have the concept of database names, the database selector is disabled. After the button turns orange, users may click it to attempt to connect to the specified system.
When the connection succeeds, the button changes to green; otherwise, it turns red and opens a .NET ErrorProvider, shown in the exploded view of Figure 3
(the red exclamation symbol). The ConnectionStringManager uses that same error message to populate the separate result text box near the bottom of the control. Figure 3
shows several typical status messages in the result text box. You may hide the result text box if you want a more compact form, but it does offer an easy way for users to copy error messages. If you hide the test button, users have no way to test the connection or get error messages.
Both the ErrorProvider and the result text box fulfill one other purpose. In a SQL Server context, you may select a database using the ComboBox dropdown sub-control on the form. This ComboBox remains empty unless and until the user attempts to open the dropdown. At that point, the ConnectionStringManager initiates a quick dialog with the database and, if successful, populates the ComboBox with the list of available databases. If that process fails, both the ErrorProvider and the result text box display an error message.
Note that to retrieve the database list, the control must have all the requisite credentials available; it will remain disabled until that condition is satisfied. In other words, the ConnectionStringManager enables the test button and the database ComboBox only after users have filled out enough of the form to be able to attempt a database connection. (The criteria are almost identical: the test button needs everything the ComboBox needs, plus a value in the ComboBox itself.) The code below shows the logic used to enable both controls:
dbComboBox.Enabled = (
(serverTextBox.TextLength > 0) &&
dbType == DBTypes.Oracle
&& usernameTextBox.TextLength > 0
&& passwordTextBox.TextLength > 0
dbType == DBTypes.SqlServer
|| (usernameTextBox.TextLength > 0
&& passwordTextBox.TextLength > 0)
testButton.Enabled = (dbComboBox.Enabled &&
dbComboBox.SelectedIndex >= 0);
The preceding code works whether or not sub-controls are enabled or even visible. So for example, if you do not display or enable the username field, but it's empty, and you are using SQL Server authentication, the control will never enable the database dropdown and the test button. The point is that it's your responsibility to ensure that any fields not exposed are nevertheless still set correctly.