Making a custom Windows Phone Bing Maps PushPin from an image

Making a custom Windows Phone Bing Maps PushPin from an image

Standard pushpins that can be used on a Bing map can get rather boring. Most of the applications which have certain artwork and styling need to use custom pushpins to display different things on a map. In this article, I’ll show how to quickly create a custom pushpin from Expression Design to the application

Let’s start from a design application such as Expression Design or a free Paint.NET. Create an image that will be used as a pushpin. I created a pushpin similar to the native ones, just changing the colors and writing “igrali pin” on it, to make it customized.

custompin2

Now, save it as a PSD or PNG file, so you can import it to your Visual Studio or Blend project. Create a new project in either of the applications mentioned above, and define the MainPage.xaml:

<phone:PhoneApplicationPage  
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:phone="clr-namespace:Microsoft.Phone.Controls;assembly=Microsoft.Phone"
    xmlns:shell="clr-namespace:Microsoft.Phone.Shell;assembly=Microsoft.Phone"
    xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
    xmlns:mapss="clr-namespace:Microsoft.Phone.Controls.Maps;assembly=Microsoft.Phone.Controls.Maps"
    mc:Ignorable="d" d:DesignWidth="480" d:DesignHeight="768"
    x:Class="CustomBingPin.MainPage"
    FontFamily="{StaticResource PhoneFontFamilyNormal}"
    FontSize="{StaticResource PhoneFontSizeNormal}"
    Foreground="{StaticResource PhoneForegroundBrush}"
    SupportedOrientations="Portrait" Orientation="Portrait"
    shell:SystemTray.IsVisible="True">

    <!--LayoutRoot is the root grid where all page content is placed-->
    <Grid x:Name="LayoutRoot" Background="Transparent">
        <Grid.RowDefinitions>
            <RowDefinition Height="Auto"/>
            <RowDefinition Height="*"/>
        </Grid.RowDefinitions>

        <!--TitlePanel contains the name of the application and page title-->
        <StackPanel x:Name="TitlePanel" Grid.Row="0" Margin="12,17,0,28"/>

        <!--ContentPanel - place additional content here-->
        <Grid x:Name="ContentPanel" Grid.Row="1" Margin="12,0,12,0">
            <mapss:Map Margin="0,0,8,0" CredentialsProvider="Your credentials” d:LayoutOverrides="Height" Name="map" />
        </Grid>
    </Grid>
</phone:PhoneApplicationPage>  

Now, you need to import the image you created earlier:

image

In my case, it’s called Layer 1.png. Now, we need to define the ControlTemplate for the pushpin inside the page or inside the app. I did it inside the page resources:

<phone:PhoneApplicationPage.Resources>  
        <ControlTemplate x:Key="PushpinControlTemplate1" TargetType="mapss:Pushpin">
            <Grid Name="contentGrid" Height="64" HorizontalAlignment="Center" VerticalAlignment="Center">
                <Image x:Name="Layer_1" Height="64" Source="pin_Images/Layer 1.png"/>
            </Grid>
        </ControlTemplate>
    </phone:PhoneApplicationPage.Resources>

Now, in order to pin this pushpin to map and show it, I hardcoded the coordinates and did it in MainPage_Loaded event handler:

void  MainPage_Loaded(object sender, RoutedEventArgs e)  
{
    Pushpin pin1 = new Pushpin();
    pin1.Location = new GeoCoordinate(45.805025, 15.978697);
    pin1.Template = (ControlTemplate)(this.Resources["PushpinControlTemplate1"]);
    map.Children.Add(pin1);

    map.SetView(pin1.Location, 10);
}

The most important part is where I set the pin template:

pin1.Template = (ControlTemplate)(this.Resources["PushpinControlTemplate1"]);  

If the template was a part of the application resources, you would write:

pin1.Template = (ControlTemplate)(Application.Current.Resources["PushpinControlTemplate1"]);  

If you prefered, you could have opened the project in Blend and then instead of using an image, do all the drawing inside the content grid:

<ControlTemplate x:Key="PushpinControlTemplate1" TargetType="mapss:Pushpin">  
                <Grid Name="contentGrid" Height="64" HorizontalAlignment="Center" VerticalAlignment="Center">
//DO THE DRAWING HERE

                </Grid>
</ControlTemplate>  

Final result is this:

scree

I hope this helps :)

Igor Ralic

igor ralic

View Comments
Microsoft Certified Solutions Developer: Windows Store Apps in C#