2011-07-10 15 views
135

Estoy tratando de dibujar algunas imágenes en miniatura a un tamaño fijo (100x100) con UIImageView. Establecí el tamaño del fotograma de mi vista de imagen en 100x100 y configuré el contentMode en UIViewContentModeScaleAspectFill.UIViewContentModeScaleAspectFill sin recorte

Según entiendo, esto debería hacer que la imagen se dibuje en el tamaño que configuré, y la imagen llenará el área de la imagen y recortará cualquier parte de la imagen que quede fuera del tamaño que configuré para la imagen ver. Sin embargo, la imagen aún se dibuja más grande o más pequeña que el tamaño de 100x100 que configuré para ella.

Si configuro contentMode en UIviewContentModeScaleToFill, la imagen se dibujará exactamente a 100x100, pero está distorsionada para ajustarse a esas dimensiones. ¿Alguna idea de por qué el relleno de aspecto no está recortando como se esperaba?

Aquí está mi código:

_photoView = [[UIImageView alloc] initWithImage:photoImage]; 
_photoView.contentMode = UIViewContentModeScaleAspectFill; 
[self addSubview:_photoView]; 

CGRect photoFrame = _photoView.frame; 
photoFrame.size = CGSizeMake(100, 100); 
_photoView.frame = photoFrame; 

para ilustrar mejor, aquí está una captura de pantalla de lo que estoy viendo. Los cuadrados verdes son el UIView que contiene el UIImageView con el que estoy trabajando. Establecí el color de fondo en verde y el marco de la vista en 100x100. Como prueba, el UIImageViews tiene un tamaño de 50x50. Como puede ver, al usar el ...AspectFill, las imágenes no tienen un tamaño de 50x50, y en algunos casos están desfasadas de donde me gustaría. Al usar ...ScaleToFill, tienen el tamaño correcto, pero la imagen está distorsionada.

Screenshot illustrating problem

Respuesta

337

Se puede tratar el establecimiento de clip para límites

[_photoview setClipsToBounds:YES]; 

o directamente en el guión gráfico/Xib si puedes:

enter image description here

+10

Eso fue todo - gracias. (Agregué la captura de pantalla anterior para mostrar mejor lo que estaba viendo, más como un ejemplo si alguien más se encuentra con este problema). –

+3

En InterfaceBuilder, renombrado (inútilmente) a "Clips de subvistas" (NB: en este caso, no lo hace) t clib "subviews", el nombre es incorrecto: clip de SELF AND subviews) – Adam

+3

Al marcar la opción 'Clip Subviews' en el archivo NIB, se hace lo mismo. Aclamaciones. – codeburn

8

Si desea ampliar sus conocimientos hay un artículo realmente bueno sobre cómo iOS UIView stack is rendered. También hay un artículo más detallado sobre el whole drawing pipeline.

En resumen:

  1. Rasterización - se rasterizadas Todo el contenido de la vista (dibujado o un tampón de píxeles fuera de la pantalla) en el espacio de coordenadas de los límites de la vista. Esto podría ser datos de imágenes o dibujos personalizados (es decir, drawRect:), pero subvista de contenido. Esta rasterización tiene en cuenta la propiedad contentMode.

    Se descarta cualquier cosa fuera de los límites de una vista.

  2. Composición - Los resultados se componen (dibujados unos encima de otros) desde la subvista hasta las supervistas. Esto usa la propiedad de marco de la subvista.

    Si la propiedad es clipsToBoundsYES en el supervista entonces se descarta subvista contenido fuera de sus límites.

+0

Esto, gracias por esto! Finalmente una explicación: D –

0

Mis subviewes se cambio de tamaño y me di cuenta que era porque el conjunto tenía xib diseño automático: enter image description here

2

tenían el mismo problema y se resolvió, marcando "Clip subvistas".

La imagen se mostraba correctamente para todas las vistas (3.5,4,4.7,5.5, ipad) en la vista previa del guión gráfico pero no en el simulador.

Después de marcar "Subvistas de clips" se resolvió el problema. :)

1

Comprobación de "subvistas de clips" directamente en el Storyboard/Xib también funcionó para mí. enter image description here

0

Si todo falla,

hacer los clips a límites en viewDidLayoutSubviews Método.

Ejemplo:

override func viewDidLayoutSubviews() { 

    imageProfile.layer.cornerRadius = imageProfile.bounds.size.width/2 
    imageProfile.clipsToBounds = true 
    imageProfile.layer.masksToBounds = true 
}