Hello All,
I was recently asked to build up a Silverlight tool to show a file full of addresses on a map. I decided to use the Silverlight bing maps control and I must say I was not disappointed with it's functionality. It ended up being extremely simple. The tools used to create this were VS2010, Silverlight 4, Bing maps Silverlight control, and the Bing maps web services.
Setting up the Bing Maps account:
All you need is a live account and your good to go: https://www.bingmapsportal.com/. Log in with your Live ID and enter your app name and URL and the keys are in the ignition!
Get the Bing Maps Control:
Grab it from: http://www.microsoft.com/downloads/details.aspx?displaylang=en&FamilyID=beb29d27-6f0c-494f-b028-1e0e3187e830. Install that bad boy and create your Silverlight app in VS2010.
Adding the Map Control to your app:
<UserControl x:Class="PeopleMap.MainPage"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:m="clr-namespace:Microsoft.Maps.MapControl;assembly=Microsoft.Maps.MapControl"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d"
d:DesignHeight="300" d:DesignWidth="400" AllowDrop="True">
<Grid x:Name="LayoutRoot" Background="White">
<m:Map x:Name="myMap" CredentialsProvider="Your Key!!" Mode="Road"/>
</Grid>
</UserControl>
Make sure to mark the user control from your main view to allow drop. I’m expecting a file with each address on the new line.
Add in the reference to the Bing Geocoding services to your Silverlight project:
Add in a Service Reference to your Silverlight project with the following URL: http://dev.virtualearth.net/webservices/v1/geocodeservice/geocodeservice.svc. I used the namespace of “BingGeocode”.
Add in code to handle the Geocode / location calls and throw some pins onto your map:
using System;
using System.IO;
using System.Linq;
using System.Windows;
using System.Windows.Controls;
using Microsoft.Maps.MapControl;
using PeopleMap.BingGeocode;
namespace PeopleMap
{
public partial class MainPage : UserControl
{
public MainPage()
{
InitializeComponent();
Drop += MainPage_Drop;
}
private void MainPage_Drop(object sender, DragEventArgs e)
{
if (e.Data != null)
{
var files = e.Data.GetData(DataFormats.FileDrop) as FileInfo[];
var firstFile = files.IfNotNull(i => i.FirstOrDefault());
firstFile.IfNotNull(i =>
{
using (var streamReader = firstFile.OpenText())
{
while (!streamReader.EndOfStream)
{
RequestAddress(streamReader.ReadLine());
}
}
});
}
}
private void RequestAddress(string lineText)
{
var geocodeRequest = new GeocodeRequest { Query = lineText };
var geocodeClient = new GeocodeServiceClient();
geocodeRequest.Credentials = new Credentials
{
ApplicationId =
((ApplicationIdCredentialsProvider) myMap.CredentialsProvider).
ApplicationId
};
geocodeClient.GeocodeCompleted += GeocodeClientGeocodeCompleted;
geocodeClient.GeocodeAsync(geocodeRequest);
}
private void GeocodeClientGeocodeCompleted(object sender, GeocodeCompletedEventArgs e)
{
if(e.Error == null)
{
var firstResult = e.Result.Results.FirstOrDefault();
if (firstResult != null)
{
var location = firstResult.Locations.FirstOrDefault();
var pin = new Pushpin {Location = location};
pin.SetValue(ToolTipService.ToolTipProperty, new TextBlock{Text = firstResult.DisplayName});
myMap.Children.Add(pin);
}
}
else
{
throw new Exception(e.Error.Message);
}
}
}
}
Useful extension methods used:
I end up using these in a bunch of my little projects to do things in line, rather than writing longer code. I think they are more readable. I hope they help you.
using System;
namespace PeopleMap
{
public static class Extenstions
{
public static TResult IfNotNull<TArg, TResult>(this TArg obj, Func<TArg, TResult> func) where TArg : class
{
return obj != null ? func(obj) : default(TResult);
}
public static void IfNotNull<TArg>(this TArg obj, Action<TArg> action) where TArg : class
{
if (obj != null)
action(obj);
}
}
}
My input (just create a txt file with the following addresses on their own lines – if you don’t like Cleveland, insert your own data):
50 Public Square, Cleveland, OH
1100 Rock and Roll Blvd., Cleveland, OH
1085 West 3rd Street, Cleveland, OH
1 Center Court, Cleveland, OH
That’s about it. The solution was very simple, but very useful. All you have to do, is drop the file on the window, and you have your data show up on the map.
If you like this, you will probably like the information coming from my twitter account.
Cheers,
David Justice
Hey All,
I was working with a client that wanted to have a default button clicked when an enter key is pressed in a textbox (password box to be more specific) within a Silverlight or WPF application. I didn't think much of it. I'll just listen to the event, bind to the button, and click the button on the enter key event. The listening and binding portion is not very tough with an attached property and a little Silverlight 3 element to element binding love. The tricky part came in when I wanted to cause the button click event to be raised. I ended up having to take a page from Josh Smith http://joshsmithonwpf.wordpress.com/2007/03/09/how-to-programmatically-click-a-button/. Thank you, Josh! This may not be the best way to do this, but it works for me.
Here is a simple page showing the usage of the default button attached property:
1 <UserControl x:Class="DefaultButton.MainPage"
2 xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
3 xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
4 xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
5 xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
6 xmlns:DefaultButton="clr-namespace:DefaultButton"
7 mc:Ignorable="d"
8 d:DesignWidth="640"
9 d:DesignHeight="480">
10 <StackPanel x:Name="LayoutRoot">
11 <TextBox Text="Press Enter"
12 DefaultButton:DefaultButtonService.DefaultButton="{Binding ElementName=button}"
13 Width="200" Height="30"/>
14 <Button x:Name="button" Content="waiting for click..."
15 Click="Button_Click" Width="200" Height="200"/>
16 <Button x:Name="reset" Content="Reset" Click="reset_Click" Width="200"/>
17 </StackPanel>
18 </UserControl>
Here is the code behind that page:
1 #region Namespaces
2
3 using System.Windows;
4 using System.Windows.Controls;
5
6 #endregion
7
8 namespace DefaultButton
9 {
10 public partial class MainPage : UserControl
11 {
12 public MainPage()
13 {
14 InitializeComponent();
15 }
16
17 private void Button_Click(object sender, RoutedEventArgs e)
18 {
19 button.Content = "I was Clicked!";
20 }
21
22 private void reset_Click(object sender, RoutedEventArgs e)
23 {
24 button.Content = "waiting for click...";
25 }
26 }
27 }
Here is the attached property:
1 #region Namespaces
2
3 using System.Windows;
4 using System.Windows.Automation.Peers;
5 using System.Windows.Automation.Provider;
6 using System.Windows.Controls;
7 using System.Windows.Input;
8
9 #endregion
10
11 namespace DefaultButton
12 {
13 public static class DefaultButtonService
14 {
15 public static DependencyProperty DefaultButtonProperty =
16 DependencyProperty.RegisterAttached("DefaultButton",
17 typeof (Button),
18 typeof (DefaultButtonService),
19 new PropertyMetadata(null, DefaultButtonChanged));
20
21 private static void DefaultButtonChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
22 {
23 var uiElement = d as UIElement;
24 var button = e.NewValue as Button;
25 if (uiElement != null && button != null)
26 {
27 uiElement.KeyUp += (sender, arg) =>
28 {
29 if (arg.Key == Key.Enter)
30 {
31 var peer = new ButtonAutomationPeer(button);
32 var invokeProv =
33 peer.GetPattern(PatternInterface.Invoke) as IInvokeProvider;
34 if (invokeProv != null)
35 invokeProv.Invoke();
36 }
37 };
38 }
39 }
40
41 public static void SetDefaultButton(UIElement obj, Button button)
42 {
43 obj.SetValue(DefaultButtonProperty, button);
44 }
45
46 public static void GetDefaultButton(UIElement obj)
47 {
48 obj.GetValue(DefaultButtonProperty);
49 }
50 }
51 }
All in all, pretty straight forward.
Cheers,
David
UPDATE: I didn't see this, but it looks like Patrick Cauldwell has blogged about a very similar topic in May (in fact the only major thing that separates the code is the binding). You can see his post here: http://www.cauldwell.net/patrick/blog/ALdquodefaultButtonrdquoInSilverlight.aspx.
Hi again,
I was a little bored this weekend and needed to add in some GA functionality to a side project. I felt like it would be best to create a simple executer to deal with the iterative behavior of a genetic algorithm. The executer take in funcs provided by the consumer and executes based on a simple iterative model.
I've included a zip of the solution with an example of usage within the accompanying test project.
Below is what I came up with. Cheers!
Code:
8 #region Dependencies
9
10 using System;
11 using System.Collections.Generic;
12 using System.Diagnostics;
13 using System.Linq;
14
15 #endregion
16
17 namespace GA
18 {
19 /// <summary>
20 /// GeneticAlgorithm runs a genetic algorithm based on an initial population, fitness func, crossover func,
21 /// optional mutation function, and tollerance
22 /// </summary>
23 /// <typeparam name="T">Type to perform the algorithm against</typeparam>
24 public class GeneticAlgorithm<T>
25 {
26 private readonly Func<IEnumerable<FitnessComposite<T>>, IEnumerable<T>> _crossoverFunction;
27 private readonly Func<IEnumerable<T>, IEnumerable<FitnessComposite<T>>> _fitnessFunction;
28 private readonly Func<IEnumerable<T>, IEnumerable<T>> _mutationFunction;
29 private readonly double _tollerance;
30 private IEnumerable<T> _population;
31
32 /// <summary>
33 ///
34 /// </summary>
35 /// <param name="population">initial population</param>
36 /// <param name="fitnessFunction">function for calculating fitness</param>
37 /// <param name="crossoverFunction">breeding fuction</param>
38 /// <param name="mutationFunction">mutation function (optional, use null if not needed)</param>
39 /// <param name="tollerance">fitness tollernance</param>
40 public GeneticAlgorithm(IEnumerable<T> population,
41 Func<IEnumerable<T>, IEnumerable<FitnessComposite<T>>> fitnessFunction,
42 Func<IEnumerable<FitnessComposite<T>>, IEnumerable<T>> crossoverFunction,
43 Func<IEnumerable<T>, IEnumerable<T>> mutationFunction,
44 double tollerance)
45 {
46 _population = population;
47 _fitnessFunction = fitnessFunction;
48 _crossoverFunction = crossoverFunction;
49 _mutationFunction = mutationFunction;
50 _tollerance = tollerance;
51 }
52
53 /// <summary>
54 /// Max number of results to return
55 /// </summary>
56 public int? MaxResults { get; set; }
57
58 /// <summary>
59 /// Max time the algorithm can run
60 /// </summary>
61 public TimeSpan? TimeOut { get; set; }
62
63 /// <summary>
64 /// Result of the algorithm
65 /// </summary>
66 public IEnumerable<FitnessComposite<T>> Results { get; private set; }
67
68 /// <summary>
69 /// Number of generations
70 /// </summary>
71 public int Generations { get; private set; }
72
73 /// <summary>
74 /// Has the algorithm reach the finish criteria (either time has expired, or the tollerance has been reached)
75 /// </summary>
76 public bool IsDone { get; private set; }
77
78 /// <summary>
79 /// The evolving population
80 /// </summary>
81 public IEnumerable<T> Population
82 {
83 get { return _population; }
84 }
85
86 /// <summary>
87 /// Run the algorithm until complete and perform the doneAction at completion
88 /// </summary>
89 /// <param name="doneAction">action to be performed when the algorithm time has expired or tollerance has been reached</param>
90 public void Run(Action<IEnumerable<FitnessComposite<T>>> doneAction)
91 {
92 var executer = new Executer(_population)
93 {
94 BreedingFunc = GetBreedingFunc(),
95 FitnessFunc = _fitnessFunction,
96 };
97
98 if (TimeOut.HasValue)
99 {
100 var timer = new Stopwatch();
101 timer.Start();
102 executer.FinishCriteria = fitnessItems => IsFitnessReached(fitnessItems) || timer.Elapsed > TimeOut;
103 InternalRun(executer, doneAction);
104 timer.Stop();
105 }
106 else
107 {
108 executer.FinishCriteria = IsFitnessReached;
109 InternalRun(executer, doneAction);
110 }
111 }
112
113 private void InternalRun(Executer executer, Action<IEnumerable<FitnessComposite<T>>> doneAction)
114 {
115 while (executer.Run())
116 {
117 _population = executer.Population;
118 Generations++;
119 }
120
121 IsDone = executer.IsDone;
122 Results = executer.Results.Where(FitnessIsLessThanOrEqualToTollerance);
123 if (MaxResults.HasValue && Results.Count() > MaxResults.Value)
124 Results = Results.Take(MaxResults.Value);
125
126 doneAction(Results);
127 }
128
129 private Func<IEnumerable<FitnessComposite<T>>, IEnumerable<T>> GetBreedingFunc()
130 {
131 return _mutationFunction != null
132 ? i => _mutationFunction(_crossoverFunction(i))
133 : _crossoverFunction;
134 }
135
136 private bool IsFitnessReached(IEnumerable<FitnessComposite<T>> fitnessComposites)
137 {
138 return FitnessIsLessThanOrEqualToTollerance(GetBestFitness(fitnessComposites));
139 }
140
141 private FitnessComposite<T> GetBestFitness(IEnumerable<FitnessComposite<T>> fitnessComposites)
142 {
143 return fitnessComposites.OrderBy(i => i.Fitness).First();
144 }
145
146 private bool FitnessIsLessThanOrEqualToTollerance(FitnessComposite<T> ratedObject)
147 {
148 return ratedObject.Fitness <= _tollerance;
149 }
150
151 #region Nested type: Executer
152
153 private class Executer
154 {
155 private IEnumerable<T> _internalPopulation;
156
157 public Executer(IEnumerable<T> initialPopulation)
158 {
159 _internalPopulation = initialPopulation;
160 }
161
162 public bool IsDone { get; private set; }
163 public Func<IEnumerable<FitnessComposite<T>>, bool> FinishCriteria { get; set; }
164 public Func<IEnumerable<T>, IEnumerable<FitnessComposite<T>>> FitnessFunc { get; set; }
165 public Func<IEnumerable<FitnessComposite<T>>, IEnumerable<T>> BreedingFunc { get; set; }
166 public IEnumerable<T> Population { get; private set; }
167 public IEnumerable<FitnessComposite<T>> Results { get; private set; }
168
169 public bool Run()
170 {
171 var fitnessComposites = FitnessFunc(_internalPopulation);
172 IsDone = FinishCriteria(fitnessComposites);
173 if (!IsDone)
174 _internalPopulation = BreedingFunc(fitnessComposites);
175 else
176 Results = fitnessComposites;
177 Population = _internalPopulation;
178 return !IsDone;
179 }
180 }
181
182 #endregion
183 }
184 }
Twitter: David Justice
Download the Code
Hello All,
Today I found my self hanging out after a sprint review with my partner in crime Kevin Rohling. TFS was down (not tfs's fault, but some other freak accident...) and I hadn't installed VS 2010 yet, so it seemed like the perfect time to do such things. I got everything up and running, and Kevin and I got into a discussion about Dynamics & performance. We made a quick lunch bet on which is faster, reflection or dynamics for simply setting a property. I figured reflection would be quicker, while Kevin thought dynamics would be faster. Well, I owe him lunch now. The code is below.
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
namespace ConsoleApplication1
{
class Program
{
static void Main(string[] args)
{
var nTimes = 1000000;
var value = "Hello World";
var myTestType = new MyTestType();
DateTime start, end;
var property = typeof(MyTestType).GetProperty("MyDynamicProperty");
start = DateTime.Now;
for (var i = 0; i < nTimes; i++)
{
//var property = typeof(MyTestType).GetProperty("MyDynamicProperty");
property.SetValue(myTestType, value, null);
}
end = DateTime.Now;
Console.WriteLine(end.Subtract(start).ToString());
dynamic myTestType2 = new MyTestType();
start = DateTime.Now;
for (int i = 0; i < nTimes; i++)
{
myTestType2.MyDynamicProperty = value;
}
end = DateTime.Now;
Console.WriteLine(end.Subtract(start).ToString());
var myTestType3 = new MyTestType();
start = DateTime.Now;
for (int i = 0; i < nTimes; i++)
{
myTestType3.MyDynamicProperty = value;
}
end = DateTime.Now;
Console.WriteLine(end.Subtract(start).ToString());
Console.ReadLine();
}
public class MyTestType
{
public string MyDynamicProperty { get; set; }
}
}
}
Results:
Reflection: 00:00:19.8581040
Dynamics: 00:00:00.6054300
Setting a property plain and simple: 00:00:00.0166005
Kevin was right by a long shot!! Who would have guessed that dynamics would be so fast. I'm quite impressed, and tip my hat to the guys that cooked that up! Cheers fellas, but thanks a lot for making my buy lunch...
On a side note: Congrats to Kevin Rohling on his winning new CloudApp() with his submission of www.myimpulselive.com! Check out the app. It's pretty darn slick!
Hello All!
Lately, I have been spending some time working with Silverlight in the context of the Facebook api. I've been amazed at the amount of data the api gives you access to. With the incredible growth facebook is experiencing (check this out: http://www.insidefacebook.com/2008/07/29/tracking-facebooks-2008-international-growth-by-country/), there are many opportunities blooming for developers that can use the information to improve / innovate with their own products. If you are a marketing / advertising business and you are not leveraging this information in one way or another, then I would say you are missing out!
In a past post (Facebook Connect Post) I showed everyone how to set up an application in Facebook and how to use Facebook Connect with Silverlight to create a simple login screen. That was a trivial proof of concept to show how one might implement such things on their Silverlight App. This post will build on the previous post, and introduce a very alpha version of a Silverlight client side api I have been working on for a little bit.
There has been many articles written on how to hook up the a Silverlight app to Facebook, but it's always used the web server as a bridge to get the data back from the Facebook api. Pete Brown did a wonderful job illustrating this in this blog post using the Facebook Developer Toolkit via Clarity Consulting. I think using your web server as the bridge to the Facebook api is slightly wasteful. As a result of that conclusion I decided to port the api to the client side. I felt it would be nice to offload much of the weight of the web requests onto the Facebook servers rather than my poorly funded web servers :). I also think this will allow for an architecture that will scale much better than the web server bridge.
<disclaimer>
If / When you look at the code, please understand this is just an api and a demo. There is little or no abstraction. There is no caching / real object model. I built this as a proof of concept and will advance it in a bit. Heck, I don't even know if this is going to garner any attention...
</disclaimer>
When I was building the api, I came to the conclusion, very early down the path, that web request completed event handlers and custom delegates are the devil, Bobby Boucher. I always want to write the call to the method, then have to go back and wire up the delegate for the call back. It bugs the hell out of me that I can't just pass an action into the method call. With that thought in my head, I made the api use generic actions passed into the api requests rather than callbacks. I'm not sure how this will go over, but I have found it a little easier to read. I do love lambdas, so I might be a bit biased in that choice.
One important thing to note about the Facebook api: It might not give you back what the xsd promises. I think I have fixed all of the places where this issue cropped up.
After you download the code, there are few things you will need to do to run the demo app. You will need to follow my original post to create an application in Facebook and get facebook connect set up for the demo. Basically, after you get your application key and secret key, you just need to plug them into a couple spots (ApplicationContext.cs, Default.aspx, and your secret key in value for app setting "secret" in the web.config). You may also need to update your service references to point to the fake host name you set up in your hosts file (from the previous post). That should get you to the point where you have the demo running.
Comments are welcomed. Bugs are welcomed. Calling me a complete butthead is welcomed. I will get back to you if you are kind enough to ask about something.
Finally, I have to give a couple shout outs. Thank you very much to the Madison, WI .NET Users group for letting me use your members as a sounding board. Lance Larsen and Travis Feirtag were kind enough to give me some time at the latest meeting. Thank you very much guys. Check them out at http://www.maddotnet.com/. Last but not least, I want to give a big high five to the guys over at http://mightymeaty.members.winisp.net/blacklight.silverlight/. They do some really cool stuff with Silverlight controls. I'm continually impressed with the quality and UX this group creates. If you look at the controls in the demo, you will notice i'm utilizing some of their controls and styles. I would recommend testing out their stuff if you get a chance.
Twitter: David Justice
Code

Hello all! First off, I want to say this post does not
reflect the way I think authentication should be handled. I don't necessarily
agree with the route Facebook has decided to go with Connect, but that is a
debate I don't really wish to be a part of right now. I would like to
concentrate on the superlatives about Facebook Connect and the possibilities
this opens up to developers. If you wish to discuss the positives and
negatives of the Facebook Connect strategy, please be my guest to comment till
your angelic heart is content.
In this post, I'm going to set up an Azure cloud service project
with a single web role that hosts a Silverlight 2 page, which utilizes Facebook
Connect. I will not go into other portions of the Facebook API during
this post, but I will extend it in a later post. Basically this is 1/10
an excersize in creating a cloud service, 1/2 using Facebook connect, and about
2/5 interactions between JavaScript and Silverlight. Ok, let's get
started.
Things needed:
1)
Azure CTP
2)
Silverlight 2
3)
Facebook account
Let first open Visual Studio 2008 and create an Web Cloud Service and call it AzureFaceBookConnect.

After that is created, let's add our Silverlight Application. We'll call it FaceBookConnect (common theme, huh).

Next let's go set up our developer account with Facebook. For this step you will need a Facebook login. It's not that bad... Plus you might actually like it if you haven't been sucked into the blackhole that is Facebook :). Go to Facebook Developers.

Click on the "Set Up New Application" button. We are going to create an application called {Test Connect} <--- just put whatever you want. Just like code, if you keep your misspellings all the same, then the compiler still loves you :).

So, just agree to everything, and use the old settings editor. You can use the updated settings editor, but the old settings editor has everything we need. Plus, the old settings editor doesn't have as many shinny buttons! In the editor, you should see something like below.

Please make sure to fabricate a good domain name. We will be using it in the near future. Actually, this doesn't need to be a real domain as you can see from mine above. We are going to update our host file, so we can test without having to use a real domain. This can be pretty useful! You can probably find your host file on a windows machine at C:\Windows\System32\drivers\etc. Also, take note of the Callback URL. The callback url will be used by the Facebook client js for authentication, and needs to be of the same base domain.
We will need to create two pages. One to host our client page, and another page to host the callback js for Facebook. You can't tell from above, but I named the callback page FbConnectCallback.aspx.

I love the old faithful, notepad! You can see above, I've added the fake domain, and mapped back to localhost. You will need to specify this domain when you are running your code. Facebook needs to call back to a page which it thinks originates from the base domain. We just want to spoof the domain.
Now onto some code: Default.aspx
<%@ Register Assembly="System.Web.Silverlight" Namespace="System.Web.UI.SilverlightControls"
TagPrefix="asp" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head id="Head1" runat="server">
<title>FaceBookConnect</title>
</head>
<body style="height: 100%; margin: 0;">
<form id="form1" runat="server" style="height: 100%;">
<asp:ScriptManager ID="ScriptManager1" runat="server" />
<div style="height: 100%;">
<asp:Silverlight ID="Xaml1" runat="server" Source="~/ClientBin/FaceBookConnect.xap"
MinimumVersion="2.0.31005.0" Width="100%" Height="100%" />
<script src="http://static.ak.connect.facebook.com/js/api_lib/v0.4/FeatureLoader.js.php"
type="text/javascript"></script>
<script type="text/javascript">
FB.init("{You're API Key from setting up you developer account}", "/FbConnectCallback.aspx");
function facebook_onlogin() {
var slcontrol = $get('Xaml1');
slcontrol.Content.slPage.LoggedIn();
}
function login() {
FB.Connect.requireSession(facebook_onlogin);
}
function logout() {
FB.Connect.logout();
}
</script>
</div>
</form>
</body>
</html>
Please pay close attention to the Facebook FeatureLoader script tag, and the fact it is placed in the body. That is manditory for the js to function properly.
Next Up: FbConnectCallback.aspx
<%@ Page Language="C#" AutoEventWireup="true" CodeBehind="FbConnectCallback.aspx.cs" Inherits="AzureFaceBookConnect_WebRole.FbConnectCallback" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" >
<head runat="server">
<title>FbConnectCallback</title>
</head>
<body>
<script src="http://static.ak.connect.facebook.com/js/api_lib/v0.4/XdCommReceiver.js" type="text/javascript"></script>
</body>
</html>
Again, pay attention to where the script tag is placed.
Now for the Silverlight: Page.xaml
<UserControl x:Class="FaceBookConnect.Page"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
<Canvas>
<Button x:Name="btnLogin" Click="Button_Click">
<Button.Content>
<Image Source="Images/connect_light_medium_long.png"/>
</Button.Content>
</Button>
</Canvas>
</UserControl>
This page is just going to host a login / logout button. You may say, that is not very useful. I would agree with you, but I can imagine this could be useful for some other cases that are not quite a simple as this one...
CodeBehind: Page.xaml.cs
#region
using System;
using System.Windows;
using System.Windows.Browser;
using System.Windows.Controls;
using System.Windows.Media.Imaging;
#endregion
namespace FaceBookConnect
{
[ScriptableType]
public partial class Page : UserControl
{
private bool _loggedin;
public Page()
{
this.InitializeComponent();
this.Loaded += this.Page_Loaded;
}
private void Page_Loaded(object sender, RoutedEventArgs e)
{
HtmlPage.RegisterScriptableObject("slPage", this);
}
[ScriptableMember]
public void LoggedIn()
{
this.btnLogin.Content = new Image
{
Source = new BitmapImage(
new Uri("Images/logout_large.png",
UriKind.Relative))
};
this._loggedin = true;
}
private void Button_Click(object sender, RoutedEventArgs e)
{
if (this._loggedin == false)
{
HtmlPage.Window.Invoke("login");
}
else
{
HtmlPage.Window.Invoke("logout");
this.btnLogin.Content = new Image
{
Source = new BitmapImage(
new Uri("Images/connect_light_medium_long.png",
UriKind.Relative))
};
this._loggedin = false;
}
}
}
}
What are we doing here? Basically, this code invokes login, and logout in js in the page. On login confirmed from facebook, we are alerted via script calling into managed code. I didn't bother styling the button very much... It's pretty lame as far as that goes, but it does achive the end goal -- bring in the designers :)!
Now what should our project look like... I'm going over this pretty quick, because the code will be zipped up down below. I will give you the opportunity to go over it yourself :).

That's pretty much it. Please check out the code below. As always, thank you.. come again!
Twitter: @DavidJustice
Code

Lately, I have been working in Silverlight 2 quite a bit. I
have been infused with inspiration from the Chicago
PhizzPop Design Challenge. I'm waiting for the pictures and vids
from a couple people to be served. I will be linking them into the blog.
For the time being, I have been hacking away at some of my own interests.
I ran into some interesting issues with the SL 2 binding. I
don't think these are new. There have been several posts about them in
the past, but I wanted to dig into them for myself, and see what reflector had
to say about it.
Update: I was completely wrong... "I will take SWORDS for 500 Alex"
Thankfully, a very friendly and knowledgeable Justin-Josef Angel helped me out with the issue and learned me 'bout some silverlight. Thank you very much Justin! Ok, so what I was trying to do was a little boneheaded (we all know pride tastes really bad)... Really, the way around the issue, as Justin pointed out, is to handle the PropertyChangedCallback on the dependency property rather than trying to place logic in the setter of the CLR Property which fronts the DependencyProperty. I am providing below the updated GlassButton class with the changes suggested.
We can all be pretty damn dumb from time to time. All we can hope is to try to learn from our mistakes, so we can be just that little bit better the next day. Anything you read below with a line struck through it, is null and void (aka dumbness). I hope this helps everyone out :).
public class GlassButton : Button
{
public static readonly DependencyProperty _radiusProperty = DependencyProperty.Register("Radius",
typeof (double),
typeof (GlassButton),
new PropertyMetadata(
new PropertyChangedCallback
(RadiusCallback)));
public double Radius
{
get { return (double) this.GetValue(_radiusProperty); }
set { this.SetValue(_radiusProperty, value); }
}
private static void RadiusCallback(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
var value = (double) e.NewValue;
if (value > 0)
{
((FrameworkElement) d).RenderTransform = new ScaleTransform {ScaleX = value/26, ScaleY = value/26};
}
}
}
The basic scenario is as follows: I have done quite a bit of
WPF programming in the past (since back when it was WinFx). I feel pretty damn good
about the bindings in WPF, and I feel like I have wrapped my head around
binding and dependency properties pretty well. So, I thought when I decided
to write Silverlight 2 apps rather than WPF apps, it would
be a very similar feeling. The feeling was abruptly interrupted by the
evilness of the ElementName Binding param. For those of you who have
spent time writing WPF apps, you will know the joy of binding element
properties to each other and having no problems. It's easy to take such
things for granted.
I understand you have to trim down the size of the download package for
SL, and I am perfectly groovy with that fact. The issue I have with it,
is that there is no recourse for a developer to step outside of those bounds.
Meaning, I would like to have my CustomDependencyProperties be able to
take part in XAML binding, the same way CoreDependencyProperties take part in
binding. Below, I'm going to outline some code to illustrate my issue.
Mind you this code is not at all cool. It just is there to elucidate
my point. If you want cool code, you can look to my boy Brownie, or
some other person in a better mood.
XAML:
<UserControl x:Class="Test.Page"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:Test="clr-namespace:Test"
Width="400" Height="300">
<Canvas>
<Canvas.Resources>
<Test:BindingHelper x:Key="bindingHelper"/>
</Canvas.Resources>
<Test:GlassButton x:Name="glass" Content="{Binding Value, Source={StaticResource bindingHelper}}"
Radius="{Binding Value, Source={StaticResource bindingHelper}}" Canvas.Top="10"/>
<Slider Value="{Binding Value, Source={StaticResource bindingHelper}, Mode=TwoWay}"
Width="100" Maximum="100" Minimum="0" Height="20"/>
</Canvas>
</UserControl>
BindingHelper:
#region
using System.ComponentModel;
#endregion
namespace Test
{
public class BindingHelper : INotifyPropertyChanged
{
private double value;
public double Value
{
get { return this.value; }
set
{
this.value = value;
if (this.PropertyChanged != null)
{
this.PropertyChanged(this, new PropertyChangedEventArgs("Value"));
}
}
}
#region INotifyPropertyChanged Members
public event PropertyChangedEventHandler PropertyChanged;
#endregion
}
}
GlassButton:
#region
using System.Windows;
using System.Windows.Controls;
using System.Windows.Media;
#endregion
namespace Test
{
public class GlassButton : Button
{
public static readonly DependencyProperty _radiusProperty = DependencyProperty.Register("Radius", typeof (double),
typeof (GlassButton), null);
public double Radius
{
get { return (double)GetValue(_radiusProperty); }
set
{
if (value > 0)
{
this.RenderTransform = new ScaleTransform {ScaleX = value/26, ScaleY = value/26};
this.SetValue(_radiusProperty, value);
}
}
}
}
}
Check out the code if you will. It's in a nice little sln zipped up, with a bow on top. Cheers! CODE ZIPPED UP
Twitter: @DavidJustice

OK, so I'm starting to sound repetitive about my excitement around
Windows Azure, but I really think it will help developers create new products
with an all time low cost to enter their specific market. Not only will it cost less to enter into
their market, I think it will help them scale their service offerings as their
business grows. We all want our
businesses to grow, but many of the initial development choices one makes when
driving to release a product do not always make sense when your customer base
grows in a few orders of magnitude.
I'm also stoked about the Silverlight Toolkit released 10.29.2008
(haven't used stoked in a while - I wonder if I can bring it back...). These controls make developing for
Silverlight a real joy. I was skeptical about
the Silverlight 1 release, as well as the initial release of WPF (which is like
forever ago), not because of the architecture or technology, but because of the
lack of controls. In the case of WPF, many
of my fellow developers refused to move from Windows Forms, because of the rich
tool sets they already had. I think MS
heard the call and has worked to remedy the situation.
I melded an Azure Web Role project and the Silverlight Toolkit
sample to give you guys a quick download, so you can play with them
together. I hope you like it, and I hope
it helps you explore some of the new technology. I call it SilverLining.
You'll need the Azure SDK, and Silverlight tools.
Twitter: @DavidJustice
This morning I found myself wrestling with SSIS to convert a
string from a flat file to a unique identifier via a Data Flow inside of an
SSIS package. I figured this would be a rather trivial case (the midget was kicking my ass!). I use
guids all over for application development and for database keys. They
are very useful, and very dependable. Here is a
line from my flat file:
61898d4c-3a1b-4736-9a36-eb90a23322e0|:|10/13/2008 11:59:58
PM|:|74afebfe-9523-4977-b5f6-5154b6c91211
Anyone see anything wrong with this? I didn't see anything
wrong, outside of the silly |:| delimiter (I don't want to get started on that
<rant/> <--- rant with no content!).
So moving forward, I created a Flat File Source, pointed to the
file, had it guess the appropriate type for import (it selected a 36 character
dt_str - fine with me), and then went into the advanced edit section and
changed the output for the column to be a unique identifier. I would expect the conversation to take place
in the middle somewhere, and if the powers that be smile kindly upon me, all
should work out well. Unfortunately, I
would get an error about truncating data, "The value could not be
converted because of a potential loss of data." I was very confused by this. I tried to push the string input from the
flat file data through a Data Converter step and do the conversion there, but
that had the same results. Basically
from that point on for about an hour, I tried every different way I could think
of to convert that guid string into a SQL unique identifier.
Eventually I gave up. The
web turned up little help, and I was nearing my wits end. I don't enjoy working on SSIS packages, and
this was not helping. Thankfully, I have
an in-house SQL ROCKSTAR!! My good
friend Chuck (a
SQL MVP) has helped me though all sorts of SQL issues in the past. I asked him about this issue, and although he
wasn't completely sure, he thought the error might be because I didn't wrap the
guid strings in braces. <rant> I
thought he was absolutely insane! Why
the heck would SSIS expect those guids to be in braces!? Why couldn't it cast them as unique
identifiers? I can say ‘61898d4c-3a1b-4736-9a36-eb90a23322e0'
as uniqueidentifier, and the T-SQL world doesn't come to a grinding halt!!
</rant>
The new input looks like this:
{61898d4c-3a1b-4736-9a36-eb90a23322e0}|:|10/13/2008 11:59:58
PM|:|{74afebfe-9523-4977-b5f6-5154b6c91211}
I went through the steps above, and tested the solution. That's it! It works like a
champ now. Thx u Chuck!!
Twitter: @DavidJustice
Basically, I wanted to build a method that gets an object from a data context whatever the primary key may look like, and whatever type that object may be. I wrote this code a little while ago when I was exploring the DynamicData libs. I was checking out some of the code in the libs, and noticed a very slick way one of devs was building expressions to grab back a data item based on a single key ID. I thought the idea of building up the expression completely ROCKED, but I wanted to expand it out to include composite primary keys. Below is my implementation of the composite primary key object fetcher. Hopefully, it will make your life a little easier.
(Needed to grab the MetaModel class)
using System.Web.DynamicData;
(Create a new MetaModel for your Context or Contexts -- make sure they are only registered once!! This can be an issue if you put this code in a static constructor, and you happen to have a generic class. That would cause the code to get executed each time you specify a new generic argument for type construction (sry, I digress))
Model = new MetaModel();
Model.RegisterContext(typeof([Your Context Type]));
(Get your meta table based on the type from your registered context -- need the metadata about the table to figure out the keys)
protected static MetaTable GetMetaTable<T>()
{
return dataModelMetaModel.GetTable(typeof (T));
}
(This is where the heavy lifting occurs. I commented what is going on. There is not much more to say. Enjoy!)
private static T FetchObject<T>(MetaTable metatable, IDictionary<string, object> pks)
where T : class
{
IQueryable query = metatable.GetQuery();
//build linq expression tree for where clause
ParameterExpression entityparam = Expression.Parameter(metatable.EntityType, "e");
List<Expression> internalExpressons = new List<Expression>();
Expression equalexpression;
foreach (MetaColumn member in metatable.PrimaryKeyColumns)
{
//convert primary key to proper type
PropertyInfo columnpropertyinfo = member.EntityTypeProperty;
MemberExpression columnexpresson = Expression.MakeMemberAccess(entityparam, columnpropertyinfo);
internalExpressons.Add(Expression.Equal(columnexpresson, Expression.Constant(pks[member.Name])));
}
// build up the primary key expressions
if (internalExpressons.Count > 1)
{
equalexpression = Expression.And(internalExpressons[0], internalExpressons[1]);
for (int i = 2; i < internalExpressons.Count; i++)
{
equalexpression = Expression.And(equalexpression, internalExpressons);
}
}
else
{
equalexpression = internalExpressons[0];
}
// Create the where clause
LambdaExpression wherelambda = Expression.Lambda(equalexpression, entityparam);
MethodCallExpression wherecall = Expression.Call(typeof (Queryable), "Where", new[] {metatable.EntityType},
query.Expression, wherelambda);
query = query.Provider.CreateQuery(wherecall);
// Call FirstOrDefault to make sure the connection is closed when finished
// saw some connections staying open when just grabbing the first object.
return query.Cast<T>().FirstOrDefault();
}
Twitter: @DavidJustice
I've been very excited recently by the release of Windows Azure, and rest of the Microsoft suite of cloud based services. I downloaded all of the sdk's, signed up for all the invitation tokens I could, and began writing code. The Visual Studio templates for Windows Azure projects makes getting your first Azure project up and running super simple. I did run into one issues with the project templates setting up my first project.
Basically, the DevelopmentStorage.exe.config for windows Azure expects you to have SQLExpress installed on your machine. I know it probably says it in quite a few places in the documentation, but instructions and documentation are for after the first faliure ;). I don't have SQLExpress installed on my machine. I run SQL2008 Dev... Now, it would not be very tough to go out and download SQLExpress, but I don't want to (a bit of laziness is good for all developers, without it your code would never be DRY). So, I just went into the DevelopmentStorage.exe.config, and editted the refs for SQLExpress, and just replaced it with localhost (I have an unnamed instance), and all was well in the world of Azure DB Objects. You should be able to find your DevelopmentStorage.exe.config at C:\Program Files\Windows Azure SDK\v1.0\bin.
I hope you have clear blue skys ahead of you!
UPDATE: I noticed that my development storage was not starting the table service for me. I reflected out the developmentstorage.exe and found that I was not supplying a proper dbName in the configuration file. I doctored up my DevelopmentStorage.exe.config configuration file to look like this:
<service name="Table" url="http://127.0.0.1:10002/" dbServer="localhost" dbName="developmentstoragedb"/>
Twitter: @DavidJustice