Wednesday, October 20, 2010

WPF - Single Instance Application

In this blog I will show how to implement an single instance application:


To implement, I will use Microsoft.Visualbasic library (latest version is 10.0.0.0).
In your main project, create a class inherit from WindowsFormsApplicationBase

public class SingleApp : WindowsFormsApplicationBase
{
   //this is the actual App class (App.xaml)
   private App _app;

   public SingleApp()
   {
      IsSingleInstance = true;
   }

   protected override bool OnStartup(StartupEventArgs eventArgs)
   {
      try
      {
         _app = new App();
         _app.Run();
      }
      catch (Exception ex)
      {
         //do handle exception
      }

      return false;
   }

   protected override void OnStartupNextInstance(StartupNextInstanceEventArgs eventArgs)
   {
      //make the running application do something. Show main window for exsample
      _app.NextInstanceRun();
   }
}

SingleApp will act like a Application host.
Now we create a static Main() function to run this SingleApp

public class AppAccessPoint
{
   /// <summary>
   /// Mains the specified args.
   /// This is the real entry point, not the WPF APP
   /// </summary>
   /// <param name="args">The args.</param>
   [STAThread]
   public static void Main(string[] args)
   {
      SingleApp manager = new SingleApp();
      manager.Run(args);
   }
}
 
 
make sure to change the start up project to the Main function
  Done 
 
 
 
 

Silverlight - Create an intance with Type from a ref assembly

Sometime, we need to create a class with type defined by runtime. These will help.
Below is a  helper class
 
public static class ReflectionHelper
{
      /// <summary>
      /// Gets a Type of an refed assembly.
      /// </summary>
      /// <param name="assemblyName">FULL Name of the assembly.</param>
      /// <param name="className">FULL Name of the class.</param>
      /// <returns></returns>
      public static Type GetAssemblyType(string assemblyName, string className)
      {
         StreamResourceInfo info = Application.GetResourceStream(new Uri(assemblyName, UriKind.Relative)); 

         Assembly assembly = new AssemblyPart().Load(info.Stream);
         Type type = assembly.GetType(className);
         return type;
      } 

      /// <summary>
      /// Gets A type of An RefFed assembly.
      /// </summary>
      /// <param name="className">FULL Name of the class.</param>
      /// <returns></returns>
      public static Type GetAssemblyType(string className)
      {
         Type type = null
         foreach (AssemblyPart part in Deployment.Current.Parts)
         {
            type = GetAssemblyType(part.Source, className); 

            if (type != null)
               break;
         }
         return type;
      }   
}
 
Next, we use the function
 
Type loaderType = ReflectionHelper.GetAssemblyType("AssemblyFullName.dll", "AssemblyFullName.ClassName"); 
object obj = Activator.CreateInstance(loaderType);

//my interface 
IToolLoader loader = obj as IToolLoader;

if (loader != null)
{ 
    //use  your interface
}


 

Reading XML through LINQ with Silverlight

Let's start with a simple xml file:

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<ImageDataSet xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
  <ImageData>
    <Index>30001</Index>
    <Name>icon1</Name>
    <Left>6</Left>
    <Top>4</Top>
    <Width>13</Width>
    <Height>5</Height>
  </ImageData>
  <ImageData>
    <Index>30002</Index>
    <Name>icon2</Name>
    <Left>6</Left>
    <Top>11</Top>
    <Width>13</Width>
    <Height>5</Height>
  </ImageData>
</ImageDataSet>

And an entity class
 
public class ImageData
{
   public int Index { getset; }
   public string Name { getset; }
   public double Left { getset; }
   public double Top { getset; }
   public double Width { getset; }
   public double Height { getset; }
}
 
Now we read the xml content by using this function

public static List<T> ReadXml<T>(Stream stream) where T : new()
{
    List<T> ts = new List<T>();
 
    Type type = typeof(T);
    PropertyInfo[] infos = type.GetProperties();
    XDocument xDoc = XDocument.Load(stream);
 
    var root = xDoc.Root;
    if (root != null)
    {
        foreach (XElement element in root.Elements(type.Name))
        {
         T t = new T();
         foreach (PropertyInfo propertyInfo in infos)
         {
             var ele = element.Element(propertyInfo.Name);
             if(ele != null)
             {
                 try
                 {
                    propertyInfo.SetValue(t, Convert.ChangeType(ele.Value, propertyInfo.PropertyType , null), null);
                 }
                 catch (Exception)
                 {
                        //type is not appropriate
                  }
               }
            }
            ts.Add(t);
        }
    }
    return ts;
}

The input stream can be getting by using Embedded Resources. In my sample ResourceData is a class in the same namespace.

Assembly assembly = typeof(ResourceData).Assembly;
Stream imageDataStream = assembly.GetManifestResourceStream(typeof(ResourceData), 
                          "Image1.xml");

var imageData = XmlHelper.ReadXml<ImageData>(imageDataStream);

J