iPad 3 renderInContext slow - Bad rendering performance
Asked Answered
O

2

6

I am trying to get an image out of a view where a user can paint on, or add some other views. With the iPad1 & 2 everything is working fine so far. But on the iPad3 it runs like a dog. I am just using the layers renderInContext method.

if ([[UIScreen mainScreen] respondsToSelector:@selector(scale)])
    UIGraphicsBeginImageContextWithOptions(self.viewDrawableViewContainer.frame.size, NO, [UIScreen mainScreen].scale);
else
    UIGraphicsBeginImageContext(self.viewDrawableViewContainer.frame.size);
[self.viewDrawableViewContainer.layer renderInContext:UIGraphicsGetCurrentContext()];
UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();   

I know this is probably caused by the cpu which is equal to the ipad2 one, but it takes about 1 second. The more the user paints or adds, the longer it will take to render. Sometimes up to 5 seconds which is really inacceptable. So are there any options to improve performance? Any chance to maybe set a smaller rendering quality - I don't need a rendering in the highest retina resolution...

I would appreciate any help! Thanks in advance

Ouellette answered 11/7, 2012 at 14:44 Comment(4)
Can you anticipate what views will be drawn? If so you could do the drawing in the background and cache the results, which wouldn't freeze the device.Yurik
Okay thanks for the hint, I could create an image in the background but the problem is, that the user may write some text and tap on go. Then I would have to do the drawing immediately after the user interaction because the view will be closed after tapping on go. But thanks, maybe I could render whilst the closing animation is performing. I'll give it a try... So there are no other ways to improve rendering performance?Ouellette
Unfortunetly no, churning out 4 times on essentially the same CPU as many pixels simply kills performance. Masking it with animations is a great way to solve the issue, and is how Apple does it. If you are allowing the user to draw to a view, what are you drawing to? Is there no UIImage backing the view that you can pull out immediately rather than rendering the view to a context?Yurik
The user can draw everything he likes. It's like a finger-pencil where you can draw everything you want. Further he is able to add notes where he can input some text via the keyboard...Ouellette
J
9

You can increase speed by rendering at lower resolution. Use a UIGraphicsBeginImageContextWithOptions scale factor less than 1.0, e.g. 0.5.

Also, if you don't need alpha you might get a small speed boost by passing YES for the opaque flag. I haven't timed the difference myself.

Jaehne answered 18/8, 2012 at 22:58 Comment(1)
tried this. I used NSDate *d1 = [NSDate date]; ... NSDate *d2 = [NSDate date]; [d2 timeIntervalSinceDate: d1]; to measure how long it takes, and no difference. iPad 3 is just far slower then iPad2 (~0.3sec to ~1.7sec)Starry
O
16

You can also increase rendering speed by modifying the interpolation quality in your context before you call render in context. I was able to get much higher speed screenshot-ting with this change than by changing the scale factor.

Of course you can use both and you don't have to set the quality to None, Low still was an improvement for me.

CGContextSetInterpolationQuality(ctx, kCGInterpolationNone);

Also, for the scale factor as mentioned in the previous answer make sure your new scale factor is a multiple of the original i.e. if the screen scale is 1.0 you should do something like .5 and not .8. Using .8 will cause the render to have calculate more information (because it isn't an even scale) and thus make it slower than using 1.0 because.

Of course this won't be a good solution for everyone.

Omnidirectional answered 9/5, 2013 at 2:39 Comment(1)
CGContextSetInterpolationQuality makes wonderful things! In my case I'm rendering layer of UICollectionView with images in cells - changing high interpolation quality to medium/low rises frame rate when scrolling very significantly.Ardrey
J
9

You can increase speed by rendering at lower resolution. Use a UIGraphicsBeginImageContextWithOptions scale factor less than 1.0, e.g. 0.5.

Also, if you don't need alpha you might get a small speed boost by passing YES for the opaque flag. I haven't timed the difference myself.

Jaehne answered 18/8, 2012 at 22:58 Comment(1)
tried this. I used NSDate *d1 = [NSDate date]; ... NSDate *d2 = [NSDate date]; [d2 timeIntervalSinceDate: d1]; to measure how long it takes, and no difference. iPad 3 is just far slower then iPad2 (~0.3sec to ~1.7sec)Starry

© 2022 - 2024 — McMap. All rights reserved.