C# Design Patterns: The Adapter Pattern
- Moving Data between Lists
- Making an Adapter
- Using the DataGrid
- Using a TreeView
- The Class Adapter
- Thought Question
The Adapter pattern is used to convert the programming interface of one class into that of another. We use adapters whenever we want unrelated classes to work together in a single program. The concept of an adapter is thus pretty simple: We write a class that has the desired interface and then make it communicate with the class that has a different interface.
There are two ways to do this: by inheritance and by object composition. In the first case, we derive a new class from the nonconforming one and add the methods we need to make the new derived class match the desired interface. The other way is to include the original class inside the new one and create the methods to translate calls within the new class. These two approaches, called class adapters and object adapters, are both fairly easy to implement.
Moving Data between Lists
Let's consider a simple program that allows you to select some names from a list to be transferred to another list for a more detailed display of the data associated with them. Our initial list consists of a team roster, and the second list has names with times or scores.
In this simple program, shown in Figure 14-1, the program reads in the names from a roster file during initialization. To move a name to the right-hand list box, you click on the name and then click on the arrow button. To move a name from the right-hand list box to the left-hand list, click on the name and then click on the back-arrow button.
Figure 14-1 A simple program to choose names for display
This is a very simple program to write in C#. It consists of the visual layout and action routines for each of the button clicks. When we read in the file of team roster data, we store each child's name and score in a Swimmer object and
then store all of these objects in an ArrayList collection called swdata. When you select one of the names to display in expanded form, you simply obtain the list index of the selected child from the left-hand list and get that child's data to display in the right-hand list.
private void btClone_Click(object sender, EventArgs e) { int i = lskids.SelectedIndex (); if( i >= 0) { Swimmer sw = swdata.getSwimmer (i); lsnewKids.Item.Add (sw.getName() +"\t"+sw.getTime ()); lskids.SelectedIndex = -1; } }
In a similar fashion, if we want to remove a name from the right-hand list, we just obtain the selected index and remove the name.
private void putBack_Click(object sender, EventArgs e) { int i = lsnewKids.SelectedIndex (); if(i >= 0) lsNewKids.Items.RemoveAt (i); }
Note that we obtain the column spacing between the two rows using the tab character. This works fine as long as the names are more or less the same length. However, if one name is much longer or shorter than the others, the list may end up using a different tab column, which is what happened here for the third name in the list.