0
votes

I've noticed that by default in a ListPicker the border and currently selected item's text automatically are the phone's accent color. I was wondering how it would be possible to hard code these values to another color (which would be selected within the ListPicker itself). For instance, my phone theme is lime but I would like to manually set the border and highlighted text color to cobalt when the cobalt item is selected. Same for cyan, red, and so forth. My ListPicker looks like this

XAML

<phone:PhoneApplicationPage.Resources>
    <DataTemplate x:Name="ListPickerItemTemplate">
        <StackPanel Orientation="Horizontal">
            <Image Source="{Binding Image}" Width="50" Height="37.59"/>
            <TextBlock Text="{Binding Name}" Margin="12,0,0,0" TextWrapping="Wrap"/>
        </StackPanel>
    </DataTemplate>
    <DataTemplate x:Name="ListPickerFullModeItemTemplate">
        <StackPanel Orientation="Horizontal">
            <Image Source="{Binding Image}" Width="50" Height="37.59"/>
            <TextBlock Text="{Binding Name}" Margin="12,0,0,0" TextWrapping="Wrap"/>
        </StackPanel>
    </DataTemplate>
</phone:PhoneApplicationPage.Resources>

...

<toolkit:ListPicker x:Name="themeListPicker" Header="Theme" FullModeHeader="Theme" CacheMode="BitmapCache"
                                        SelectionChanged="themeListPicker_SelectionChanged"
                                        ItemTemplate="{StaticResource ListPickerItemTemplate}" 
                                        FullModeItemTemplate="{StaticResource ListPickerFullModeItemTemplate}"/>

XAML.CS

protected override void OnNavigatedTo(NavigationEventArgs e)
    {
        base.OnNavigatedTo(e);

        themeList = new List<Theme>();
        themeList.Add(new Theme() { Image = new BitmapImage(new Uri("/Assets/Themes/Indigo.png", UriKind.Relative)), Name = "indigo" });
        //themeList.Add(new Theme() { Image = new BitmapImage(new Uri("/Assets/Themes/Lime.png", UriKind.Relative)), Name = "lime" });
        //themeList.Add(new Theme() { Image = new BitmapImage(new Uri("/Assets/Themes/Green.png", UriKind.Relative)), Name = "green" });
        //themeList.Add(new Theme() { Image = new BitmapImage(new Uri("/Assets/Themes/Emerald.png", UriKind.Relative)), Name = "emerald" });
        //themeList.Add(new Theme() { Image = new BitmapImage(new Uri("/Assets/Themes/Teal.png", UriKind.Relative)), Name = "teal" });
        themeList.Add(new Theme() { Image = new BitmapImage(new Uri("/Assets/Themes/Cyan.png", UriKind.Relative)), Name = "cyan" });
        themeList.Add(new Theme() { Image = new BitmapImage(new Uri("/Assets/Themes/Cobalt.png", UriKind.Relative)), Name = "cobalt" });
        //themeList.Add(new Theme() { Image = new BitmapImage(new Uri("/Assets/Themes/Violet.png", UriKind.Relative)), Name = "violet" });
        //themeList.Add(new Theme() { Image = new BitmapImage(new Uri("/Assets/Themes/Pink.png", UriKind.Relative)), Name = "pink" });
        //themeList.Add(new Theme() { Image = new BitmapImage(new Uri("/Assets/Themes/Magenta.png", UriKind.Relative)), Name = "magenta" });
        //themeList.Add(new Theme() { Image = new BitmapImage(new Uri("/Assets/Themes/Crimson.png", UriKind.Relative)), Name = "crimson" });
        themeList.Add(new Theme() { Image = new BitmapImage(new Uri("/Assets/Themes/Red.png", UriKind.Relative)), Name = "red" });
        //themeList.Add(new Theme() { Image = new BitmapImage(new Uri("/Assets/Themes/Orange.png", UriKind.Relative)), Name = "orange" });
        //themeList.Add(new Theme() { Image = new BitmapImage(new Uri("/Assets/Themes/Amber.png", UriKind.Relative)), Name = "amber" });
        //themeList.Add(new Theme() { Image = new BitmapImage(new Uri("/Assets/Themes/Yellow.png", UriKind.Relative)), Name = "yellow" });
        //themeList.Add(new Theme() { Image = new BitmapImage(new Uri("/Assets/Themes/Brown.png", UriKind.Relative)), Name = "brown" });
        //themeList.Add(new Theme() { Image = new BitmapImage(new Uri("/Assets/Themes/Olive.png", UriKind.Relative)), Name = "olive" });
        themeList.Add(new Theme() { Image = new BitmapImage(new Uri("/Assets/Themes/Steel.png", UriKind.Relative)), Name = "steel" });
        //themeList.Add(new Theme() { Image = new BitmapImage(new Uri("/Assets/Themes/Mauve.png", UriKind.Relative)), Name = "mauve" });
        //themeList.Add(new Theme() { Image = new BitmapImage(new Uri("/Assets/Themes/Sienna.png", UriKind.Relative)), Name = "sienna" });

        themeListPicker.ItemsSource = themeList;

    }

As you can see I may have more than 5 items in my ListPicker, in which the FullModeItemTemplate would take precedence (although I will probably stick to just 5 options at the most). How might I change the ListPickers border and selected item accent colors to match the color that is selected in the ListPicker?

2

2 Answers

1
votes

You'll have to do a couple of things:

  1. Add a Color and Brush property to your Theme class.
  2. Add a template for your ListPicker to your xaml
  3. Add a CurrentTheme property to your xaml.cs
  4. Bind CurrentTheme to border of ListPicker

Your Theme class will look something like

public class Theme
{
    public string Name { get; set; }
    public BitmapImage Image { get; set; }
    public Color Color { get; set; }

    public SolidColorBrush Brush
    {
        get
        {
            return new SolidColorBrush(Color);
        }
    }
}

This makes it easy to add colored themes to your list (using the Color property) and binding that color to your text and border (using the Brush property).

YourPage.xaml.cs

themeList.Add(new Theme
{ 
    Image = new BitmapImage(new Uri("/Assets/Themes/Indigo.png", UriKind.Relative)),
    Name = "cyan",
    Color = Colors.Cyan 
});

YourPage.xaml

<TextBlock 
    Text="{Binding Name}" 
    Foreground="{Binding Brush}"
    Margin="12,0,0,0" 
    TextWrapping="Wrap"/>

If you want to bind the selected theme to the border of the ListPicker you will need to add a template for the ListPicker. The easiest way to do that is to use Expression Blend. If you have done that you can bind the color of the border like so:

Add current theme to YourPage.xaml:

private Theme _currentTheme;
public Theme CurrentTheme
{
    get
    {
        return _currentTheme;
    }

    private set
    {
        if (value == _currentTheme) return;
        _currentTheme = value;
        NotifyPropertyChanged("CurrentTheme");
    }
}

private void ThemesListPicker_OnSelectionChanged(object sender, SelectionChangedEventArgs e)
{
    if (ThemesListPicker.SelectedItem == null) return;
    CurrentTheme = ThemesListPicker.SelectedItem as Theme;
}

Bind the brush to the border in the list picker template:

<!-- Omitted rest of template for brevity -->
<Border 
    x:Name="Border"
    Background="{TemplateBinding Background}"
    BorderThickness="{TemplateBinding BorderThickness}" 
    BorderBrush="{Binding CurrentTheme.Brush}">
0
votes

think you can use converter to get the desired result

for converter

public class SelectedItemColorConverter:IValueConverter
    {
        public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
        {


            if ((bool)value)
            {
                return new SolidColorBrush((Colors.Red);
            }
            return new SolidColorBrush(Colors.White);
        }

        public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
        {

           return null;
        }
    }