2010-10-12 31 views
8

Estoy tratando de recortar una región de UIView, en un UIImage para su reutilización posterior.UIImage de una región de UIView

he trabajado a cabo este código de algunos fragmentos:

CGRect _frameIWant = CGRectMake(100, 100, 100, 100); 

UIGraphicsBeginImageContext(view.frame.size); 
[view.layer renderInContext:UIGraphicsGetCurrentContext()]; 

//STEP A: GET AN IMAGE FOR THE FULL FRAME 
UIImage *_fullFrame = UIGraphicsGetImageFromCurrentImageContext(); 
UIGraphicsEndImageContext(); 

//STEP B: CLIP THE IMAGE 
CGImageRef _regionImage = CGImageCreateWithImageInRect([_fullFrame CGImage], _frameIWant); 
UIImage *_finalImage = [UIImage imageWithCGImage:_regionImage]; 
CGImageRelease(_regionImage); 

'vista' es el UIView la que estoy recorte y _finalImage es el UIImage que quiero.

El código funciona sin problemas, sin embargo es un poco lento. Creo que se puede obtener algo de rendimiento tomando solo la parte de la pantalla directamente en el Paso A.

Estoy buscando algo como renderInContext: withRect: o jeje.

Aún no han encontrado nada :(, por favor, ayúdame si usted sabe de alguna alternativa

+0

podría volver a formatear? difícil de leer – Rudiger

Respuesta

6

Este método clips una región de la vista utilizando menos memoria y tiempo de CPU:

-(UIImage*)clippedImageForRect:(CGRect)clipRect inView:(UIView*)view 
{ 
    UIGraphicsBeginImageContextWithOptions(clipRect.size, YES, 1.f); 
    CGContextRef ctx = UIGraphicsGetCurrentContext(); 
    CGContextTranslateCTM(ctx, -clipRect.origin.x, -clipRect.origin.y); 
    [view.layer renderInContext:ctx]; 
    UIImage *img = UIGraphicsGetImageFromCurrentImageContext(); 
    UIGraphicsEndImageContext(); 
    return img; 
} 
0

Usted podría tratar de rasterización de la primera UIView:.

view.layer.shouldRasterize = YES; 

que tienen un éxito limitado, pero el uso de este está diciendo que estoy haciendo lo mismo que usted (más la línea anterior) y funciona bien. ¿En qué contexto está haciendo esto? Puede ser su problema de rendimiento.

EDITAR: También podría intentar usar los límites de la vista en lugar del marco de la vista. no son siempre lo mismo.

+0

El contexto 'principal', creo. Creo un nuevo contexto en el hilo principal. : S – almosnow

0

SWIFT versión de @ phix23 solución. añadiendo escala

func clippedImageForRect(clipRect: CGRect, inView view: UIView) -> UIImage { 
    UIGraphicsBeginImageContextWithOptions(clipRect.size, true, UIScreen.mainScreen().scale); 
    let ctx = UIGraphicsGetCurrentContext(); 
    CGContextTranslateCTM(ctx, -clipRect.origin.x, -clipRect.origin.y); 
    view.layer.renderInContext(ctx!) 
    let img = UIGraphicsGetImageFromCurrentImageContext(); 
    UIGraphicsEndImageContext(); 
    return img 
} 
Cuestiones relacionadas