c# winforms winapi resources

Evitar recursos de iconos duplicados en un proyecto.NET(C#)



winforms winapi (5)

Estoy usando Visual C # 2008 Express. Me gustaría usar el mismo ícono para la aplicación (es decir, el ícono que se muestra para el archivo .exe) y para el formulario principal. Desafortunadamente, VC # no parece ser muy inteligente al respecto, e insiste en duplicar los datos del ícono.

Parece que no hay una forma de seleccionar un icono "ya incrustado" para usarlo en el icono de formulario o proyecto (solo seleccionando un archivo), y usar el mismo archivo para ambos iconos solo incrusta el archivo el doble de lo que puedo ver. No es un gran problema (el espacio en el disco duro es barato ahora, ¿verdad?), Pero me molesta.

¿Alguna idea de cómo evitar esto? ¿Hay una manera de cargar programáticamente el ícono del ejecutable para usarlo cuando se construye el formulario, por ejemplo? Un par de publicaciones en el foro sobre cosas similares parecen sugerir que los recursos de .NET no usan el sistema de recursos de Windows tradicional. ¿Hay alguna forma desde el marco de acceder a los recursos de estilo antiguo? ¿O tengo que enlazar las funciones de la API de Win32 para hacerlo?


Creo que, en muchos casos, incluir un ícono duplicado es al final del día más eficiente que tratar de extraerlo del recurso no administrado, considerando que no puede usar Icon.ExtractAssociatedIcon para las rutas UNC.


Estás buscando Icon.ExtractAssociatedIcon . Llama pasando tu ejecutable:

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


Sí, es bastante molesto. Pero el problema con la respuesta propuesta de Icon.ExtractAssociatedIcon es que recuperará el ícono 32x32, y luego disminuirá la muestra a un ícono 16x16 en la ventana de formularios o en la barra de tareas, que se verá terrible a menos que su ícono 32x32 esté construido de manera muy inteligente.

La forma en que lo hago es con interoperabilidad (ponga la primera línea en el constructor de formularios):

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);

Pero esto tampoco es bueno, ya que desea el icono 32x32 para cosas como la lista de iconos Alt-Tab. Así que realmente necesitas extraer todo el ícono, que es un trabajo más grande. Tal vez haya una forma sencilla de combinar los dos iconos en uno. O puede hacer como este programa de codeproject , que extrae todo el ícono en primer lugar con una enorme pila de código.


Tienes razón, y es bastante molesto.

Debe cargar los íconos usted mismo en lugar de confiar en el código generado por el diseñador. Guarde el icono como un recurso de proyecto, luego cargue el recurso en la propiedad Icon del formulario en el constructor del formulario:

this.Icon = Properties.Resources.myIconResourceName;


Tuve un problema similar.

Tengo un icono exe que quiero reutilizar para los subformularios sin aumentar el tamaño del archivo.

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

No sé si esto es útil, pero quiero compartirlo de todos modos.