Con el reproductor de sonido me ha surgido otro problema interesante que hasta ahora había detectado pero al que nunca me había enfrentado en serio, el de los iconos y los temas oscuros.
Nunca he sido partidario de usar iconos propios en los programas, no por principios si no porque hay que incluirlos en el ejecutable (o no, pero ese es otro tema que veremos más abajo) y este empieza a tomar dimensiones exageradas y volverse pesado. Por eso siempre utilizo, cuando es posible, los iconos del stock de gambas. Apropiados, adaptados y a tu disposición en un par de clicks.
El problema surge cuando necesitas un icono que no existe en el stock. Tienes entonces que utilizar una imagen que pilles por ahí o hacer una con gambas o con gimp o con lo quieras o crearla en tiempo de ejecución mezclando iconos. Este último método me ha servido muchas veces. Si queremos un botón que abra el diálogo de búsqueda buscamos en el stock el icono de la lupa. Si queremos un botón (o el mismo) que cierre el diálogo de búsqueda mezclamos la lupa con el icono de cerrar, así:
Código:
miButton.picture=MixIcons(stock["24/find"], stock["16/cancel"]) 'nótese que el segundo Picture, que es el que queda sobre el otro es más pequeño para no taparlo del todo
Public Sub MixIcons(pic1 As Picture, pic2 As Picture) As Picture 'Une dos Pictures
With paint
.Begin(pic1)
.DrawPicture(pic2, 8, 8, pic2.W, pic2.H) 'nótese que las coordenadas del segundo icono están desplazadas de manera que aparezca en la esquina inferior izquierda.
.End
End With
Return pic1
End
Y todo queda muy bonito con un botón que muestra una lupa con una X roja delante... o no, que luego le pasas el programa a tu primo, que usa otro tema de escritorio de otra distro distinta y le aparecen unos prismáticos con una x gris delante, o vaya usted a saber qué... pero no importa porque la idea de lo que quieres expresar es clara y nadie se queja.
Sin embargo hay ocasiones en que ningun icono ni mezcla de iconos del stock nos vale y tenemos que incluir la imagen en nuestro proyecto. No problema, es fácil y queda bonito... hasta que utilizas un tema Oscuro de escritorio. Gambas, al detectar un tema oscuro, invierte los colores de todas las imágenes, de manera que si tu icono era una X negra sobre el fondo gris clarito de un tema claro aparecerá como una X blanca sobre el fondo oscuro de un tema oscuro. Eso está perfecto para los iconos del stock, pero puede volver una imagen muy bonita en una mierda ininteligible como no te andes con ojo.
No hay problema, esa inversión sólo se produce para iconos que se asignan en el ide, si los asignamos vía código no se invierten, mantienen sus colores... que pueden ser un desastre cuando el usuario utiliza un tema de escritorio distinto del nuestro (o nosotros nos hartamos y lo cambiamos). ¿Cómo nos aseguramos entonces de que la visualización de nuestro programa es siempre la adecuada? He aquí la cuestión.
La solución que he encontrado es la siguiente:
1.- Creas (copias, fusilas, pirateas o diseñas), un set de iconos adecuados para la visualización por defecto de tu programa, escritorio claro, por ejemplo, y lo (de momento) ubicas en una carpeta dentro del raiz de tu proyecto.
2.- Creas (copias, fusilas, etc.), otro set de iconos, con los mismos nombres, para la visualización en temas oscuros y la ubicas dentro de otra carpeta distinta de tu proyecto.
3.- Asignas por código los iconos adecuados a los controles según el tema sea claro u oscuro (Application.Darktheme = true)
Tanto rollo para acabar con esta tontería artesana... que no soluciona todos los problemas ni mucho menos.
Problema A: El ejecutable se te hace de un tamaño innoble.
Problema B: Si tu programa dispone de mecanismos de adaptación de colores por el usuario, o si el usuario tiene un tema de escritorio con colores personalizados o inusuales, los iconos pueden quedar horribles
Solución al problema A: Colocas las carpetas de los iconos dentro de la carpeta .Hidden de tu proyecto de manera que no se incluyan en el programa y las incluyes como archivos asociados al mismo a la hora de crear el paquete de instalación diciéndole que los copie en
user.home &/ ".local/share/icons/"& Application.name. Luego en tu programa estableces una variable según el tema de escritorio y asignas los iconos según el tema.
Código:
Private sub AsignaIconos()
dim PathIcons as string = user.home &/ ".local/share/icons" &/ Application.Name & "/"
if Application.DarkTheme then
sPathicons &= "Dark"
else
sPathicons &= "Clear"
endif
miButton1.Picture=Picture.Load(sPathicons&/"icono1.png")
miButton2.Picture=Picture.Load(sPathicons&/"icono3.png")
......
.....
'etc, 'etc.
end
Solución al problema B:
No permites al usuario cambiar los colores del programa o incluyes en tu programa un "Editor de temas" que le permita cambiarlos de manera que le sean agradables.
Con el Reproductor de sonido me he encontrado este problema y he optado por, en principio, crear dos Temas: uno similar al que presenta Audacious (Si, otra vez) con fondo negro y fuente azul, para el que he diseñado una serie de iconos, y otro que es el tema de escritorio, con iconos del Stock. De momento lo dejo así, dejando para un futuro inmediato la creación de un editor de Temas, tal como hice para el programa Soprano, que permita al usuario crear sus propias "Skins", que es como lo llamaban en el viejo Winamp.
Perdón por el ladrillo.
Saludos