Click here to Skip to main content
Click here to Skip to main content
Add your own
alternative version

How To Embed An Application Into a Docking Library

, 3 Sep 2011 CPOL
Step by Step conversion of an application into a Docking application component
SofaAdditionalExamples_-_Step_by_Step.zip
Examples
Step by step SofaComponization
0. Original CSWPFMasterDetailBinding
CSWPFMasterDetailBinding.suo
Data
Properties
Settings.settings
1. From Application To Component
1. From Application To Component.suo
CSWPFMasterDetailBinding
CSWPFMasterDetailBinding.csproj.user
Data
Properties
Settings.settings
SofaBasicContainer
Properties
app.manifest
Settings.settings
Resources
Sofa.bmp
Sofa
SofaBasicContainer.csproj - Copie.user
Perspectives
_Dev_SofaBasicContainer.csproj.user
_SofaBasicContainer.csproj.user
2. From Simple Component to sub-Components
2. From Simple Component to sub-Components.suo
CSWPFMasterDetailBinding
CSWPFMasterDetailBinding.csproj.user
Data
MainComponent.xaml.cs.bak
Properties
Settings.settings
SofaBasicContainer
BaseWindow.xaml.cs.bak
Properties
app.manifest
Settings.settings
Resources
Sofa.bmp
Sofa
SofaBasicContainer.csproj - Copie.user
Perspectives
_Dev_SofaBasicContainer.csproj.user
_SofaBasicContainer.csproj.user
3. About Perspectives
3. About Perspectives.suo
CSWPFMasterDetailBinding
CSWPFMasterDetailBinding.csproj.user
Data
MainComponent.xaml.cs.bak
Properties
Settings.settings
Service References
SofaBasicContainer
BaseWindow.xaml.cs.bak
Properties
app.manifest
Settings.settings
Resources
Sofa.bmp
Sofa
SofaBasicContainer.csproj - Copie.user
Perspectives
_Dev_SofaBasicContainer.csproj.user
_SofaBasicContainer.csproj.user
External dependencies
log4net.dll
Mef.Codeplex
System.ComponentModel.Composition.Codeplex.dll
System.ComponentModel.Composition.Registration.dll
System.Reflection.Context.dll
Prism.Mef_Codeplex
Microsoft.Practices.Prism.dll
Microsoft.Practices.Prism.Interactivity.dll
Microsoft.Practices.Prism.MefExtensions.dll
Microsoft.Practices.Prism.UnityExtensions.dll
Microsoft.Practices.ServiceLocation.dll
Microsoft.Practices.Unity.dll
Microsoft.Practices.Unity.Interception.dll
WPFToolkit.dll
Libraries
ExternalFrameworks.dll
Sofa.Commons.dll
Sofa.Component.dll
Sofa.Container.dll
Sofa.Themes.dll
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using log4net;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Input;
using Sofa.Container;
using Sofa.Commons;
using System.Xml.Serialization;
using System.Xml;
using System.IO;
using System.Reflection;
using System.Windows.Media;
using System.Windows.Threading;
using System.Deployment.Application;
using log4net.Appender;
using AvalonDock;

namespace SofaBasicContainer
{
    static class Utils
    {
        static readonly ILog Log = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);

        internal static void InvokeMethod(object target, string methodName, object[] parameters)
        {
            System.Type t = target.GetType();
            if (t != null)
            {
                System.Reflection.MethodInfo m = t.GetMethod(methodName);
                if (m != null)
                {
                    try
                    {
                        m.Invoke(target, parameters);
                    }
                    catch
                    {
                        Log.Error(string.Format("Error while invoking method '{0}' on type '{1}'. Check there is no error in the invoked code,", m, target));
                    }
                }
                else Log.Warn(String.Format("Method '{0}' was called but not found in '{1}'.", methodName, target.ToString()));
            }
            else Log.Warn(String.Format("Type of '{0}' was not found when invoking method '{1}'.", target.ToString(), methodName));
        }

        internal static void InvokeMethodInApp(SofaContainer sofaContainer, string productName, string method)
        {
            //If the productName Application is not in the same currentPerspective: GoToExisting or ImportInCurrent currentPerspective ?
            InvokeMethodInApp(sofaContainer, productName, method, ShowPerspectiveMode.ImportInCurrent);
        }

        internal static void InvokeMethodInApp(SofaContainer sofaContainer, string productName, string method, ShowPerspectiveMode showPerspectiveMode)
        {
            if (productName != null && productName != "" && method != null & method != "")
            {
                SofaComponent sofaComponent = null;

                //Search the component on ProductName + IsActiveXxxxxx = true (in case there's more that 1 instance component)
                //First try IsActiveContent (Component is in a DockablePane)
                try
                {
                    sofaComponent = sofaContainer.SofaComponentList.Single(delegate(SofaComponent c) { return c.ProductName == productName && ((ManagedContent)c.DockableContent).IsActiveContent == true; });
                }
                catch { }
                //If not dound
                if (sofaComponent == null)
                {
                    //Then try IsActiveDocument (Component is in a DocumentPane)
                    try
                    {
                        sofaComponent = sofaContainer.SofaComponentList.Single(delegate(SofaComponent c) { return c.ProductName == productName && ((ManagedContent)c.DockableContent).IsActiveDocument == true; });
                    }
                    catch { }
                }
                
                //Not found: The target is not yet opened
                if (sofaComponent == null)
                {
                    sofaComponent = sofaContainer.OpenComponent(productName);
                }

                //sofaComponent.UserControl = Component
                Type t = sofaComponent.UserControl.GetType();
                if (t != null)
                {
                    System.Reflection.MethodInfo m = t.GetMethod(method);
                    if (m == null)
                    {
                        string s = String.Format("Method called from a menu: Error while invoking method '{0}' on type '{1}'. The method does not exist or is not public", method, t);
                        Log.Error(s);
                        throw new ArgumentException(s);
                    }
                    else
                    {
                        try
                        {
                            if (m != null) m.Invoke(sofaComponent.UserControl, null);
                        }
                        catch (Exception e)
                        {
                            Log.Error(string.Format("Method called from a menu: Error while invoking method '{0}' on type '{1}'. Check there is no error in the invoked code,", m, t));
                            throw e;
                        }
                    }
                }
            }
        }

        public static string ObjectToXml(Object o)
        {
            StringWriter Output = new StringWriter(new StringBuilder());
            string Ret = "";

            try
            {
                XmlSerializer s = new XmlSerializer(o.GetType());
                s.Serialize(Output, o);

                Ret = Output.ToString().Replace("xmlns:xsd=\"http://www.w3.org/2001/XMLSchema\"", "");
                Ret = Ret.Replace("xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\"", "");
                Ret = Ret.Replace("<?xml version=\"1.0\" encoding=\"utf-16\"?>", "").Trim();
            }
            catch (Exception) { throw; }

            return Ret;
        }

        public static Object XmlToObject(string xml, Type t)
        {
            Object o;
            StringReader Input = new StringReader(xml);

            try
            {
                //XmlSerializer s = new XmlSerializer(typeof(Demo_Container.Model.Contact));
                XmlSerializer s = new XmlSerializer(t);
                o = s.Deserialize(Input);
            }
            catch (Exception) { throw; }
            return o;
        }

        public static void LoadResourceDictionary(string path, string assemblyFullName)
        {
            string dictionaryName = string.Format("/{0};component/{1}", assemblyFullName, path);
            var uri = new Uri(dictionaryName, UriKind.Relative);
            var dictionary = (ResourceDictionary)Application.LoadComponent(uri);
            Application.Current.Resources.MergedDictionaries.Add(dictionary);
        }

        //Finds a parent of a given item on the visual tree.
        public static T TryFindParent<T>(this DependencyObject child) where T : DependencyObject
        {
            //get parent item
            DependencyObject parentObject = GetParentObject(child);

            //we've reached the end of the tree
            if (parentObject == null) return null;

            //check if the parent matches the type we're looking for
            T parent = parentObject as T;
            if (parent != null)
            {
                return parent;
            }
            else
            {
                //use recursion to proceed with next level
                return TryFindParent<T>(parentObject);
            }
        }

        public static DependencyObject GetParentObject(this DependencyObject child)
        {
            if (child == null) return null;

            //handle content elements separately
            ContentElement contentElement = child as ContentElement;
            if (contentElement != null)
            {
                DependencyObject parent = ContentOperations.GetParent(contentElement);
                if (parent != null) return parent;

                FrameworkContentElement fce = contentElement as FrameworkContentElement;
                return fce != null ? fce.Parent : null;
            }

            //also try searching for parent in framework elements (such as DockPanel, etc)
            FrameworkElement frameworkElement = child as FrameworkElement;
            if (frameworkElement != null)
            {
                DependencyObject parent = frameworkElement.Parent;
                if (parent != null) return parent;
            }

            //if it's not a ContentElement/FrameworkElement, rely on VisualTreeHelper
            return VisualTreeHelper.GetParent(child);
        }


        internal static void SetLog4NetFile()
        {
            //Move log file to Sofa location
            foreach (IAppender appender in LogManager.GetRepository().GetAppenders())
            {
                String t = appender.GetType().ToString();

                //Move log file location
                if (t == "log4net.Appender.RollingFileAppender" || t == "log4net.Appender.FileAppender")
                {
                    FileAppender fileAppender = appender as FileAppender;

                    string d1;
                    if (ApplicationDeployment.IsNetworkDeployed)
                        d1 = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData), "Sofa");
                    else
                        d1 = Path.Combine(ContainerParameter.DebugDirectoryLocation, "Sofa");

                    string d2 = Path.Combine(d1, Path.GetFileName(fileAppender.File));
                    fileAppender.File = d2;
                    fileAppender.ActivateOptions();
                }

                //Disable console if not at dev time
                if (ApplicationDeployment.IsNetworkDeployed && t == "log4net.Appender.TraceAppender")
                {
                    TraceAppender traceAppender = appender as TraceAppender;
                    traceAppender.Threshold = log4net.Core.Level.Off;
                }
            }
        }


        internal static void CopySofaFolder()
        {
            string sourceFolder = @".\Sofa\";
            string destFolder;
            if (ApplicationDeployment.IsNetworkDeployed)
                destFolder = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData), "Sofa");
            else
                destFolder = Path.Combine(ContainerParameter.DebugDirectoryLocation, "Sofa");

            CopyFolder(sourceFolder, destFolder);
        }

        private static void CopyFolder(string sourceFolder, string destFolder)
        {
            if (Directory.Exists(sourceFolder))
            {
                if (!Directory.Exists(destFolder)) Directory.CreateDirectory(destFolder);

                string[] files = Directory.GetFiles(sourceFolder);
                foreach (string file in files)
                {
                    string name = Path.GetFileName(file);
                    string dest = Path.Combine(destFolder, name);
                    try { File.Copy(file, dest); }
                    //In case of error: Probably file already exists
                    catch { }
                    File.Delete(file);
                }

                string[] folders = Directory.GetDirectories(sourceFolder);
                foreach (string folder in folders)
                {
                    string name = Path.GetFileName(folder);
                    string dest = Path.Combine(destFolder, name);
                    CopyFolder(folder, dest);
                }
            }
        }

        internal static void AppDispatcherUnhandledException(object sender, DispatcherUnhandledExceptionEventArgs e)
        {
            String s = "DispatcherUnhandledExceptionEventArgs information:";
            s += String.Format("\nException.Message: '{0}'.", e.Exception.Message.ToString());
            s += String.Format("\nException.Source dll: '{0}'.", e.Exception.Source.ToString());
            if (e.Exception.InnerException != null)
            {
                s += String.Format("\nException.InnerException.Message: '{0}'.", e.Exception.InnerException.Message);
            }
            s += String.Format("\nException.StackTrace:");
            s += "\n" + e.Exception.StackTrace;

            Log.Error(s);
            MessageBox.Show("An error occured during the last operation.\nPlease contact your administrator.\n\nMessage:\n" + e.Exception.Message.ToString(), "Error");

            e.Handled = true;
        }
    }
}

By viewing downloads associated with this article you agree to the Terms of Service and the article's licence.

If a file you wish to view isn't highlighted, and is a text file (not binary), please let us know and we'll add colourisation support for it.

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)

Share

About the Author

Sofa Team

United States United States
No Biography provided

| Advertise | Privacy | Mobile
Web02 | 2.8.141022.2 | Last Updated 3 Sep 2011
Article Copyright 2011 by Sofa Team
Everything else Copyright © CodeProject, 1999-2014
Terms of Service
Layout: fixed | fluid