I Can't Believe That Worked

Code and Ideas, minus the profanity (the one language all developers know)

November 2008 - Posts

Silverlight 2 XAML Binding and Custom / Core Dependency Properties

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

kick it on DotNetKicks.com

Silver Lining for Windows Azure -- Silverlight 2 Sample Hosted in Azure

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

Unique Identifier Flat File Import with SSIS

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

 

MetaTable Expression Builder for Fetching Any Object Via Collection of Primary Keys

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

Windows Azure and _NOT_ SQLExpress

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