Quartz PDF API Cause Memory Crashes

I am having problems using the Quartz PDF API for iOS. At the moment I am building with SDK 4.0 GM Seed and it works on my iPad 3.2 (I tried using SDK 3.2 with the same results).

All the code I use is based on the standard Apple Quartz documentation and from various sources around the world. Therefore, I cannot imagine that I am doing something completely different or wrong.

The code works fine in the Simulator (all versions, this is a universal app) and even when using the Simulate Memory feature. I used the Leaks tool and there are no leaks it finds. Build and Analyze doesn't find anything either. There is no bad or low memory log left in my library.

All of this makes me think that the device is running out of memory. This happens after you've skipped 50 pdf pages, with about 35% having some kind of image (on some page). This is not a glitch on any particular page. The PDF I download is about 75 pages and 3.5 MB.

I've looked at similar issues on this site and around the internet, and have applied some guidelines in the code below. Now I post a link to the pdf document at every turn of the page and I no longer save / release the link to the page. I also made it easy to exchange images using CGImages with just the UIGraphicsGetImageFromCurrentImageContext function. I've tried various implementations for switching images, including completely replacing pdfImgView with a new dedicated temporary instance (using [[UIImageView alloc] iniWithImage:UIGraphicsGetImageFromCurrentImageContext()]

), using an installer for pdfImgView, and freeing temp. All variants pass leak and analyzer tests, but still exhibit the same failure behavior.

So, before moving away from PDFs entirely, is there anything I should try or something I'm missing?

View the controller code that is called in the interface handlers for paging and on first load:

[self drawPage];

// ...animation code...simple CATransition animation...crashes with or without

// scrollView is a UIScrollView that is a subview of self.view
[scrollView.layer addAnimation:transition forKey:nil];
// pdfImgView is a UIImageView that is a subview of scrollView
pdfImgView.image = UIGraphicsGetImageFromCurrentImageContext();

      

drawPage method used to customize and draw the PDF page in context:

[CFURLRef pdfURL = CFBundleCopyResourceURL(CFBundleGetMainBundle(), CFSTR("BME_interior.pdf"), NULL, NULL);
pdfRef = CGPDFDocumentCreateWithURL((CFURLRef)pdfURL); // instance variable, not a property
CFRelease(pdfURL);
CGPDFPageRef page = CGPDFDocumentGetPage(pdfRef, currentPage);

CGRect box = CGPDFPageGetBoxRect(page, kCGPDFMediaBox);
// ...setting scale and imageHeight, both floats...

if (UIGraphicsBeginImageContextWithOptions != NULL) {
    UIGraphicsBeginImageContextWithOptions(CGSizeMake(self.view.frame.size.width, imageHeight), NO, 0.0);
} else {
    UIGraphicsBeginImageContext(CGSizeMake(self.view.frame.size.width, imageHeight));
}
CGContextRef context = UIGraphicsGetCurrentContext();
NSLog(@"page is %d, context is %d, pdf doc is %d, pdf page is %d", currentPage, context, pdfRef, page); // all prints properly

// ...setting up scrollView for new page, using same instance...

CGContextTranslateCTM(context, (self.view.frame.size.width-(box.size.width*scale))/2.0f, imageHeight);
CGContextScaleCTM(context, scale, -1.0*scale);

CGContextSaveGState(context);
CGContextDrawPDFPage(context, page);
CGContextRestoreGState(context);

CGPDFDocumentRelease(pdfRef);
pdfRef = NULL;

      

+2


source to share


2 answers


Aha! I fixed the bugs by adding UIGraphicsEndImageContext();

before starting a new image context. I don't even get memory warnings now ...



+1


source


Call

CGContextSetInterpolationQuality(context, kCGInterpolationHigh); 
CGContextSetRenderingIntent(context, kCGRenderingIntentDefault);

      



before CGContextDrawPDFPage

solved a similar problem.

Credits go to this Johannes answer: CGContextDrawPDFPage takes up most of the memory

0


source







All Articles