2009-02-27 35 views
19

我正在使用Visual C#2008 Express。我想爲應用程序使用相同的圖標(即爲.exe顯示的圖標)以及主窗體。不幸的是,VC#似乎並不聰明,堅持複製圖標數據。在.NET(C#)項目中避免重複的圖標資源

似乎沒有選擇用於表單或項目圖標(僅選擇文件)的「已經嵌入」圖標的方法,並且對兩個圖標使用相同的文件只是將文件嵌入兩次盡我所能看到。這不是什麼大問題(現在硬盤空間很便宜,對吧?),但它讓我感到不安。

任何想法如何避免這種情況?有沒有一種方法來編程加載可執行文件的圖標,以便在構建表單時使用,比如說?一些關於類似事情的論壇帖子似乎暗示,.NET資源不會使用正常的舊Windows資源系統 - 在獲得舊式資源的框架內有沒有辦法?或者我必須綁定Win32 API函數才能做到這一點?

+0

爲什麼不使用繼承?在一個自定義Form類中定義圖標並在任何地方使用它。 – 2010-07-31 14:01:55

+0

我記得我的Delphi編程時間... self.Icon = Application.Icon; :P ...在.NET中太難了:D – Learner 2012-07-26 20:31:50

+0

[任何從資源中使用圖標的簡單方法?](http:// stackoverflow。com/questions/5656809/any-easy-way-to-use-icons-from-resources) – KyleMit 2015-02-12 20:46:56

回答

6

是的,這很煩人。但是Icon.ExtractAssociatedIcon的建議答案的問題是,它將檢索32x32圖標,然後在窗體窗口或任務欄上縮減爲16x16圖標,除非您的32x32圖標構造得非常巧妙,否則這看起來很糟糕。

我做它的方式是與互操作(把第一行中的窗體構造函數):

this.Icon = ExtractSmallIconFromLibrary(Application.ExecutablePath); 
... 

public static Icon ExtractSmallIconFromLibrary(string file) { 
    IntPtr[] reficon = new IntPtr[1]; 
    int nextracted = ExtractIconEx(file, 0, null, reficon, 1); 
    if (nextracted < 1) 
     return null; 
    Icon unmanaged_icon = Icon.FromHandle(reficon[0]); 
    Icon icon = (Icon)unmanaged_icon.Clone(); 
    DestroyIcon(unmanaged_icon.Handle); 
    return icon; 
} 

[DllImport("Shell32", CharSet = CharSet.Auto)] 
extern static int ExtractIconEx(
    [MarshalAs(UnmanagedType.LPTStr)] 
    string lpszFile, 
    int nIconIndex, 
    IntPtr[] phIconLarge, 
    IntPtr[] phIconSmall, 
    int nIcons 
    ); 

[DllImport("user32.dll", CharSet = CharSet.Auto)] 
extern static bool DestroyIcon(IntPtr handle); 

但這並不是很大,或者說,既然你做 32×32的圖標像Alt-Tab圖標列表。所以你真的需要提取整個圖標,這是一個更大的工作。也許有一種直接的方法可以將兩個圖標組合成一個。或者你可以像這樣做codeproject程序,它首先用一大堆代碼提取整個圖標。

14

你說得對,而且很煩人。

您必須自己加載圖標,而不是依賴設計器生成的代碼。保存圖標爲一個項目的資源,然後加載資源到窗體的Icon財產形式的構造函數:

this.Icon = Properties.Resources.myIconResourceName; 
10

您正在尋找Icon.ExtractAssociatedIcon。呼叫通過您的可執行文件:

var icon = Icon.ExtractAssociatedIcon(Assembly.GetExecutingAssembly().Location); 
1

我有一個類似的問題。

我有和exe圖標我想重複使用子窗體而不增加文件大小。

//From MyApp 
MySubForm msf = new MySubForm(); 
msf.Icon = this.Icon; 
msf.Show(); 

我不知道這是否有用,但我想分享它。

3

我認爲在許多情況下,包括重複圖標在一天結束時比試圖從非託管資源中提取效率更高效 - 考慮到您無法將Icon.ExtractAssociatedIcon用於UNC路徑。