Tuesday, February 2, 2010

WPF Commands in IronPython

Dependency Properties and Commands are very useful WPF features.

In my last post I wrote about how to use Dependency Properties in IronPython. In this post we will see how to implement and use the WPF RelayCommand (for more details see WPF Apps With The Model-View-ViewModel Design Pattern).

 

import clr

clr.AddReference("WindowsBase")
clr.AddReference("PresentationCore")
clr.AddReference("PresentationFramework")

from System import (
    EventArgs
)

from System.Windows import (
    DependencyObject
)

from System.Windows.Input import (
    ICommand
)

class RelayCommand(ICommand):

    def __init__(self, executeFunction, canExecuteFunction):
        self._executeFunction = executeFunction
        self._canExecuteFunction = canExecuteFunction
        self._handlers = []

    def CanExecute(self, parameter):
        return self._canExecuteFunction(parameter)

    def add_CanExecuteChanged(self, handler):
        self._handlers.append(handler)

    def remove_CanExecuteChanged(self, handler):
        self._handlers.remove(handler)

    def canExecuteChanged(self):
        for handler in self._handlers:
            handler(self, EventArgs.Empty)

    def Execute(self, parameter):
        self._executeFunction(parameter)
        self.canExecuteChanged()


class Planning(DependencyObject):

    _sessionProperty = None

    def __new__(cls):
       if not Planning._sessionProperty:
            Planning._sessionProperty = DependencyProperty.Register(
                "session", clr.GetClrType(Session), clr.GetClrType(Planning))   
        return DependencyObject.__new__(cls)

    def __init__(self):
        self.loginCommand = RelayCommand(lambda p : self.login(p), lambda p : not self.session)
    def login(self, user):
        self.session = Session(user)

    def getSession(self):
        return self.GetValue(Planning._sessionProperty)

    def setSession(self, value):
        self.SetValue(Planning._sessionProperty, value)

    session = property(getSession, setSession)

Friday, January 29, 2010

WPF Dependency Properties in IronPython

One of the best features added to WPF are Dependency Properties. Dependency properties use a combination of a property and a static field (a class field in python).

As follows you will find an example:

import clr

clr.AddReference("WindowsBase")
clr.AddReference("PresentationCore")
clr.AddReference("PresentationFramework")

from System.Windows import (
DependencyObject, DependencyProperty
)


class Planning(DependencyObject):

_sessionProperty = None

def __new__(cls):
if not Planning._sessionProperty:
Planning._sessionProperty = DependencyProperty.Register(
"session", clr.GetClrType(Session), clr.GetClrType(Planning))
return DependencyObject.__new__(cls)

def getSession(self):
return self.GetValue(Planning._sessionProperty)

def setSession(self, value):
self.SetValue(Planning._sessionProperty, value)

session = property(getSession, setSession)

Sunday, December 27, 2009

Using an IronPython object from C#

The new keyword “dynamic” added to C# (.Net 4.0) allows you to interoperate with any dynamic language such as IronPython or IronRuby.

This new feature bypasses any static type checking at compile time, assuming that any operation is allowed. But, if it is not allowed, an error will be showed at run time.

For example, the following Customer “IronPython Class” is invoked from the C# code as a dynamic object:


IronPython code (Sample.py)

# Function (method) that creates a new Customer
def CreateCustomer(firstName, lastName):
    return Customer(firstName, lastName)

# Customer object
class Customer(object): 

    # Initialization (constructor)
    def __init__(self, firstName, lastName):
        self._firstName = firstName
        self._lastName = lastName

    # Function (method) that print the customer
    def printNames(self):
        print self._firstName + ' ' + self._lastName


C# code (Program.cs)

using Microsoft.Scripting.Hosting;
using IronPython.Hosting;

class Program
{
    static void Main(string[] args)
    {

        ScriptRuntime py = Python.CreateRuntime();
        dynamic sample = py.UseFile("Sample.py");
        dynamic customer = sample.CreateCustomer("Paul", "Smith");
        customer.printNames();
    }
}


You can download the source code here.

Tuesday, December 22, 2009

Using PLINQ to improve performance

The version 4.0 of .Net has a new feature called “Parallel LINQ” or PLINQ. If you use LINQ to filter or process a large amount of objects in memory and/or it is required a high-cost evaluation, PLINQ is for you.

PLINQ segments the source in parts and it uses different threads in order to process each segment.

var validCustomers = allCustomers.AsParallel()
  .Where(c => c.IsValid())
  .ToArray();

PLINQ

Here you can download the sample code.

For more details I recommend you to watch the Igor Ostrovsky presentation in the PDC 2009 webpage.

Monday, November 30, 2009

Entity Framework 4.0 - Foreign Key Relationships

The current version of EF (v3.5) maps table relationships as properties, hiding database foreign-key columns. However, there are some scenarios where you don’t need the entire referenced object to do some operation, you only need its “Id” (foreign key).

For example, in a web application it is very common to use combo-boxes in order to assign relationships. In these scenarios, after a post-back it is necessary to re-create the model and its relationships (using combo-boxes “selected values”). Since you don’t have the referenced objects, you must get them from the database or use “Stub Entities” to simulate them.

To solve this problem, the version 4.0 will also allow you to map foreign-key columns as properties, making it easier.

More info: http://blogs.msdn.com/adonet/archive/2009/11/06/foreign-key-relationships-in-the-entity-framework.aspx.

Thursday, November 26, 2009

WF Course

Last week I was teaching a three days course about WF (Windows Workflow Foundation).

The content was the following:

Day OneWF
Introduction
Parameters
Conditions
Persistence
WebServices
LocalServices

Day Two
Errors
FaultHandlers
Transactions
Compensation
Compensation + Transaction

Day Three
Parallel Execution
WCF
Tracking
Custom Activities
WF v4 Overview
Questions

 

Here you can download the presentation (in Spanish).

And here is the code: DayOne, DayTwo and DayThree.

Wednesday, October 14, 2009

POCO in Entity Framework 4.0

The new version (4.0) of Entity Framework allows us to use “Plain Old CLR Objects” as entities. In the current version (3.5) every entity must inherit from EntityObject, but in the new version it is possible to use a simple POCO:

public class Order
{
  public Guid Id { get; set; }
  public Product Product { get; set; }
  public int Quantity { get; set; } 
}

In order to use this new feature it is necessary to follow these three steps:
1. Create the edmx file (ModelEntities). 
2. Turn off the code generation removing the value of the “Custom Tool” property.
3. Create the context this way:

public class ModelContext : ObjectContext
{   
  public ModelContext() : base("name=ModelEntities", "ModelEntities")  
  {
  }

  public ObjectSet<Order> Orders
  {
    get { return base.CreateObjectSet<Order>(); }
  }
}

More information:
POCO in the Entity Framework: Part 1 - The Experience
POCO in the Entity Framework: Part 2 – Complex Types, Deferred Loading and Explicit Loading
POCO in the Entity Framework: Part 3 – Change Tracking with POCO