1.4 EditandUpdateDataUsingBoundControls Although viewing data is fine in some situations, the real power comes in being able to edit the data in the text box andupdate the data in the server. In this How-To, you learn just that, using some new methods and properties from the various data controls, including autogenerated commands that create update, insert, and delete SQL statements for you. This How-To also introduces you to the BinderContext class, which is used to perform updates with bound controls. The form as created in How-To 1.4 is great if you just want to view data for various records. But what if you want to let users editandupdate the data? Technique Continuing with the form you used in the previous How-Tos, you are going to add a few command buttons with code that will perform the following: • Edit. Toggle the look of the text boxes to let the user know that he can edit the data in the controls by giving the controls a sunken look. • Save. Save the changes made to the data back to the server. Then toggle the look of the text boxes back to flat so that the user knows he can't edit them. • Cancel. Toggle the text boxes back to flat so that the user knows he can't edit them anymore, but don't save the data. It is important to let users know when they can editand when they can't. By toggling the style of the text boxes between flat and sunken and the color between gray and white, users have a definite clue that they can edit the data at certain times (see Figure 1.8). Another useful item to note about this How-To is the introduction of the BindingContext class. This class helps you work with databound controls. Each control on a Windows form has a BindingContext object as well as BindingContext objects for any controls that are contained within that control. Each form also has a BindingContext object. BindingContext objects manage BindingManagerBase class object(s) for each control. Through the BindingContext object, you can manage editing and updating data back to the server. BindingManagerBase objects help with synchronization of datasets with controls. You are going to use the BindingContext class throughout the rest of this chapter, but only a couple of methods. Steps Open the solution for the chapter called "VB .NET How-To Chapter 1," and run the application. From the main form, click the command button with the caption "How-To 1.4." Click the Load List button. Along with the list being filled with customers whose names start with A, you will see the detail How-To fill in on the right side of the form with the first customer in the list. Click Edit. You will now be able to change the data in the text boxes. After you have changed a couple of fields, click Save. If you select another customer from the list box, select the one you changed. You will see that your changes have in fact been saved. If you click Cancel instead of Save, your changes will not be saved. Note that if you change the name of the customer, you must load the list again to see the changes in the list box. 1. Add the three command buttons to your form as described in Table 1.6 and as displayed in Figure 1.8. Table 1.6. Command Buttons to Edit, Save, and Cancel Changes to Data Object Property Setting Command Button Name btnEdit Caption &Edit Command Button Name btnSave Caption &Save Command Button Name btnCancel Caption &Cancel 2. Add the code shown in Listing 1.6 to the btnEdit Click event. Listing 1.6 frmHowTo1_4.vb: Calling the ActiveEditing Subroutine from the btnEdit Command Button Private Sub btnEdit_Click(ByVal sender As System.Object, _ ByVal e As System.EventArgs) Handles btnEdit.Click '- Enable the editing of the form ActivateEditing(True) End Sub This calls the routine called ActivateEditing, listed here. This code iterates through all the controls on the form and uses the TypeOf condition to check whether the current control is a text box. It also ensures that the control is not the txtCustLimit text box. If the control is a text box and the parameter called bEnable has been passed in as True, then the sunken look is given to the text box using the BorderStyle and the BackColor property is set to white. Otherwise, the BorderStyle is set to FixedSingle, which is flat, and the BackColor is set to the backcolor of the form. The Enabled property of the text box is set to whatever bEnabled is: True or False. Listing 1.7 frmHowTo1_4.vb: Toggling the Enabled Property and Look of Text Boxes Private Sub ActivateEditing(ByVal bEnable As Boolean) Dim oCurr As Object '- Loop through each of the controls on the form For Each oCurr In Me.Controls() '- Check to see if the control is a text box If TypeOf oCurr Is TextBox And oCurr.Name <> "txtCustLimit" Then '- If so, toggle the properties If bEnable Then oCurr.BorderStyle() = _ System.Windows.Forms.BorderStyle.Fixed3D oCurr.BackColor() = System.Drawing.Color.White Else oCurr.BorderStyle() = _ System.Windows.Forms.BorderStyle.FixedSingle oCurr.BackColor() = Me.BackColor End If oCurr.Enabled = bEnable End If Next End Sub 3. Add the code to the Click event of the btnSave command button. This code calls a new routine called SaveRecord, which performs the actual save. The ActivateEditing is then called, passing False to disable the controls because you are finished editing. Listing 1.8 frmHowTo1_4.vb: Calling the SaveRecord Routine and Disabling the Text Boxes by Calling ActivateEditing Private Sub btnSave_Click(ByVal sender As System.Object, _ ByVal e As System.EventArgs) Handles btnSave.Click '- Save the information SaveRecord() '- Disable the text boxes ActivateEditing(False) End Sub Following is the code for the subroutine called SaveRecord. This routine calls the EndCurrentEdit method of the BindingContext class, passing in the dataset called dsCustomerIndividual, and specifying the Customers table. Then the Update method is called off the data adapter called odaCustomerIndividual, passing the same parameters. This updates the changes back to the dataset. Finally, the dataset changes are sent backto the server. Listing 1.9 frmHowTo1_4.vb: Saving the Data Back to the Server Private Sub SaveRecord() '- Use the BindingContext class to end current editing ' so that we can update the server. Me.BindingContext(Me.dsCustomerIndividual, "Customers").EndCurrentEdit() '- Perform the requested task at the dataset ' level using the data adapter Me.odaCustomerIndividual.Update(Me.dsCustomerIndividual, "Customers") '- By accepting the changes, the data gets sent back to the server Me.dsCustomerIndividual.AcceptChanges() End Sub Note If you haven't read about ADO.NET yet, then you might be confused about doing an update to the dataset, accepting changes, and sending the changes back to the server. ADO.NET works using disconnected data. When you create a dataset by using a data adapter, the data is actually created using XML. To see proof of this, take a look at dsCustomerIndividual.xsd, found in the Solutions Explorer. <xsd:schemaid="dsCustomerIndividual"targetNamespace="http://w ww.tempuri.org / dsCustomerIndividual.xsd"xmlns="http://www.tempuri.org/ dsCustomerIndividual.xsd"xmlns: xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com: xml-msdata"attributeFormDefault="qualified" elementFormDefault="qualified"> <xsd:element name="dsCustomerIndividual" msdata:IsDataSet="true"> <xsd:complexType> <xsd:choice maxOccurs="unbounded"> <xsd:element name="Customers"> <xsd:complexType> <xsd:sequence> <xsd:element name="CustomerID" type="xsd:string" /> <xsd:element name="CompanyName" type="xsd:string" /> <xsd:element name="ContactName" type="xsd:string" minOccurs="0" /> <xsd:element name="ContactTitle" type="xsd:string" minOccurs="0" /> <xsd:element name="Address" type="xsd:string" minOccurs="0" /> <xsd:element name="City" type="xsd:string" minOccurs="0" /> <xsd:element name="Region" type="xsd:string" minOccurs="0" /> <xsd:element name="PostalCode" type="xsd:string" minOccurs="0" /> <xsd:element name="Country" type="xsd:string" minOccurs="0" /> <xsd:element name="Phone" type="xsd:string" minOccurs="0" /> <xsd:element name="Fax" type="xsd:string" minOccurs="0" /> </xsd:sequence> </xsd:complexType> </xsd:element> </xsd:choice> </xsd:complexType> <xsd:unique name="Constraint1" msdata:PrimaryKey="true"> <xsd:selector xpath=".//Customers" /> <xsd:field xpath="CustomerID" /> </xsd:unique> </xsd:element> </xsd:schema> This is all performed under the covers, so the good news is that you don't have to know XML to work with datasets and ADO. More information on this can be found in Chapter 3. 4. The last task is to give you the capibility to cancel the edits. You do this by placing the following code in the Click event on btnCancel. Calling the CancelCurrentEdit method of the BindingContext object for the form, the current edits are cancelled. Next, the text boxes are disabled using the routine ActivateEditing. Listing 1.10 frmHowTo1_4.vb: Canceling Changes to Dataand Disabling the Text Boxes Again Private Sub btnCancel_Click(ByVal sender As System.Object, _ ByVal e As System.EventArgs) Handles btnCancel.Click '- Use the BindingContext class to cancel the current editing. Me.BindingContext(Me.dsCustomerIndividual, _ "Customers").CancelCurrentEdit() ActivateEditing(False) End Sub How It Works When the user clicks the btnEdit button, the ActiveEditing routine alerts the user that he can edit the data in the text boxes. The text boxes are enabled. If the user then clicks the btnSave button, the data is updated to the dataset and then back to the server. If the user clicks the btnCancel button, the edits are canceled. In both cases, the ActivateEditing routine is called to disable the text boxes and let the user know that the text boxes cannot be edited. Comments This How-To showed the bare bones for editing and updating data. It presented a basic technique to get started. As you continue, you will learn methods to add and delete records, as well as handle errors. Using ADO.NET, which you use for bound controls, takes some getting used to if you have worked with other data accessing methods such as ADO and DAO. The BindingContext and BindingManagerBase objects make working with bound objects in code much more manageable. . 1.4 Edit and Update Data Using Bound Controls Although viewing data is fine in some situations, the real power comes in being able to edit the data in. text box and update the data in the server. In this How-To, you learn just that, using some new methods and properties from the various data controls,