Namespaces
Variants
Actions

How to create a button with image for Windows Phone

Jump to: navigation, search

This article explains how to create a custom button with an image for Windows Phone.

SignpostIcon XAML 40.png
WP Metro Icon UI.png
Article Metadata

Code Example
Tested with
SDK: Windows Phone 7.1
Devices(s): Tested with the Lumia 900

Compatibility
Platform(s): Windows Phone
Device(s): All Windows Phones

Article
Keywords: button, image
Created: ArchieCoder (28 Sep 2012)
Last edited: hamishwillee (10 Apr 2013)

Contents

Introduction

There are many examples in the Windows Phone community showing how to create a button with an image. We can achieve this result with the following code:

<Button>
<Image Source="MyImage.png"/>
</Button>

The problem with the code above is that the Button can only display a single image: it cannot display a different (more appropriate) image when the button is disabled or pressed.

This article shows how to create (and use) the custom ButtonImage class to set a different image for the disabled and the pressed states. If you are not interested on the code of the ButtonImage class, you can skip this section and go directly to the #Usage section.

ButtonImage.png
The button has an image for each state:
  • Normal

ImageNormal.png

  • Pressed

ImagePressed.png

  • Disabled

ImageDisabled.png

ButtonImage implementation

The ButtonImage class has XAML code and C# code.

XAML code

<Button x:Class="DotNetApp.ButtonImage"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
IsEnabledChanged="ButtonIsEnabledChanged"
MouseEnter="ButtonMouseEnter"
MouseLeave="ButtonMouseLeave">
 
<Image Stretch="None"
HorizontalAlignment="Center"
VerticalAlignment="Center"
x:Name="image" />
</Button>

There is nothing fancy here, it is a button that has an image has content.

C# code

using System;
using System.Windows;
using System.Windows.Media.Imaging;
 
namespace DotNetApp
{
public partial class ButtonImage
{
#region Fields
 
public new static readonly DependencyProperty IsEnabledProperty = DependencyProperty.Register("IsEnabled", typeof (bool), typeof (ButtonImage), null);
public static readonly DependencyProperty ImageSourceProperty = DependencyProperty.Register("ImageSource", typeof (string), typeof (ButtonImage), null);
public static readonly DependencyProperty ImagePressedSourceProperty = DependencyProperty.Register("ImagePressedSource", typeof (string), typeof (ButtonImage), null);
public static readonly DependencyProperty ImageDisabledSourceProperty = DependencyProperty.Register("ImageDisabledSource", typeof (string), typeof (ButtonImage), null);
 
private BitmapImage _image;
private BitmapImage _imagePressed;
private BitmapImage _imageDisabled;
private bool _isPressed;
 
#endregion
 
#region Constructor
 
public ButtonImage()
{
InitializeComponent();
}
 
#endregion
 
#region Properties
 
public new bool IsEnabled
{
get { return (bool)GetValue(IsEnabledProperty); }
 
set
{
SetValue(IsEnabledProperty, value);
 
SetImageFromState();
}
}
 
public string ImageSource
{
get { return (string) GetValue(ImageSourceProperty); }
 
set
{
SetValue(ImageSourceProperty, value);
 
_image = SetImage(value);
SetImageFromState();
}
}
 
public string ImagePressedSource
{
get { return (string) GetValue(ImagePressedSourceProperty); }
 
set
{
SetValue(ImagePressedSourceProperty, value);
 
_imagePressed = SetImage(value);
SetImageFromState();
}
}
 
public string ImageDisabledSource
{
get { return (string) GetValue(ImageDisabledSourceProperty); }
 
set
{
SetValue(ImageDisabledSourceProperty, value);
 
_imageDisabled = SetImage(value);
SetImageFromState();
}
}
 
#endregion
 
#region Event Handlers
 
private void ButtonIsEnabledChanged(object sender, DependencyPropertyChangedEventArgs e)
{
SetImageFromState();
}
 
private void ButtonMouseEnter(object sender, System.Windows.Input.MouseEventArgs e)
{
_isPressed = true;
 
SetImageFromState();
}
 
private void ButtonMouseLeave(object sender, System.Windows.Input.MouseEventArgs e)
{
_isPressed = false;
 
SetImageFromState();
}
 
#endregion
 
#region Private Methods
 
private static BitmapImage SetImage(string imageSource)
{
BitmapImage bitmapImage = null;
 
if (!string.IsNullOrEmpty(imageSource))
{
bitmapImage = new BitmapImage(new Uri(imageSource, UriKind.RelativeOrAbsolute));
}
 
return bitmapImage;
}
 
private void SetImageFromState()
{
if (!IsEnabled)
{
image.Source = _imageDisabled;
}
else if (_isPressed)
{
image.Source = _imagePressed;
}
else
{
image.Source = _image;
}
}
 
#endregion
}
}

Once again, there is nothing "special" here. I load the correct images and based on the event handlers (ButtonIsEnabledChanged, ButtonMouseEnter and ButtonMouseLeave).

Usage

To use the ButtonImage control in your app, just follow those steps:

  1. Add the files ButtonImage.xaml and ButtonImage.xaml.cs to your project.
  2. Add the normal image, the pressed image and the disabled image to your project. If your button does not need a pressed image or a disabled image, you don't have to specify one.
  3. Add the XML code
<ButtonImageApp:ButtonImage ImageSource="/ImageNormal.png"
ImageDisabledSource="/ImageDisabled.png"
ImagePressedSource="/ImagePressed.png"
Style="{StaticResource ButtonImageStyle}"
Height="50"
Width="150" />

All the properties are important. The ImageSource, ImageDisabledSource, ImagePressedSource are the actual images that you want for each state. The Height and the Width need to be the same as the specified images.

The last piece of the puzzle is the Style property set to "{StaticResource ButtonImageStyle}". If you do not set this property, there will be an unwanted transparent area around the image and the image will be smaller. Your last step is to define the ButtonImageStyle into your project. You can add it into your page or in the App resources section. The code to copy is:

Page

<phone:PhoneApplicationPage.Resources>
 
<Style x:Key="ButtonImageStyle"
TargetType="ButtonImageApp:ButtonImage">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="ButtonImageApp:ButtonImage">
<Grid Background="Transparent">
<VisualStateManager.VisualStateGroups>
<VisualStateGroup x:Name="CommonStates">
<VisualState x:Name="Normal" />
<VisualState x:Name="MouseOver" />
<VisualState x:Name="Pressed" />
<VisualState x:Name="Disabled" />
</VisualStateGroup>
</VisualStateManager.VisualStateGroups>
<Border x:Name="ButtonBackground">
<ContentControl x:Name="ContentContainer"
ContentTemplate="{TemplateBinding ContentTemplate}"
Content="{TemplateBinding Content}" />
</Border>
</Grid>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
 
</phone:PhoneApplicationPage.Resources>

or App

<Application.Resources>
 
<Style x:Key="ButtonImageStyle"
TargetType="ButtonImageApp:ButtonImage">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="ButtonImageApp:ButtonImage">
<Grid Background="Transparent">
<VisualStateManager.VisualStateGroups>
<VisualStateGroup x:Name="CommonStates">
<VisualState x:Name="Normal" />
<VisualState x:Name="MouseOver" />
<VisualState x:Name="Pressed" />
<VisualState x:Name="Disabled" />
</VisualStateGroup>
</VisualStateManager.VisualStateGroups>
<Border x:Name="ButtonBackground">
<ContentControl x:Name="ContentContainer"
ContentTemplate="{TemplateBinding ContentTemplate}"
Content="{TemplateBinding Content}" />
</Border>
</Grid>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
 
</Application.Resources>

Conclusion

The ButtonImage derives from a Button so you can add a Command or the Click handler.

Download

This page was last modified on 10 April 2013, at 04:28.
453 page views in the last 30 days.
Nokia Developer aims to help you create apps and publish them so you can connect with users around the world.

京ICP备05048969号  © Copyright Nokia 2013 All rights reserved