Using ValueConverter to Show/Hide Element in Silverlight (MVVM)


One of my reader “Girish” recently contacted me with a problem statement. His problem is, he wants to show a TextBox on selection of “Others” from a ComboBox and I informed him to use a ValueConverter and also told him, I will do a blog post on it, so that he can understand each step from that.

 

This post I am dedicating to him. May be, some other people who are new to Silverlight can get benefit from it. Read the full post to learn the process to do it.

 

Background

Let us understand, what we want to do. We need to create a UI. There will be a ComboBox having some countries list. If the Country name is not listed there, the user will chose “Others” from the dropdown menu. On selection of “Others”, it will show a TextBox below the ComboBox where he can enter the desired Country name.

 

Here is what we want to demonstrate:

 

image

 

 

MVVM Project Structure

Generally it is simple to do in normal way, but we will see it in action using proper MVVM way. Let’s structure our project as below:

 

image

  • First of all, we need the “View”. Let us have a “MainView.xaml” where we will have a ComboBox and a TextBox
  • Create the ViewModel for the “MainView” and name it as “MainViewModel.cs”
  • We need the Model named “Country”, which will have some properties to store the Country name & Country code
  • We need a provider called “CountryService.cs” to return the Countries list to the client. Here we will return some hard coded values
  • We need a ValueConverter which will return Visibility.Visible or Visibility.Collapsed based on the Country code

 

Play with the Code

Let us start playing with the code. First create the Model “Country” having two properties “DisplayText” and “CodeName”. DisplayText will return the Country name and the CodeName will return the code name of the Country. CodeName will help us to do the business logic.

 

Here is the code:

 
namespace CountrySelectionDemo.Models
{
    public class Country
    {
        public string DisplayText { get; set; }
        public string CodeName { get; set; }
    }
}

 

As mentioned earlier, we are going to return some hard coded Country names for our sample application. Create a Static class called “CountryService” and call the GetList() method to return a collection of Countries. Here is the code of that:

 

using System.Collections.ObjectModel;
using CountrySelectionDemo.Models;
 
namespace CountrySelectionDemo.Providers
{
    public static class CountryService
    {
        public static ObservableCollection<Country> GetList()
        {
            return new ObservableCollection<Country>
               {
                   new Country {DisplayText = "India", CodeName = "IN"},
                   new Country {DisplayText = "Srilanka", CodeName = "SL"},
                   new Country {DisplayText = "Bangladesh", CodeName = "BD"},
                   new Country {DisplayText = "China", CodeName = "CH"},
                   new Country {DisplayText = "Pakistan", CodeName = "PK"},
                   new Country {DisplayText = "United States of America", CodeName = "US"},
                   new Country {DisplayText = "United Kingdom", CodeName = "UK"},
                   new Country {DisplayText = "Others", CodeName = "OTHERS"},
               };

}

    }
}

 

We need the ValueConverter, which will be able to convert the Country CodeName to Visibility. In all the case, it will return Visibility.Collapsed but when the CodeName is “Others” or something like that (depends on your actual code) return Visibility.Visible.

 

See the below code for details:

 

using System;
using System.Globalization;
using System.Windows;
using System.Windows.Data;
 
namespace CountrySelectionDemo.Converters
{
    public class CountryCodeToVisibilityConverter : IValueConverter
    {
        public object Convert(object value, Type targetType,
                                object parameter, CultureInfo culture)
        {
            if (value != null && value.ToString().Equals("OTHERS"))
            {
                return Visibility.Visible;
            }
            return Visibility.Collapsed;
        }
 
        public object ConvertBack(object value, Type targetType,
                                    object parameter, CultureInfo culture)
        {
            throw new NotImplementedException();
        }
    }
}

 

 

Now, we will implement the ViewModel. It will have a Countries list. Call the service to fetch the country details and store them in the Countries property, as shown below:

 

using System.Collections.ObjectModel;
using CountrySelectionDemo.Models;
using CountrySelectionDemo.Providers;
 
namespace CountrySelectionDemo.ViewModels
{
    public class MainViewModel
    {
        public ObservableCollection<Country> Countries { get; set; }
 
        public MainViewModel()
        {
            Countries = CountryService.GetList();
        }
    }
}

 

Come to the View. In the view, we need to include the xmlns namespace for the ViewModel and the Converter. Create the StaticResource of MainViewModel and CountryCodeToVisibilityConverter, as shown below and set the DataContext of the LayoutRoot Grid to the MainViewModel.

 

image

 

As shown in the above screenshot, set the ItemsSource of the ComboBox to Countries, which is available in your ViewModel as a Property. Set the DisplayMemberPath to “DisplayText”. This will show the Country name to the screen. Set SelectedValuePath to “CodeName”. This step will set the CodeName as value of each combo box item, so that, we will be able to get the SelectedValue of the dropdown to do our business logic.

 

After this, set the Binding of the TextBox visibility. It should bind the SelectedValue of the ComboBox as the Visibility with the Conversion logic written in the CountryCodeToVisibilityConverter. See the above code snapshot.

 

Here is the full code of the XAML page i.e. View:

 

<UserControl x:Class="CountrySelectionDemo.Views.MainView"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:viewModels="clr-namespace:CountrySelectionDemo.ViewModels"
    xmlns:converters="clr-namespace:CountrySelectionDemo.Converters" 
    Height="80" Width="305">
    <UserControl.Resources>
        <viewModels:MainViewModel x:Key="mainViewModel"/>
        <converters:CountryCodeToVisibilityConverter 
                    x:Key="countryCodeToVisibilityConverter"/>
    </UserControl.Resources>
    <Grid x:Name="LayoutRoot" Background="White" 
          DataContext="{StaticResource mainViewModel}">
        <StackPanel Orientation="Vertical">
            <StackPanel Orientation="Horizontal">
                <TextBlock Text="Select Country:" Height="25" Margin="5"/>
                <ComboBox x:Name="comboBox" ItemsSource="{Binding Countries}"
                          DisplayMemberPath="DisplayText"
                          SelectedValuePath="CodeName"
                          Width="200" Height="25" Margin="5"/>
            </StackPanel>
            <TextBox Width="200" Height="25" Margin="5" 
                     HorizontalAlignment="Right" 
                     Visibility="{Binding SelectedValue, 
                            Converter={StaticResource countryCodeToVisibilityConverter}, 
                            ElementName=comboBox}"/>
        </StackPanel>
    </Grid>
</UserControl>

 

 

Next Step

This is all about the coding part. Now run your application and you will see the dropdown in the screen. Change the value to any country, you will see that there are no TextBox visible in the screen. But once you change it to “Others”, the TextBox will be visible in the screen, where you will be able to enter the new Country. Need more code to implement the feature.

 

If you now change the Combo selection to any other Country, voila, the TextBox will disappear from the screen. This is exactly the same thing we wanted to develop.

 

Just understand the use & implementation of the ValueConverter. You will be able to do more operation with the help of this.


If you have come this far, it means that you liked what you are reading. Why not reach little more and connect with me directly on Twitter, Facebook, Google+ and LinkedIn. I would love to hear your thoughts and opinions on my articles directly. Also, don't forget to share your views and/or feedback in the comment section below.

9 comments

  1. Good Sight given. thanx
    Please put the source code of sample , or mail me if possible

    ReplyDelete
  2. Wouldn't it be better if the VM exposed a Visiblility property and have logic in VM to set it to TRUE/FALSE whenever ComboBox selected item changes and the textbox bound to the Visibility property ?

    ReplyDelete
  3. Wow great! I's awesome post. Learn a lots please let me know how can i contact you because I m new developer in silverlight and facing lots of problem.

    ReplyDelete
  4. Hi Raj,

    You may contact me here: http://www.kunal-chowdhury.com/p/forum.html

    ReplyDelete
  5. hi Kunal,

    Please help me on Dependency Property (Why and When) in Silverligt with a code example.

    ReplyDelete
  6. I'm extremely pleased to discover this great site. I want to to thank you for your time for this particularly wonderful read!! I definitely enjoyed every part of it and I have you bookmarked to look at new information in your blog.

    ReplyDelete
  7. Hi Kunal,

    Thanks for your post. I tried this code but i am not able to show the TextBox on selection of Others. I have tried the complete code given above. Is there Something missing in this code from your side ?? Because i am complete new in MVVM So please help Sothat I can use this code.

    I debug this program and the control goes in "Convert" function of "CountryCodeToVisibilityConvertor" and returns "Visibility.Visible" on Selection of Others but the TextBox not shows. Is there something missing...

    Thanks,
    Rachit

    ReplyDelete
  8. Hi Rachit,

    Can you share me the sample project that you are working on?

    ReplyDelete
  9. Thanks a lot.. Worked like a charm

    ReplyDelete

 
© 2008-2016 Kunal-Chowdhury.com - Microsoft Technology Blog for developers and consumers | Designed by Kunal Chowdhury
Back to top