如何使用silverlight加載動態庫(dll)併發布到IIS7

n  開發環境搭建

本程序採用Visual Studio 2010 Ultimate+ Silverlight 4爲開發環境,VS 2010下載地址參考\\192.168.75.5\共享軟件\常用軟件\visual studio,安裝方法不再詳述,Silverlight4_Tools下載地址參考http://www.microsoft.com/downloads/zh-cn/details.aspx?FamilyID=b3deb194-ca86-4fb6-a716-b67c2604a139

1.   安裝VS2010

2.   安裝Silverlight4_Tools

安裝時如果遇到如下錯誤:


請不要灰心,將Silverlight4_Tools.exe改爲Silverlight4_Tools.zip,則可以發現這就是一個壓縮包,文件內容如下:


l  首先安裝VS10-KB982218-v4.exe

l  接着安裝silverlight_sdk.msi

l  再安裝Silverlight_Developer.exe

爲了驗證Silverlight是否已經安裝成功,打開VS2010,單擊File->New->Project->Visual C#,選擇Silverlight Application,如圖:


一路往下:


打開MainPage.xaml.cs,在InitializeComponent行設置斷點,


按下F10,看看是否能夠調試,如果有錯誤提示,則說明安裝的Silverlight的Developer和RunTime版本不一致,請下載Silverlight Developer 和RunTime運行時庫,本才程序使用的版本爲4.0.605310,有需要者可聯繫([email protected]),如果提示不能安裝,則將先前安裝的版本卸載後重新安裝。4.0.608310下載地址爲(http://222.218.45.50:82/down/Silverlight.zip),至此,silverlight開發環境搭建完畢。


n  創建動態庫

首先,爲了測試Silverlight加載動態庫,我們打開VS 2010,編一個動態庫出來,步驟如下:File->New->Project->Visual C++->Win32 ConsoleApplication,將工程命名爲load_dll,如圖:


單擊ok,單擊Next,在Application Settings選擇Dll,如圖:


單擊Finish,完成動態庫的創建。爲了測試,我們在load_dll.cpp文件中添加兩個函數,命名爲add_number,sub_number,代碼如下:


選擇工程load_dll,右鍵->Add->New Item->Visual C++->Code->Module- DefinitionFile,將其命名爲load_dll,如圖


單擊Add,添加如下代碼:


單擊Build->Build Solution,完成動態庫的創建。

n  Silverlight之加載動態庫

打開VS 2010,單擊File->New->Project->Visual C#->Silverlight Application,將工程命名爲load_dll,如圖:


在彈出的對話框中單擊OK


完成load_dll工程的創建。打開load_dll.Web下的ClientBin目錄,將先前創建的load_dll.dll文件拷貝 到ClientBin目錄下,選擇ClientBing,右鍵->Add->Exist Item選擇拷貝過來的load_dll.dll,將其添加到ClientBin目錄中。爲了能夠在工程中加載動態庫,右鍵load_dll.Web->Add->New Item,在彈出的對話框中選擇Online Templates->選擇Web Service,命名爲WebService1.asmx,如圖:


單擊Add,完成asmx文件的添加。

在WebService1.asmx.cs文件中添加如下代碼:

using System;

using System.Collections.Generic;

using System.Linq;

using System.Web;

using System.Web.Services;

using System.Runtime.InteropServices;

 

namespace load_dll.Web

{

    /// <summary>

    /// Summary description for WebService1

    /// </summary>

    [WebService(Namespace= "http://tempuri.org/")]

    [WebServiceBinding(ConformsTo= WsiProfiles.BasicProfile1_1)]

    [System.ComponentModel.ToolboxItem(false)]

    // To allow thisWeb Service to be called from script, using ASP.NET AJAX, uncomment thefollowing line.

    //[System.Web.Script.Services.ScriptService]

    public class WebService1: System.Web.Services.WebService

    {

        const string DllPath = "G:/learn/silverlight/load_dll/load_dll.Web/ClientBin/load_dll.dll";

        [WebMethod]

        public string HelloWorld()

        {

            return"Hello World";

        }

 

        [WebMethod]

        public int SLAddNumber(inta, int b)

        {

            returnadd_number(a, b);

        }

 

        [WebMethod]

        public int SLSubNumber(inta, int b)

        {

            returnsub_number(a, b);

        }

 

        [DllImport(DllPath,CharSet = CharSet.Ansi, EntryPoint = "add_number", ExactSpelling = false)]

        public extern intadd_number(int a, intb);

 

        [DllImport(DllPath,CharSet = CharSet.Ansi, EntryPoint = "sub_number", ExactSpelling = false)]

        public extern intsub_number(int a, intb);

    }

}

可以看出DllPath被設置爲絕對路徑,爲什麼這麼設後面再說。右鍵load_dll.Web->Build,如果沒有出現錯誤則表示成功了一半,這個一定要編譯,否則下面的工作無法繼續,選中load_dll工程,右鍵->Add Service Reference,如圖:


單擊Discover,將自動列出WebService.asmx,雙擊MainPage.xaml,在Form上添加兩個按鈕,一個設爲相加,一個設爲相減,並分別雙擊,添加如下代碼:

using System;

using System.Collections.Generic;

using System.Linq;

using System.Net;

using System.Windows;

using System.Windows.Controls;

using System.Windows.Documents;

using System.Windows.Input;

using System.Windows.Media;

using System.Windows.Media.Animation;

using System.Windows.Shapes;

using load_dll.ServiceReference1;

 

namespace load_dll

{

    public partial class MainPage : UserControl

    {

        publicMainPage()

        {

            InitializeComponent();

        }

 

        privatevoid button1_Click(objectsender, RoutedEventArgs e)

        {

            //創ä¡ä建¡§webService代䨲理¤¨ª類¤¨¤的Ì?對?象¨®實º¦Ì例¤y

            WebService1SoapClientsclient = new WebService1SoapClient();

            sclient.SLAddNumberAsync(100, 50);

            sclient.SLAddNumberCompleted += new EventHandler<SLAddNumberCompletedEventArgs>(show_add);

        }

        public void show_add(objectsender, SLAddNumberCompletedEventArgs e)

        {

            MessageBox.Show((e.Result).ToString());

        }

        privatevoid button2_Click(objectsender, RoutedEventArgs e)

        {

            //創ä¡ä建¡§webService代䨲理¤¨ª類¤¨¤的Ì?對?象¨®實º¦Ì例¤y

            WebService1SoapClientsclient = new WebService1SoapClient();

            sclient.SLSubNumberAsync(100, 50);

            sclient.SLSubNumberCompleted += new EventHandler<SLSubNumberCompletedEventArgs>(show_sub);

        }

        public void show_sub(objectsender, SLSubNumberCompletedEventArgs e)

        {

            MessageBox.Show((e.Result).ToString());

        }

    }

}

按下F7鍵,編譯成功後,CTRl+F5運行即可看到如下效果:


n  Silverlight之IIS的安裝

爲了能夠運行ASP.NET服務,需要在部署機器上安裝IIS服務,這裏只說明如何在Windows 7上安裝IIS服務,方法如下:

單擊開始->控制面板->程序->打開或關閉windows功能,在彈出的對話框上選擇Internet信息服務->萬維網服務->應用程序開發功能->ASP.NET,如圖:


Windows 7 系統上安裝好IIS 服務後,默認就支持.asmx,和.xaml擴展名的文件,在XP系統上或者Server機器上部署IIS時,還需添加對上述兩種擴展名的支持,具體可用IIS 和MIME爲關鍵字搜索即可獲得方法。在瀏覽器輸入:http://127.0.0.1,如果出現IIS的歡迎界面,則說明IIS服務安裝成功。右鍵我的電腦->管理->服務和應用程序->Iternet 信息服務,可以看到IIS已經爲我們創建好了一個DefaultWeb Site站點。

n  Silverlight之發佈

前面,我們已經完成了名爲load_dll的Silverlight工程,現在我們要將其部署到IIS服務站點,還記得上面說過的動態庫的加載路徑的問題,這裏我們不能寫爲絕對路徑,需要設置爲虛擬的路徑,這樣客戶端在訪問服務端時才能訪問加載到這個動態庫,將先前的代碼修改如下:

using System;

using System.Collections.Generic;

using System.Linq;

using System.Web;

using System.Web.Services;

using System.Runtime.InteropServices;

 

namespace load_dll.Web

{

    public class DllInvoke

    {

        [DllImport("kernel32.dll")]

        privateextern static IntPtr LoadLibrary(Stringpath);

        [DllImport("kernel32.dll")]

        privateextern static IntPtr GetProcAddress(IntPtrlib, String funcName);

        [DllImport("kernel32.dll")]

        privateextern static bool FreeLibrary(IntPtrlib);

 

        public Delegate Invoke(StringAPIName, Type t)

        {

            IntPtrapi = GetProcAddress(hLib, APIName);

            return(Delegate)Marshal.GetDelegateForFunctionPointer(api,t);

        }

        privateIntPtr hLib;

        publicDllInvoke(String DLLPath)

        {

            hLib = LoadLibrary(DLLPath);

        }

        ~DllInvoke()

        {

            FreeLibrary(hLib);

        }

    }

    /// <summary>

    /// Summary description for WebService1

    /// </summary>

    [WebService(Namespace= "http://tempuri.org/")]

    [WebServiceBinding(ConformsTo= WsiProfiles.BasicProfile1_1)]

    [System.ComponentModel.ToolboxItem(false)]

    // To allow thisWeb Service to be called from script, using ASP.NET AJAX, uncomment thefollowing line.

    //[System.Web.Script.Services.ScriptService]

    public class WebService1: System.Web.Services.WebService

    {

        public delegate int Proc_add_number(inta, int b);

        public delegate int Proc_sub_number(inta, int b);

       

       // conststring DllPath ="G:/learn/silverlight/load_dll/load_dll.Web/ClientBin/load_dll.dll";

        [WebMethod]

        public string HelloWorld()

        {

            return"Hello World";

        }

 

        [WebMethod]

        public int SLAddNumber(inta, int b)

        {

            DllInvokeinvoke = new DllInvoke(Server.MapPath(@"~/ClientBin/load_dll.dll"));

            Proc_add_numberadd_number = (Proc_add_number)invoke.Invoke("add_number", typeof(Proc_add_number));

            returnadd_number(a, b);

        }

 

        [WebMethod]

        public int SLSubNumber(inta, int b)

        {

            DllInvokeinvoke = new DllInvoke(Server.MapPath(@"~/ClientBin/load_dll.dll"));

            Proc_sub_numbersub_number = (Proc_sub_number)invoke.Invoke("sub_number", typeof(Proc_sub_number));

            returnsub_number(a, b);

        }

 

        //[DllImport(DllPath,CharSet = CharSet.Ansi, EntryPoint = "add_number", ExactSpelling =false)]

        //publicstatic extern int add_number(int a, int b);

 

        //[DllImport(DllPath,CharSet = CharSet.Ansi, EntryPoint = "sub_number", ExactSpelling = false)]

        //publicstatic extern int sub_number(int a, int b);

    }

}

通過使用Server.MapPath(@"~/ClientBin/load_dll.dll")就可以將虛擬路徑轉換爲物理路徑了。打開ServiceReferences.ClientConfig,將

<endpoint address="http://localhost:62429/WebService1.asmx" binding="basicHttpBinding"

                bindingConfiguration="WebService1Soap" contract="ServiceReference1.WebService1Soap"

                name="WebService1Soap" />

修改爲

<endpoint address="http://192.168.202.168/WebService1.asmx" binding="basicHttpBinding"

                bindingConfiguration="WebService1Soap" contract="ServiceReference1.WebService1Soap"

                name="WebService1Soap" />

其中,192.168.202.168爲我的IIS服務地址,對應的修改即可。右鍵load_dll.Web->Publish,彈出的對話框中填入如下信息


ServiceURL爲本機地址,即IIS所在的機器,Site/application爲缺省站點名,單擊Publish,即可完成站點發布。

本程序的源碼我已經上傳到我的資源中,下載地址爲http://download.csdn.net/my/uploads,如果有需要可以跟我聯繫QQ:540331240

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章