Question

I want to take screen shot of window and use that image as background view for new view controller. My problem is, that image is some what blur in retina display because the image should be 640X1136. But the following code returns image with size of only 320X568.

Note: If I use the apple's private API UIGetScreenImage() it returns the image in size 640X1136.

   -(UIImage*)getScreenShot:(CALayer*)layer 
    {
            UIGraphicsBeginImageContextWithOptions(layer.frame.size, NO, 0.0);
            [layer renderInContext:UIGraphicsGetCurrentContext()];
            UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
            UIGraphicsEndImageContext();
            return image;
    }

       [self getScreenShot:self.window.layer];

Is any way to get the screen shot image in size 640X1136 with out using apple's private API?

Was it helpful?

Solution

-(UIImage*)getScreenShot:(CALayer*)layer
{
    CGFloat scale = 1.0;
#if __IPHONE_OS_VERSION_MAX_ALLOWED >= 40000
    if ([[UIScreen mainScreen] respondsToSelector:@selector(scale)]){
        scale = [[UIScreen mainScreen] scale];
    }
#endif
    UIGraphicsBeginImageContextWithOptions(CGSizeMake(layer.frame.size.width*scale, layer.frame.size.height*scale), NO, 0.0);
    [layer renderInContext:UIGraphicsGetCurrentContext()];
    UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
    UIGraphicsEndImageContext();
    return image;
}

OTHER TIPS

If you're on iOS 7 you can use the new methods which are designed for taking screen shots, drawViewHierarchyInRect:afterScreenUpdates: (check this documentation link for info on the BOOL parameter for the drawViewHierarchyInRect:afterScreenUpdates: method).
If not you can use the old method renderInContext:. If you're only targeting iOS 7, you can remove the below if statement.

UIVIew *window = [UIApplication sharedApplication].delegate.window;
CGRect rect = window.bounds;
UIGraphicsBeginImageContextWithOptions(rect.size, NO, 0);
if ([window respondsToSelector:@selector(drawViewHierarchyInRect:afterScreenUpdates:)]) {
    [window drawViewHierarchyInRect:rect afterScreenUpdates:NO];
} else {
    [window.layer renderInContext:UIGraphicsGetCurrentContext()];
}
UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
// image now contains a screen shot

The scale parameter ensure the screen shot is the correct resolution, passing in 0 to UIGraphicsBeginImageContextWithOptions means it will use the [UIScreen mainScreen].scale value. The UIImage might report it's size as non-retina, but its scale will be correct as 2.0, and this value is used to calculate the pixel image size as per the docs:

If you multiply the logical size of the image (stored in the size property) by the value in this property, you get the dimensions of the image in pixels.

Try this one,

  UIGraphicsBeginImageContext(self.bounds.size);    

or

  UIGraphicsBeginImageContext(CGSizeMake(640X1136));
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top