2011-10-05 9 views
6

He mirado alrededor y parece que la gente dice que puede volver a procesar los datos después de acercar el zoom ahora que conoce el factor de escala para UIScrollView. También he visto algunas publicaciones sobre cómo hacer que tu capa sea un CATiledLayer y establecer los levelsOfDetailBias y levelsOfDetail.Reproducción de contenido después de ampliar para UIScrollView

Lo que tengo es una UIScrollView, y en ella, una ResultsView que es una subclase de UIView:

- (id)initWithFrame:(CGRect)frame 
{ 
    self = [super initWithFrame:frame]; 
    if (self) { 
     CATiledLayer *tiledLayer = (CATiledLayer *)self.layer; 
     tiledLayer.levelsOfDetailBias = 3; 
     tiledLayer.levelsOfDetail = 3; 
     self.opaque = YES; 
    } 
    return self; 
} 

/* 
// Only override drawRect: if you perform custom drawing. 
// An empty implementation adversely affects performance during animation. 
- (void)drawRect:(CGRect)rect 
{ 
    // Drawing code 
} 
*/ 

+ (Class)layerClass { 
    return [CATiledLayer class]; 
} 

En mi clase en la que tengo el UIScrollView y ResultsView, que hago:

- (UIView *)viewForZoomingInScrollView:(UIScrollView *)scrollView { 
    return self.ResultsView; 
} 

¿Es esto suficiente para tener el texto reintegrado (nítido)? O tengo que implementar algo en

- (void)drawLayer:(CALayer *)layer inContext:(CGContextRef)ctx { 
} 

Si es así, no estoy seguro de cómo hacerlo. En mi clase con UIScrollView y ResultsView, en ResultsView (en el XIB), solo tengo un par de UILabels y UIViews (UIViews usado para encabezados/pies de página para la vista). Así que no sé cómo volver a dibujarlos desde ResultsView. Aunque ResultsView tiene los UILabels y UIViews como elementos secundarios en el XIB, no estoy seguro de cómo los volvería a dibujar de la clase ResultsView, y lo que tendría que hacer de todos modos.

¿O es este el enfoque equivocado? ¿Solo necesito cambiar el tamaño de UILabel y UIView por el factor de escala en el método scrollViewDidEndZooming: delegate? TIA

Respuesta

18

Creo que está tomando un enfoque equivocado. Si su vista consiste en UILabels y UIViews que no hacen ningún dibujo personalizado, no me meteré con el uso de una vista respaldada por CATiledLayer. En su lugar poner en práctica el scrollViewDidEndZooming: withView: atScale: método delegado y hacer algo como esto:

- (void)scrollViewDidEndZooming:(UIScrollView *)scrollView withView:(UIView *)view atScale:(float)scale { 
    scale *= [[[self.scrollView window] screen] scale]; 
    [view setContentScaleFactor:scale]; 
    for (UIView *subview in view.subviews) { 
     [subview setContentScaleFactor:scale]; 
    } 
} 
+0

gracias. Funcionó muy bien. No creo que hubiera encontrado este tipo de respuesta yo mismo. ¿Puedes explicar por qué necesitas la escala de la primera línea * = ... ¿Sería diferente el valor que devuelve la ventana/pantalla/escala para los dispositivos? Gracias. –

+0

Sí, eso hace que la pantalla Retina sea compatible. En los iPhones/iPod toques iPad y no Retina, la escala de la pantalla de la ventana es 1.0 por lo que no tiene ningún efecto. En las pantallas Retina, es 2.0, por lo que ajusta correctamente la escala de esas pantallas. – afarnham

+0

Un enfoque incluso más limpio podría ser hacer que la vista esté haciendo zoom en una subclase de UIView (si no lo está) y crear un método que indique a cada subvista que actualice su contenido directamente en lugar de recorrer todas las subvistas. Te daría un control más detallado si tienes algunas subvistas que hacen un dibujo personalizado, ya que también querrás llamar a setNeedsDisplay en esas. – afarnham

4

que tienen algo pequeño para añadir a la solución aceptada que me causó unos minutos de dolor en caso de que alguien más se encuentra con el la misma cosa.

Al pasar por todas las subimágenes en la vista que está acercando y al llamar a setContentScaleFactor no se tiene en cuenta si alguna de las subvistas mismas tiene subvistas. Si usted tiene una configuración más complicada de esa manera, hacer seguro también de bucle a través de los subvistas de esos puntos de vista de contenedores y llame

[subview setContentScaleFactor:scale]; 

en cada uno. Hice un método que puedo invocar para llamar a setContentScaleFactor en todas las subvistas de una vista determinada y llamar eso para cada "vista de contenedor" en la pantalla.

- (void)scrollViewDidEndZooming:(UIScrollView *)scrollView withView:(UIView *)view atScale:(float)scale 
{ 
    scale *= [[[self.scrollView window] screen] scale]; 
    [view setContentScaleFactor:scale]; 
    for (UIView *subview in view.subviews) 
    { 
     [self setContentSizeForView:subview andScore:scale]; 

     //Loop through all the subviews inside the subview 
     for(UIView *subSubview in subview.subviews) 
     { 
      [self setContentSizeForView:subSubview andScale:scale]; 
     } 
    } 
} 

- (void) setContentSizeForView:(UIView*) view andScale:(float)scale 
{ 
    [view setContentScaleFactor:scale]; 
} 
+0

¿Tengo que hacer otras llamadas?Cuando configuro el contentScaleFactor de mi subclase UIView (la vista se usa para dibujar y para ampliar) igualar el valor de la escala (del método delegado UIScrollView), mi aplicación se ralentiza mucho y se cuelga. – Sebastian

+0

Sí, también noté que se trata de una operación muy lenta cuando hay muchas subvistas. Finalmente abandoné el contenido de nitidez mientras hacía zoom para una jerarquía de vista/subvista complicada, ya que era demasiado lenta. – DiscDev

+0

¿por qué no pegas en el método que hiciste? –

Cuestiones relacionadas