IanG on Tap

Ian Griffiths in Weblog Form (RSS 2.0)

Blog Navigation

August (2014)

(1 item)

July (2014)

(5 items)

April (2014)

(1 item)

March (2014)

(1 item)

January (2014)

(2 items)

November (2013)

(2 items)

July (2013)

(4 items)

April (2013)

(1 item)

February (2013)

(6 items)

September (2011)

(2 items)

November (2010)

(4 items)

September (2010)

(1 item)

August (2010)

(4 items)

July (2010)

(2 items)

September (2009)

(1 item)

June (2009)

(1 item)

April (2009)

(1 item)

November (2008)

(1 item)

October (2008)

(1 item)

September (2008)

(1 item)

July (2008)

(1 item)

June (2008)

(1 item)

May (2008)

(2 items)

April (2008)

(2 items)

March (2008)

(5 items)

January (2008)

(3 items)

December (2007)

(1 item)

November (2007)

(1 item)

October (2007)

(1 item)

September (2007)

(3 items)

August (2007)

(1 item)

July (2007)

(1 item)

June (2007)

(2 items)

May (2007)

(8 items)

April (2007)

(2 items)

March (2007)

(7 items)

February (2007)

(2 items)

January (2007)

(2 items)

November (2006)

(1 item)

October (2006)

(2 items)

September (2006)

(1 item)

June (2006)

(2 items)

May (2006)

(4 items)

April (2006)

(1 item)

March (2006)

(5 items)

January (2006)

(1 item)

December (2005)

(3 items)

November (2005)

(2 items)

October (2005)

(2 items)

September (2005)

(8 items)

August (2005)

(7 items)

June (2005)

(3 items)

May (2005)

(7 items)

April (2005)

(6 items)

March (2005)

(1 item)

February (2005)

(2 items)

January (2005)

(5 items)

December (2004)

(5 items)

November (2004)

(7 items)

October (2004)

(3 items)

September (2004)

(7 items)

August (2004)

(16 items)

July (2004)

(10 items)

June (2004)

(27 items)

May (2004)

(15 items)

April (2004)

(15 items)

March (2004)

(13 items)

February (2004)

(16 items)

January (2004)

(15 items)

Blog Home

RSS 2.0

Writing

Programming C# 5.0

Programming WPF

Other Sites

Interact Software

Generating WPF Content with LINQ

Tuesday 13 November, 2007, 05:37 PM

Mike Taulty recently posted an example showing how to use LINQ to generate a graph in XAML.

He uses the new XML literal syntax in VB.NET. Since C# doesn’t get that feature, an exact conversion to C# would be relatively verbose. So, score one to VB.NET? Not so fast. I wanted to show an alternative approach that works as well in C# as it does in VB.NET.

You don’t need to go via XAML for this sort of thing at all. Perhaps the most important thing to grasp about XAML in WPF is that anything you can do with XAML, you can also do with code. Here’s a LINQ example based on Mike’s program, but which bypasses the XAML completely:

public Window1()
{
  List<Point> data = new List<Point>();
  int width = 8 * 96;
  int height = 6 * 96;

  for (double i = 0; i < (Math.PI * 2); i += (Math.PI / 50))
  {
    data.Add(new Point(i, Math.Sin(i)));
  }

  this.Content = new Grid
  {
    Width = width, Height = height,
    Background = Brushes.Black,
    Children =
    {
      new Polyline
      {
        Stroke = Brushes.White,
        Stretch = Stretch.Fill,
        StrokeThickness = 2,
        Points = new PointCollection(
          from p in data
          select new Point(p.X, p.Y))
      }
    }
  };
}

This has much the same effect as Mike’s example. The main difference is that this builds the UI objects directly, whereas his code builds a XAML document which, if loaded, will create the UI objects. I’m assuming that we do actually want to show the graph, in which case the important thing is that you create the relevant objects—a Grid and a Polyline in this case. XAML is strictly optional in WPF; the objects describe the UI, and XAML is merely one convenient way to create those objects.

In fact, I’d argue that in this particular case, XAML might best be avoided. The problem with generating XAML from either C# or VB.NET is that you get no compile time type checking, and no IntelliSense. XAML-specific tools such as Visual Studio 2008’s WPF designer in can offer such facilities, but by intermingling XAML and code in one file, we make it harder for the tools to help us. By contrast, the technique I’m using here combines LINQ with WPF in a way that retains full compile-time checking and IntelliSense.

Moreover, the new C# 3.0 object initializer syntax offers something that used to be the preserve of XAML: I’ve been able to make my code’s structure directly reflect the structure of the objects I’m creating. (Creating trees of WPF objects in C# 2.0 is much more cumbersome and, in my opinion, is much harder to read than XAML. This is one of the main reasons we favoured XAML over C# in the examples in our WPF book.)

That said, sometimes you do actually want XAML. For example, if you’re building a Silverlight 1.0 application, you really do need to provide XAML, because there’s no other way to create new UI objects. (Silverlight 1.1 fixes that.) So Mike’s technique would be appropriate when generating XAML content on the fly on a web server, for example. And there are some things that are still pretty clunky in code—I’d rather set up data bindings in XAML than C#, for example.

This example starts off with some data generated by code, and so it’s easiest to remain entirely within one programming language. But in practice, most of your UI won’t be built from data. Even if you do have a significant amount of data-driven UI, you’re likely to have a lot of static content too. There are plenty of situations where XAML makes the most sense.

So I don’t want anyone reading this to go off and write something of the form “WPF author abandons XAML”... I’m still a big fan of XAML, and even with the better syntax available in C# 3.0 I’m not planning to get rid of the XAML examples in the next edition of Chris’s and my book. I just wanted to show that for certain tasks, it’s more straightforward to build UI objects directly from code. As ever, it’s a case of choosing the right tool for the job.

And don’t forget, data binding is sometimes a better solution to this kind of problem. See my harmonic series demo for an example of how to generate a graph in WPF with data binding.

Copyright © 2002-2013, Interact Software Ltd. Content by Ian Griffiths. Please direct all Web site inquiries to webmaster@interact-sw.co.uk