Bien Tengo un mundo de dificultad para rastrear esta pérdida de memoria. Cuando ejecuto este script, no veo ningún error de memoria, pero mi objectalloc está subiendo. Instruments apunta a CGBitmapContextCreateImage> create_bitmap_data_provider> malloc, esto ocupa el 60% de mi objectalloc.iPhone - UIImage Leak, CGBitmapContextCreateImage Leak
Este código se invoca varias veces con un NSTimer.
//GET IMAGE FROM RESOURCE DIR
NSString * fileLocation = [[NSBundle mainBundle] pathForResource:imgMain ofType:@"jpg"];
NSData * imageData = [NSData dataWithContentsOfFile:fileLocation];
UIImage * blurMe = [UIImage imageWithData:imageData];
NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];
UIImage * scaledImage = [blurMe _imageScaledToSize:CGSizeMake(blurMe.size.width/dblBlurLevel, blurMe.size.width/dblBlurLevel) interpolationQuality:3.0];
UIImage * labelImage = [scaledImage _imageScaledToSize:blurMe.size interpolationQuality:3.0];
UIImage * imageCopy = [[UIImage alloc] initWithCGImage:labelImage.CGImage];
[pool drain]; // deallocates scaledImage and labelImage
imgView.image = imageCopy;
[imageCopy release];
A continuación se muestra la función de desenfoque. Creo que el problema objectalloc se encuentra aquí. Tal vez solo necesito un par de ojos frescos. Sería genial si alguien pudiera resolver esto. Lo siento, es un poco largo ... Trataré de acortarlo.
@implementation UIImage(Blur)
- (UIImage *)blurredCopy:(int)pixelRadius
{
//VARS
unsigned char *srcData, *destData, *finalData;
CGContextRef context = NULL;
CGColorSpaceRef colorSpace;
void * bitmapData;
int bitmapByteCount;
int bitmapBytesPerRow;
//IMAGE SIZE
size_t pixelsWide = CGImageGetWidth(self.CGImage);
size_t pixelsHigh = CGImageGetHeight(self.CGImage);
bitmapBytesPerRow = (pixelsWide * 4);
bitmapByteCount = (bitmapBytesPerRow * pixelsHigh);
colorSpace = CGColorSpaceCreateDeviceRGB();
if (colorSpace == NULL) { return NULL; }
bitmapData = malloc(bitmapByteCount);
if (bitmapData == NULL) { CGColorSpaceRelease(colorSpace); }
context = CGBitmapContextCreate (bitmapData,
pixelsWide,
pixelsHigh,
8,
bitmapBytesPerRow,
colorSpace,
kCGImageAlphaPremultipliedFirst);
if (context == NULL) { free (bitmapData); }
CGColorSpaceRelease(colorSpace);
free (bitmapData);
if (context == NULL) { return NULL; }
//PREPARE BLUR
size_t width = CGBitmapContextGetWidth(context);
size_t height = CGBitmapContextGetHeight(context);
size_t bpr = CGBitmapContextGetBytesPerRow(context);
size_t bpp = (CGBitmapContextGetBitsPerPixel(context)/8);
CGRect rect = {{0,0},{width,height}};
CGContextDrawImage(context, rect, self.CGImage);
// Now we can get a pointer to the image data associated with the bitmap
// context.
srcData = (unsigned char *)CGBitmapContextGetData (context);
if (srcData != NULL)
{
size_t dataSize = bpr * height;
finalData = malloc(dataSize);
destData = malloc(dataSize);
memcpy(finalData, srcData, dataSize);
memcpy(destData, srcData, dataSize);
int sums[5];
int i, x, y, k;
int gauss_sum=0;
int radius = pixelRadius * 2 + 1;
int *gauss_fact = malloc(radius * sizeof(int));
for (i = 0; i < pixelRadius; i++)
{
.....blah blah blah...
THIS IS JUST LONG CODE THE CREATES INT FIGURES
........blah blah blah......
}
if (gauss_fact) { free(gauss_fact); }
}
size_t bitmapByteCount2 = bpr * height;
//CREATE DATA PROVIDER
CGDataProviderRef dataProvider = CGDataProviderCreateWithData(NULL, srcData, bitmapByteCount2, NULL);
//CREATE IMAGE
CGImageRef cgImage = CGImageCreate(
width,
height,
CGBitmapContextGetBitsPerComponent(context),
CGBitmapContextGetBitsPerPixel(context),
CGBitmapContextGetBytesPerRow(context),
CGBitmapContextGetColorSpace(context),
CGBitmapContextGetBitmapInfo(context),
dataProvider,
NULL,
true,
kCGRenderingIntentDefault
);
//RELEASE INFORMATION
CGDataProviderRelease(dataProvider);
CGContextRelease(context);
if (destData) { free(destData); }
if (finalData) { free(finalData); }
if (srcData) { free(srcData); }
UIImage *retUIImage = [UIImage imageWithCGImage:cgImage];
CGImageRelease(cgImage);
return retUIImage;
}
La única cosa que puedo pensar en que se mantiene la ObjectAlloc está presente UIImage * retUIImage = [UIImage imageWithCGImage: CGImage]; ... pero ¿cómo hacerlo Libero que después se ha vuelto? Espero que alguien pueda ayudar por favor.
tengo ni idea de si está relacionado a la fuga, pero no debería estar llamando 'libre (bitmapData)' antes de que haya soltado el contexto. Los bloques de memoria asignados con 'malloc()' no tienen contadores de retención, por lo que si llama a 'free()' se libera inmediatamente, incluso si el CGContext lo está usando. – benzado
¿Está dirigido a iPhone OS 3.1 o superior? Puede ser un error en el marco 3.0 o anterior. Si está en 3.1, no necesita asignar bitmapData para 'CGBitmapContextCreate'. También '_imageScaledToSize' es una llamada no documentada. Por favor no lo uses Algunas personas pueden no estar dispuestas a responder su pregunta si está utilizando llamadas no documentadas. – lucius
hey bbullis21 ¿su código de desenfoque funciona bien en el dispositivo? – Leena