Winform程序經(jīng)常需要引用一些第三方dll文件,這些dll在發(fā)布后與exe文件保存在同一目錄下,雖然將dll文件集成到exe中會(huì)增大文件尺寸,但程序目錄會(huì)相對(duì)整潔。
下面介紹一種比較簡(jiǎn)單的集成方法和注意事項(xiàng)。
第一步,將需要引用的dll文件復(fù)制到項(xiàng)目中
您可以:1.復(fù)制到項(xiàng)目根目錄;2.復(fù)制到某個(gè)文件夾中。
此處以將dll復(fù)制到"lib"文件夾為例。
將要引用的dll文件復(fù)制到"lib"文件夾中
第二步,引用復(fù)制到項(xiàng)目中的dll文件
右鍵點(diǎn)擊"引用"或項(xiàng)目名稱,選擇"添加引用(F)..."
切換至在“添加引用”對(duì)話框中的“瀏覽”選項(xiàng)卡,選擇項(xiàng)目目錄中剛剛復(fù)制過(guò)來(lái)的dll文件。
第三步,設(shè)置引用項(xiàng)的屬性為“復(fù)制到輸出目錄”為“不復(fù)制”
右鍵點(diǎn)擊“引用”文件夾中剛剛完成添加引用的項(xiàng)目,并點(diǎn)擊“屬性”
將“屬性頁(yè)”中的“復(fù)制本地”項(xiàng)改為“False”。
第四步,設(shè)置之前復(fù)制到項(xiàng)目中的dll文件屬性
右鍵點(diǎn)擊最開(kāi)始復(fù)制到項(xiàng)目目錄中的dll文件,點(diǎn)擊“屬性”。
將“屬性”頁(yè)中的“復(fù)制到輸出目錄”設(shè)置為“不復(fù)制”,“生成操作”設(shè)置為“嵌入的資源”。
至此,所有的文件和引用設(shè)置就結(jié)束了,下面是最后的關(guān)鍵一步:
第五步,在program.cs中添加加載文件代碼
由于文件被集成到exe中,不會(huì)被自動(dòng)加載,所以需要在這里告訴程序在加載失敗時(shí)加載集成在exe中的dll文件。
在Program.cs中添加下面高亮部分代碼,目的是在程序集解析失敗時(shí)(由于我們?cè)O(shè)置不將dll復(fù)制到根目錄,所以此處的解析失敗自然就是找不到引用的dll文件),告訴程序加載已經(jīng)集成到exe中的dll。
這里要注意設(shè)置dll文件前綴(下面示例代碼中的[resourceName]變量):集成到項(xiàng)目中的文件,在原始文件名之前會(huì)自動(dòng)加入【程序集名稱】和【文件夾名】,見(jiàn)下方用Reflector工具打開(kāi)的exe文件中的資源文件,像這樣:“[程序集名稱].[文件夾名].[原始文件名]”。
如果dll文件是復(fù)制到根目錄,那么集成后的文件名就是:“[程序集名稱].[原始文件名]”。
如果dll文件是復(fù)制到dll目錄,那么集成后的文件名就是:“[程序集名稱].dll.[原始文件名]”。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 | using System; using System.Collections.Generic; using System.Linq; using System.Windows.Forms; using System.Reflection; namespace ProxySniffer { static class Program { /// <summary> /// 應(yīng)用程序的主入口點(diǎn)。 /// </summary> [STAThread] static void Main() { //用于加載引用的dll資源 AppDomain.CurrentDomain.AssemblyResolve += (sender, args) => { String resourceName = "ProxySniffer.lib." + new AssemblyName(args.Name).Name + ".dll" ; using (var stream = Assembly.GetExecutingAssembly().GetManifestResourceStream(resourceName)) { Byte[] assemblyData = new Byte[stream.Length]; stream.Read(assemblyData, 0, assemblyData.Length); return Assembly.Load(assemblyData); } }; Application.EnableVisualStyles(); Application.SetCompatibleTextRenderingDefault( false ); Application.Run( new Form1()); } } } |
使用Reflector打開(kāi)exe文件查看內(nèi)部資源就一目了然了,這個(gè)各位可以自己確認(rèn)總結(jié)規(guī)律:
程序集名稱,還可以使用以下方式獲?。?/p>
1 | Assembly.GetExecutingAssembly().GetName().Name |
最后,重新發(fā)布程序,exe變大,同目錄下的dll文件也消失了。
聯(lián)系客服