.net - source - Mis imágenes son borrosas ¿Por qué no funciona SnapsToDevicePixels de WPF?
image source wpf xaml (12)
Estoy usando algunas imágenes en mi aplicación de WPF.
XAML:
<Image Name="ImageOrderedList"
Source="images/OrderedList.png"
ToolTip="Ordered List"
Margin="0,0,5,5"
Width="20"
Height="20"
SnapsToDevicePixels="True"
MouseUp="Image_MouseUp"
MouseEnter="Image_MouseEnter"
MouseLeave="Image_MouseLeave" />
Pero, parecen borrosos:
Aquí hay una comparación de lado a lado ampliada. Un original está a la izquierda:
¿Por qué la línea SnapsToDevicePixels="True"
previene este problema?
+1 para Zack Peterson
Estoy usando .Net 3.5 sp1 y parece la solución más simple para una gran cantidad de imágenes borrosas. No es gran cosa especificar RenderOptions en el lugar, pero para los componentes de terceros, tiene sentido un estilo en los recursos de la aplicación:
<Style TargetType="{x:Type Image}">
<Setter
Property="RenderOptions.BitmapScalingMode"
Value="NearestNeighbor" />
</Style>
Funcionó bien cuando AvalonDock comenzó a mostrar iconos borrosos.
Asegúrese de guardar la imagen en el mismo DPI en el que está trabajando su aplicación WPF, algunos formatos de imagen tienen esta información almacenada como metadatos. No sé si esto resuelve el problema, pero he tenido algunos problemas debido a esto, donde las imágenes cambiaron de tamaño al 100%, se hicieron más grandes o más pequeñas de lo esperado.
Podría ser algo similar.
Creo que esto es un error (o al menos lo fue). Consulte esta página de intercambio de correo electrónico de soporte de Microsoft para obtener algunas ideas para solucionarlo.
En lugar de utilizar SnapsToDevicePixels
, en su lugar utilicé RenderOptions.BitmapScalingMode
y ahora son agradables y nítidas.
XAML:
<Image Name="ImageOrderedList"
Source="images/OrderedList.png"
ToolTip="Ordered List"
Margin="0,0,5,5"
Width="20"
Height="20"
RenderOptions.BitmapScalingMode="NearestNeighbor"
MouseUp="Image_MouseUp"
MouseEnter="Image_MouseEnter"
MouseLeave="Image_MouseLeave" />
Así es como se ve ahora:
Imágenes nítidas de WPF http://img13.imageshack.us/img13/9926/crispwpfimages.gif
Es posible que desee considerar probar una nueva propiedad disponible ahora en WPF4 . Deje RenderOptions.BitmapScalingMode
en RenderOptions.BitmapScalingMode
o simplemente no lo declare.
NearestNeighbor funcionó para mí, excepto que dio lugar a mapas de bits irregulares al hacer zoom en la aplicación. Tampoco pareció solucionar los fallos técnicos en los que los iconos se dimensionaban de maneras extrañas.
En su elemento raíz (es decir, su ventana principal) agregue esta propiedad: UseLayoutRounding="True"
.
Una propiedad que anteriormente solo estaba disponible en Silverlight ahora ha solucionado todos los problemas de tamaño de Bitmap. :)
He descubierto que ninguna combinación de las soluciones sugeridas podría curar mi problema de imagen borrosa aparentemente aleatorio. Me gusta que muchos otros no puedan actualizar a .net 4 para usar la propiedad UseLayoutRendering
.
Lo que he encontrado para trabajar:
- Asegúrese de que las dimensiones de su imagen [original] sean múltiplos de 2. Esto parece prevenir algunos de los problemas de escalado de la imagen.
- A veces también he encontrado que ajustar los márgenes en las imágenes por un píxel o 2 puede evitar el problema.
He encontrado que RenderOptions.BitmapScalingMode = "NearestNeighbor" no funciona para mí. Estoy usando Windows XP x32 con DirectX 9.0c. Como el procesamiento real de WPF se realiza con DirectX, esto podría tener un efecto. Tengo anti-aliasing activado para XP con las siguientes entradas de registro:
[HKEY_LOCAL_MACHINE / SOFTWARE / Microsoft / Avalon.Graphics] "MaxMultisampleType" = dword: 00000004 "EnableDebugControl" = dword: 00000001
Sin embargo, apagar aa con estos ajustes no tiene efecto en las imágenes. Creo que esto solo afecta a 3D Viewports.
Finalmente, descubrí que la borrosidad se produce con el texto de TextBlocks y con las imágenes. Y la borrosidad solo ocurre en algunos bloques de texto e imágenes, no en todos.
Intenté usar RenderOptions.BitmapScalingMode = HighQuality, parece que causa algunos problemas en Windows 8.1, así que lo que hice fue ejecutarlos a través de la herramienta llamada PngOut.exe
http://advsys.net/ken/utils.htm
Lo cual reduce el encabezado del png, y también reduce el tamaño, pero sin cambiar la calidad de la imagen.
¡Y ahora todas mis imágenes son perfectas! :-)
Lo primero que pensé, al leer la pregunta, fue que estabas explotando demasiado la imagen, pero ese no parece ser el caso al mirar la imagen que tienes de la aplicación.
El segundo pensamiento es la paleta de colores, pero con el negro como uno de los colores que no se procesa correctamente, esto no es tan probable.
Si puedes descartar por completo los dos anteriores, actualmente estoy perplejo.
Como experimento, puedes probar otros formatos de gráficos, pero PNG debería estar bien. Tendré que pensarlo un poco más para llegar a una mejor respuesta.
RenderOptions.BitmapScalingMode = "NearestNeighbor" funciona bien la mayor parte del tiempo. Sin embargo, ocasionalmente obtendrá fallas gráficas (en mi caso, 4 de 5 imágenes aparecieron bien, pero el quinto tenía una ligera distorsión en el borde derecho). Lo arreglé aumentando el margen derecho del control de Imagen en 1.
Si eso aún no lo soluciona, intente con el control de clase Bitmap que menciona EugeneZ. Es un reemplazo para el control de imagen y hasta ahora me ha funcionado bastante bien. Ver blogs.msdn.com/dwayneneed/archive/2007/10/05/…
Usar UseLayoutRounding="True"
en la ventana raíz funciona en muchos casos, pero encontré un problema cuando usé el control WPF Ribbon . Mi aplicación se basa en pestañas contextuales que aparecen de acuerdo con lo que está haciendo el usuario y cuando establezco UseLayoutRounding
en True
, la pestaña contextual no aparece y tampoco la imagen de RibbonButton. Además, la aplicación se congela durante muchos segundos y el ventilador de la CPU comienza a cantar.
El uso de RenderOptions.BitmapScalingMode="NearestNeighbor"
en mi imagen corrigió los problemas de representación de la imagen (imagen borrosa y recortada) y es totalmente compatible con el uso de Tabs Contextual Tabs.
Use UseLayoutRounding = True en el elemento superior de su aplicación