About Me
I'm a Software Engineer specialized in Microsoft technology with a special interest for Silverlight. Since 2007 I work for Rubicon as a Software Engineer.
|
Archive for December, 2008
|
|
|
Mark Monster
December 27th, 2008
.NET, Compact Framework, Technology
|
|
Just this week I bought a new mobile phone. Of course it’s a Windows Mobile powered mobile phone, a HTC Touch Diamond. I thought: "What about some .NET Compact Framework 3.5 development". So I started setting up a Windows Mobile Development VPC.
I started with the following:
- Windows Server 2008
- Visual Studio 2008 (with Smart Device extensions installed)
After this I wanted to be able to develop for Windows Mobile 6.x so I needed more, much more.
Installing Windows Mobile 6 wasn’t really easy. I needed a pre-requisite, Windows Mobile Device Center. But sadly trying to install this I got a very informative message: "The update could not be installed because at least one Windows component required by Windows Mobile Device Center is missing". So which component? After some Googling I found out it was the "Desktop Experience" feature that needed to be installed on Windows Server 2008. So it took me some time, but in the end I got the SDK running.
Next step would be getting the networking available from the emulator. This looked easy, but I got a strange message: "Failed to open the VPC Network Driver. Verify that the driver is installed…". So some more Googling. The solution lies in using the Windows Mobile Device Center for sharing the connection. This article explains everything (in the old days we would have used ActiveSync as mentioned in the article).
In the end I got my blog loaded in Internet Explorer on the Emulator.

|
|
|
Mark Monster
December 22nd, 2008
.NET, Silverlight, Technology
|
|
On the Silverlight forums I found out someone wants to refresh the Silverlight Object from Javascript. Basically this solution calls a Javascript function from the Silverlight environment. I though it would be a good way to make use of features available in Silverlight.js to make it easier to create the Javascript function to refresh the Silverlight Object. The strange thing was it took me a long time to get it to work. Yes this small part Javascript in the example below took me a very long time. This has all to do with using Google Chrome and Mozilla Firefox. In the end I was not able to get this working in Chrome and Firefox, I’m not sure if this is because of failing in Silverlight.js or not, but I was not even able to load an initial Silverlight Control from javascript.
The solution: One Javascript function, and a call from Silverlight to the Javascript function. (Only working from within Internet Explorer)
The Javascript function.
The function is very straight forward. I make use of the Silverlight.js function Silverlight.CreateObject. The function I created asks for three parameters, the hosting element (will contain the Silverlight control), the source (location of the xap file), and the initParams.
function CreateSilverlight(hostElement, source, initParams) {
var pluginId = hostElement.id + "PluginId";
hostElement.innerHTML = Silverlight.createObject(source,
null, pluginId,
{
width: "200", height: "50",
background: "white", alt: "<!--Silverlight 2.not installed-->",
version: "2.0.31005.0", autoUpgrade: true
},
{ onError: onSLError, onLoad: onSLLoad },
initParams, hostElement.id);
}
Make it load from the window.load.
window.onload = function() {
CreateSilverlight(silverlightControlHost, "ClientBin/MM.Silverlight.Experiments2.SUI.xap", "param1=value1,param2=value2");
}
The call from Silverlight.
I wanted to be able to see that the code was actually executed so I put a timestamp in. Calling Javascript from Silverlight is very easy, you can make use of either HtmlPage.Window.Eval or HtmlPage.Window.CreateInstance, I used HtmlPage.Window.Eval.
HtmlPage.Window.Eval(string.Format(
@"CreateSilverlight(silverlightControlHost,
'ClientBin/MM.Silverlight.Experiments2.SUI.xap',
'currenttime={0},otherparam=othervalue');", DateTime.Now));
This is all, nothing more, the sad part I only got it working in Internet Explorer, but that might be because of some bad Javascript. I attached the full solution for download.
|
|
|
Mark Monster
December 20th, 2008
Private Life
|
|
A small Christmas greeting from my family.

|
|
|
Mark Monster
December 20th, 2008
Technology
|
|
I’ve had trouble in the past with sharing my internet connection with Windows Server 2003 but also with Windows Server 2008 in Virtual PC. This is because I have no physical network connection at home, I do everything wireless. And setting the physical network device as network adapter for the virtual machine doesn’t work either. So I followed the following steps.
Step 1: Set the virtual machine settings to Shared Networking (NAT).
Step 2: Set the network settings inside the Virtual Machine, manual set the Preferred DNS Server to 192.168.131.254.
This did the trick for me. I hope this will work for more people because it did take me a long time to find this solution.
|
|
|
Mark Monster
December 7th, 2008
.NET, Silverlight, Technology
|
|
It’s already almost a year ago when I found out about Google Chart API. I used it for my year ending post of 2007. I haven’t done anything useful with Google Chart API after this post. But I’d like to experiment, so I thought what about an integration between Silverlight and the Google Chart API.
Integration
The integration is a very slim line. Just a HTTP Get to an Uri that follows the specs in the Google Chart API. The documentation consists of the following parts:
But all I used was basically the example on the API front page:
http://chart.apis.google.com/chart?cht=p3&chd=t:60,40&chs=250×100&chl=Hello|World
This example contains the following parts: Chart Type, Chart Data, Chart Size and Chart Labels.
How I want it to work?
I want to be able to do a very simple thing in the Silverlight application. No logic about how the integration is done, is a very important idea. I also have the meaning that we should not have to use a special control to view a chart, just because we already have an Image control for viewing an image. A chart is not that much more than an image, isn’t it?
1 var chartData = new GoogleChartData
2 {
3 Size = new Size(400, 200),
4 Type = ChartType.Pie3d,
5 Labels = {"Silverlight", "Flex"},
6 Data = {"20", "80"},
7 Title = string.Format("RIA's{0}Compared", Environment.NewLine)
8 };
9
10 chartImage.SetValue(HeightProperty, chartData.Size.Height);
11 chartImage.SetValue(WidthProperty, chartData.Size.Width);
12
13 chartImage.Source = googleChartBuilder.ConvertFrom(chartData);
Set up the chart data in lines 1 to 8. After this I want to make sure the target image control has the same dimensions as set in the chart data. Then run the GoogleChartBuilder to convert the data to an image.
The inner workings
The GoogleChartData class is just a data structure class.
1 public class GoogleChartData
2 {
3 public GoogleChartData()
4 {
5 Data = new List<string>();
6 Labels = new List<string>();
7 }
8
9 public IList<string> Data { get; set; }
10 public IList<string> Labels { get; set; }
11 public Size Size { get; set; }
12 public ChartType Type { get; set; }
13
14 public string Title { get; set; }
15 }
The logic is divided in two classes, one for constructing any uri you can think of, the other one for transforming the GoogleChartData into a querystring dictionary. The UriBuilder is very simple just ensures that the first part is preceded by a ?-character and the next parts are preceded by the &-character.
1 public class UriBuilder : IUriBuilder
2 {
3 public Uri Build(string baseUri, string page, IDictionary<string, string> queryString)
4 {
5 if(string.IsNullOrEmpty(baseUri) && string.IsNullOrEmpty(page))
6 throw new Exception("baseUri and/or page should be provided.");
7
8 UriKind kind;
9 if (string.IsNullOrEmpty(baseUri))
10 kind = UriKind.Relative;
11 kind = UriKind.Absolute;
12
13 var uriBuilder = new StringBuilder(string.Concat(baseUri,page));
14 if(queryString!=null && queryString.Count >0)
15 {
16 char separatorCharacter = '?';
17 foreach (var queryPart in queryString)
18 {
19 uriBuilder.Append(separatorCharacter);
20 uriBuilder.Append(queryPart.Key);
21 uriBuilder.Append('=');
22 uriBuilder.Append(HttpUtility.UrlEncode(queryPart.Value));
23
24 separatorCharacter = '&';
25 }
26 }
27 return new Uri(uriBuilder.ToString(), kind);
28 }
29 }
Now for the part that’s responsible for the translation of the GoogleChartData into an uri.
1 public class GoogleChartBuilder : IGoogleChartBuilder
2 {
3 private readonly IUriBuilder uriBuilder;
4
5 public GoogleChartBuilder(IUriBuilder uriBuilder)
6 {
7 this.uriBuilder = uriBuilder;
8 }
9
10 public BitmapImage ConvertFrom(GoogleChartData googleChartData)
11 {
12 IDictionary<string,string> queryString = new Dictionary<string, string>();
13
14 //ChartSize
15 queryString.Add("chs",string.Format("{0}x{1}",googleChartData.Size.Width,googleChartData.Size.Height));
16
17 //ChartType
18 if(googleChartData.Type == ChartType.Pie3d)
19 queryString.Add("cht","p3");
20
21 //Labels
22 if (googleChartData.Labels != null && googleChartData.Labels.Count > 0)
23 queryString.Add("chl",string.Join("|", googleChartData.Labels.ToArray()));
24
25 //Data
26 if (googleChartData.Data != null && googleChartData.Data.Count > 0)
27 queryString.Add("chd", string.Concat("t:",string.Join(",", googleChartData.Data.ToArray())));
28 //Title
29 if(!string.IsNullOrEmpty(googleChartData.Title))
30 queryString.Add("chtt",googleChartData.Title.Replace(" ","+").Replace(Environment.NewLine,"|"));
31 return new BitmapImage(uriBuilder.Build("http://chart.apis.google.com/", "chart", queryString));
32 }
33 }
This isn’t that difficult and translates into something like the following.
This solution is not done at all, it’s just a proof-of-concept of the integration of Silverlight and the Google Chart API. You can download the sources here.
|
|
|
Mark Monster
December 7th, 2008
.NET, Silverlight, Technology
|
|
Sometimes you want to know the username of a user that’s logged on to your domain. This specially the occasion for intranet applications. Let’s assume we are building an intranet application because this is the only occasion where a NTLM username is valid I guess. There is no way we can get the NTLM Username directly from within Silverlight yet. So we have two options left: Client Side Javascript and Server Side scripting.
Client Side
Let’s begin with the Client Side Javascript. At least we should start investigating it. The first piece of code I found makes use of ActiveX, see the following:
var wshshell=new ActiveXObject("wscript.shell");
var username=wshshell.ExpandEnvironmentStrings("%username%");
Sadly it throws an error, not a good start. Google again. Not many options left, most people just say it isn’t possible. After a while I found the following:
var wshNetwork = new ActiveXObject("WScript.Network");
var username = WshNetwork.UserName;
But this also throws an error. So I guess we are left to the Server Side solution.
Server Side
So what we have left is Server Side scripting. We can again take different approaches like calling the server side through Ajax but I took the easy way, by just generating the NTLM Username into the HTML. We can make use of the InitParams to pass some startup parameters to the Silverlight control. The InitParams is a string that has comma-separated name-value pairs that are separated by the equals sign. So this could look like the following in HTML:
<param name="InitParams" value="name1=value1,name2=value2" />
What we do in the ASPX page where the Silverlight control is hosted, add the following code in the Page_Load:
1 if (User != null && User.Identity != null && User.Identity.IsAuthenticated)
2 Silverlight1.InitParameters = string.Format("User.Identity.Name={0}", User.Identity.Name);
In Silverlight we can read this value in the App.xaml.cs.
1 private void Application_Startup(object sender, StartupEventArgs e)
2 {
3 string userName = e.InitParams["User.Identity.Name"];
4 this.RootVisual = new Page();
5 }
The generated HTML looks like the following:
<param name="InitParams" value="User.Identity.Name=DOMAINNAME\Username"></param>
|
|
|
Mark Monster
December 6th, 2008
.NET, LINQ, ORM, Technology
|
|
Beside column mapping we did in Part 1 of the "Linq to SQL doing it manually" series. We also want to have relationships, this part will be all about relationships. The series contains the following parts:
When we take a look at the generated code for a one-to-many relation it has the following looks.
For the one-side:
1 private EntityRef<Post> _Post;
2 [Association(Name="Post_PostTagRelation", Storage="_Post", ThisKey="PostId", OtherKey="Id", IsForeignKey=true)]
3 public Post Post
4 {
5 get
6 {
7 return this._Post.Entity;
8 }
9 set
10 {
11 Post previousValue = this._Post.Entity;
12 if (((previousValue != value)
13 || (this._Post.HasLoadedOrAssignedValue == false)))
14 {
15 this.SendPropertyChanging();
16 if ((previousValue != null))
17 {
18 this._Post.Entity = null;
19 previousValue.PostTagRelations.Remove(this);
20 }
21 this._Post.Entity = value;
22 if ((value != null))
23 {
24 value.PostTagRelations.Add(this);
25 this._PostId = value.Id;
26 }
27 else
28 {
29 this._PostId = default(System.Guid);
30 }
31 this.SendPropertyChanged("Post");
32 }
33 }
34 }
35
36 private System.Guid _PostId;
37 [Column(Storage="_PostId", DbType="UniqueIdentifier NOT NULL", IsPrimaryKey=true)]
38 public System.Guid PostId
39 {
40 get
41 {
42 return this._PostId;
43 }
44 set
45 {
46 if ((this._PostId != value))
47 {
48 if (this._Post.HasLoadedOrAssignedValue)
49 {
50 throw new System.Data.Linq.ForeignKeyReferenceAlreadyHasValueException();
51 }
52 this.OnPostIdChanging(value);
53 this.SendPropertyChanging();
54 this._PostId = value;
55 this.SendPropertyChanged("PostId");
56 this.OnPostIdChanged();
57 }
58 }
59 }
For the many-side:
1 private EntitySet<PostTagRelation> _PostTagRelations;
2 [Association(Name="Post_PostTagRelation", Storage="_PostTagRelations", ThisKey="Id", OtherKey="PostId")]
3 public EntitySet<PostTagRelation> PostTagRelations
4 {
5 get
6 {
7 return this._PostTagRelations;
8 }
9 set
10 {
11 this._PostTagRelations.Assign(value);
12 }
13 }
I think this is a lot of code. So let’s try to minimize this.
For the one-side:
1 [Column(IsPrimaryKey = true)]
2 private Guid PostId { get; set; }
3
4 [Association(IsForeignKey = true, ThisKey = "PostId")]
5 public Post Post { get; set; }
For the many-side:
1 private IList<PostTagRelation> postTagRelations = new List<PostTagRelation>();
2 [Association(Storage = "postTagRelations", OtherKey = "PostId")]
3 public IList<PostTagRelation> PostTagRelations
4 {
5 get { return postTagRelations; }
6 set { postTagRelations = value; }
7 }
A lot less code I would guess. From 72 lines to just 12 lines. But we are not there yet. After some testing I found out the generated relation is bi-directional, and the relation I created is just uni-directional. What does this mean? This means that if you manipulated either post.PostTagRelations or postTagRelation.Post the other will be changed as well in a bi-directional relation. I remember in the past you had to do something special to make this work with NHibernate. I have no solution for this right now, but you can take a look at how other people did something similar on CodePlex. One of the troubles I find in the solution they propose is the usage of EntityRef and EntitySet. Those are both parts of Linq to SQL and would kind of interfere with my other code-parts, if used.
Another feature that is lost is lazy loading. I must admit I don’t hate it being lost. I think people must think about persistence before doing everything automatically. So if we want to load only the tags we don’t have to anything special. But if we also want to load the PostTagRelations and the Posts with the tags we will have to add some DataLoadOptions. The following code example show how it works.
1 using (var context = new Context(""))
2 {
3 var dataLoadOptions = new DataLoadOptions();
4 dataLoadOptions.LoadWith<Tag>(t => t.PostTagRelations);
5 dataLoadOptions.LoadWith<PostTagRelation>(ptr => ptr.Post);
6 //dataLoadOptions.LoadWith<PostTagRelations>(ptr => ptr.Tag);
7 context.LoadOptions = dataLoadOptions;
8
9 var dotNetTag = (from tag in context.Tags
10 where tag.Name.Equals(".NET")
11 select tag).Single();
12
13 Assert.Equal(3, dotNetTag.PostTagRelations.Count());
14
15 var posts = from postTagRelation in dotNetTag.PostTagRelations
16 where postTagRelation.Post != null
17 select postTagRelation.Post;
18 Assert.Equal(3, posts.Count());
19
20 var tags = from postTagRelation in dotNetTag.PostTagRelations
21 where postTagRelation.Tag != null
22 select postTagRelation.Tag;
23 Assert.Equal(3, tags.Count());
24 }
The only thing I must admit, line 23 fails. The tags aren’t loaded in the PostTagRelations. I tried adding line 6 but this did throw an exception: "System.InvalidOperationException : Cycles not allowed in LoadOptions LoadWith type graph." I have no solution for this yet, but it has something to do with the bi-directional issue I also found.
There are some areas of improvement on the relationships with Linq to SQL.
|
|
|
Mark Monster
December 6th, 2008
Private Life
|
|
Just a few weeks ago I was on a trip with my department of Rubicon. Besides a good dinner we also went skydiving, indoor skydiving in Roosendaal. If you have a chance to take a sky dive lesson, I think you should take it. Thanks to Robert Krom for taking the picture.

|
|