I want to take screenshot of only image in imageview. I have tried following code but it will take screenshot of imageview .
CGRect grabRect = CGRectMake(self.vwBackup.frame.origin.x,self.vwBackup.frame.origin.y,self.vwBackup.frame.size.width,self.vwBackup.frame.size.height);
if ([[UIScreen mainScreen] respondsToSelector:#selector(scale)]) {
UIGraphicsBeginImageContextWithOptions(grabRect.size, NO, [UIScreen mainScreen].scale);
} else {
UIGraphicsBeginImageContext(grabRect.size);
}
CGContextRef ctx = UIGraphicsGetCurrentContext();
CGContextTranslateCTM(ctx, -grabRect.origin.x, -grabRect.origin.y);
[self.view.layer renderInContext:ctx];
UIImage *viewImage = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
// UIImageWriteToSavedPhotosAlbum(viewImage, nil, nil, nil);
self.ImgEditableView.image=viewImage;
Here i have attached image of taken screenshot with above code:
if ([[UIScreen mainScreen] respondsToSelector:#selector(scale)])
UIGraphicsBeginImageContextWithOptions(self.displayImageView.bounds.size, NO, [UIScreen mainScreen].scale);
else
UIGraphicsBeginImageContext(self.displayImageView.bounds.size);
[self.displayImageView.layer renderInContext:UIGraphicsGetCurrentContext()];
UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
NSData * imgData = UIImagePNGRepresentation(image);
if(imgData)
{
[imgData writeToFile:#"screenshot.png" atomically:YES];
}
else
NSLog(#"error while taking screenshot");
Related
I am using following code to capture screen. Before it was working fine but now its retuning nil image.I am using iPhone 5,5c and 5s.
+ (UIImage *)screenshot
{
CGSize imageSize = CGSizeZero;
imageSize = [UIScreen mainScreen].bounds.size;
UIGraphicsBeginImageContextWithOptions(imageSize, NO, 0);
CGContextRef context = UIGraphicsGetCurrentContext();
for (UIWindow *window in [[UIApplication sharedApplication] windows])
{
CGContextSaveGState(context);
CGContextTranslateCTM(context, window.center.x, window.center.y);
CGContextConcatCTM(context, window.transform);
CGContextTranslateCTM(context, -window.bounds.size.width * window.layer.anchorPoint.x, -window.bounds.size.height * window.layer.anchorPoint.y);
if ([window respondsToSelector:#selector(drawViewHierarchyInRect:afterScreenUpdates:)])
{
[window drawViewHierarchyInRect:window.bounds afterScreenUpdates:YES];
}
else
{
[window.layer renderInContext:context];
}
CGContextRestoreGState(context);
}
UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
return image;
}
Now I am using this code and its working good.
+ (UIImage *)screenshot:(UIView *)view
{
CGRect screenRect = [[UIScreen mainScreen] bounds];
UIGraphicsBeginImageContextWithOptions(screenRect.size, NO, 0.0);
CGContextRef ctx = UIGraphicsGetCurrentContext();
[[UIColor blackColor] set];
CGContextFillRect(ctx, screenRect);
[view.layer renderInContext:ctx];
UIImage *newImage = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
return newImage;
}
Here is a method that I use to capture a UIView into a UIImage.
+ (UIImage *)renderView:(UIView *)view toImageWithSize:(CGSize)size {
UIGraphicsBeginImageContextWithOptions(size, NO, 0.);
CGContextRef c = UIGraphicsGetCurrentContext();
[view.layer renderInContext:c];
UIImage *viewImage = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
return viewImage;
}
And then you can have your screenshot method that uses the method above to render the rootViewController of the main window into an image:
+ (UIImage *)screenshot {
UIWindow *mainWindow = [UIApplication sharedApplication].windows.firstObject;
UIView *mainView = mainWindow.rootViewController.view;
return [self renderView:mainView toImageWithSize:mainView.bounds.size];
}
I hope this is helpful.
Well, this piece of code works for me. This code capture a screenshot of the view (self.view here) and all its subviews. Means, in one word, screenshot of the screen.
+ (UIImage *)screenshot {
CGRectMake *captureFrame = [[UIScreen mainScreen] bounds]; //The portion and size of the area, you want to capture. I have set it to the size of window
CALayer *layer;
layer = self.view.layer;
UIGraphicsBeginImageContext(self.view.bounds.size);
CGContextClipToRect (UIGraphicsGetCurrentContext(),captureFrame);
[layer renderInContext:UIGraphicsGetCurrentContext()];
UIImage *screenImage = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
return screenImage;
}
Hope this helps.
I am new to mobile programming. I am working in H264 video rendering in iOS application using VideoToolBox framework. It has one feature to take snapshot while rendering the video. Whenever I take a snapshot, I get the Black screen only.
I tried this
1. renderInContext,
2. drawViewHierarchyInRect,
3. snapshotViewAfterScreenUpdates method
to capture the rendering the video but returns a Black screen only.
//snapshot coding
UIGraphicsBeginImageContextWithOptions (self.view.bounds.size, YES, 0.0);
[self.view.layer renderInContext:UIGraphicsGetCurrentContext()];
UIImage *snapshotImage = UIGraphicsGetImageFromCurrentImageContext();
mImageView.image = snapshotImage;
UIGraphicsEndImageContext();
UIImageWriteToSavedPhotosAlbum(snapshotImage,self, #selector(image:didFinishSavingWithError: contextInfo:), nil);
Check this out,
following chunk of code works for me to take screen's snap shot
if ([[UIScreen mainScreen] respondsToSelector:#selector(scale)])
UIGraphicsBeginImageContextWithOptions(APP_DELEGATE.window.bounds.size, NO, [[UIScreen mainScreen] scale]);
else
UIGraphicsBeginImageContext(APP_DELEGATE.window.bounds.size);
[APP_DELEGATE.window.layer renderInContext:UIGraphicsGetCurrentContext()];
UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
NSData * data = UIImagePNGRepresentation(image);
I guess, it will help you. let me know if so
I've not worked with video yet, but a simple snapshot of UIView with subViews on it works fine
+ (UIImage *)makeSnapShot:(UIView *)view image:(UIImageView *)imageView
{
CGFloat offset_x = /*your_value*/;
CGFloat offset_y = /*your_value*/;
UIGraphicsBeginImageContext(view.bounds.size);
[view.layer renderInContext:UIGraphicsGetCurrentContext()];
UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
CGRect rect = CGRectMake(offset_x, offset_y, imageView.bounds.size.width, imageView.bounds.size.height);
CGImageRef imageRef = CGImageCreateWithImageInRect([image CGImage], rect);
image = [UIImage imageWithCGImage:imageRef];
CGImageRelease(imageRef);
return image;
}
Not sure if this is what you're looking for, but if you need to get a snapshot of the VTDecompressionSession, you can send the CVImageBuffer that you get from the decodeFrame callback into this method to get a UIImage. You can also add your CIContext to the parameters list instead of using the temporaryContext.
+ (UIImage *) UIImageFromCVImageBufferRef:(CVImageBufferRef)imageBuf
{
CIImage *ciImage = [CIImage imageWithCVPixelBuffer:imageBuf];
CIContext *temporaryContext = [CIContext contextWithOptions:nil];
CGImageRef videoImage = [temporaryContext
createCGImage:ciImage
fromRect:CGRectMake(0, 0,
CVPixelBufferGetWidth(imageBuf),
CVPixelBufferGetHeight(imageBuf))];
UIImage *image = [[UIImage alloc] initWithCGImage:videoImage];
CGImageRelease(videoImage);
return image;
}
func takeScreenshot(_ shouldSave: Bool = true) {
var screenshotImage :UIImage?
let layer = UIApplication.shared.keyWindow!.layer
let scale = UIScreen.main.scale
UIGraphicsBeginImageContextWithOptions(layer.frame.size, false, scale)
self.view.drawHierarchy(in: self.view.bounds, afterScreenUpdates: true)
screenshotImage = UIGraphicsGetImageFromCurrentImageContext()
UIGraphicsEndImageContext()
if let image = screenshotImage, shouldSave {
UIImageWriteToSavedPhotosAlbum(image, nil, nil, nil)
}
}
I'm trying to create a screenshot tweak for iOS 7 but all i am able to save is a blank image.
This is my code:
UIView *screenshotView = [[UIScreen mainScreen] snapshotViewAfterScreenUpdates:NO];
UIGraphicsBeginImageContext(screenshotView.bounds.size);
[[screenshotView layer] renderInContext:UIGraphicsGetCurrentContext()];
UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
[UIImageJPEGRepresentation(image, 1.0) writeToFile:fname atomically:YES];
Does anyone have a solution?
thank you
It appears you should not use snapshotViewAfterScreenUpdates to render images (see raywenderlich forum) but drawViewHierarchyInRect instead:
UIGraphicsBeginImageContextWithOptions(self.view.bounds.size, NO, 0.0f);
[self.view drawViewHierarchyInRect:self.view.frame afterScreenUpdates:NO];
UIImage *snapshotImage = UIGraphicsGetImageFromCurrentImageContext();
for compatibility reason i still haven't used snapshotViewAfterScreenUpdates but the following code works. give it a try.
UIGraphicsBeginImageContextWithOptions(size, myView.opaque, 2.0);
[myView.layer renderInContext:UIGraphicsGetCurrentContext()];
UIImage *theImage = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
// do something with theImage
Set the output on a UIImageView
- (UIImage *)screenshot
{
CGSize imageSize = CGSizeZero;
UIInterfaceOrientation orientation = [UIApplication sharedApplication].statusBarOrientation;
if (UIInterfaceOrientationIsPortrait(orientation)) {
imageSize = [UIScreen mainScreen].bounds.size;
} else {
imageSize = CGSizeMake([UIScreen mainScreen].bounds.size.height, [UIScreen mainScreen].bounds.size.width);
}
UIGraphicsBeginImageContextWithOptions(imageSize, NO, 0);
CGContextRef context = UIGraphicsGetCurrentContext();
for (UIWindow *window in [[UIApplication sharedApplication] windows]) {
CGContextSaveGState(context);
CGContextTranslateCTM(context, window.center.x, window.center.y);
CGContextConcatCTM(context, window.transform);
CGContextTranslateCTM(context, -window.bounds.size.width * window.layer.anchorPoint.x, -window.bounds.size.height * window.layer.anchorPoint.y);
if (orientation == UIInterfaceOrientationLandscapeLeft) {
CGContextRotateCTM(context, M_PI_2);
CGContextTranslateCTM(context, 0, -imageSize.width);
} else if (orientation == UIInterfaceOrientationLandscapeRight) {
CGContextRotateCTM(context, -M_PI_2);
CGContextTranslateCTM(context, -imageSize.height, 0);
} else if (orientation == UIInterfaceOrientationPortraitUpsideDown) {
CGContextRotateCTM(context, M_PI);
CGContextTranslateCTM(context, -imageSize.width, -imageSize.height);
}
if ([window respondsToSelector:#selector(drawViewHierarchyInRect:afterScreenUpdates:)]) {
[window drawViewHierarchyInRect:window.bounds afterScreenUpdates:YES];
} else {
[window.layer renderInContext:context];
}
CGContextRestoreGState(context);
}
UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
return image;
}
I'm trying to capture the screen inside of my app, it used to work just great, but now I only get a blurry image. like that:
This is my code:
- (UIImage *)takeScreenShotWithFrame:(CGRect)frame
{
if ([[UIScreen mainScreen] respondsToSelector:#selector(scale)]) {
UIGraphicsBeginImageContextWithOptions(frame.size, NO, [UIScreen mainScreen].scale);
} else {
UIGraphicsBeginImageContext(frame.size);
}
[self.view drawViewHierarchyInRect:frame afterScreenUpdates:NO];
UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
return image;
}
What am I doing wrong?
Thanks in advance!
instead of:
[self.view drawViewHierarchyInRect:frame afterScreenUpdates:NO];
Try:
CGContextRef context = UIGraphicsGetCurrentContext();
[self.view.layer renderInContext:context];
I am trying to generate screenshot of UIView which having subview with CATransform3DMakeRotation. Screenshot is generated but it doesn't contain Rotation.
Is it possible to achieve this?
Actual View:
ScreenShot Image
Using following call to Flip the view horizontally...
currentView.layer.transform = CATransform3DConcat(currentView.layer.transform,CATransform3DMakeRotation(M_PI, 0.0, 1.0, 0.0f));
Code for taking screen shot
+ (UIImage *) imageWithView:(UIView *)view
{
CGSize screenDimensions = view.bounds.size;
// Create a graphics context with the target size
// (last parameter takes scale into account)
UIGraphicsBeginImageContextWithOptions(screenDimensions, NO, 0);
// Render the view to a new context
CGContextRef context = UIGraphicsGetCurrentContext();
[view.layer renderInContext:context];
UIImage *img = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
return img;
}
The "renderInContext" only works for Affine transform. So convert the 3D transform into affine transform like this
currentView.layer.affineTransform = CATransform3DGetAffineTransform(CATransform3DConcat(currentView.layer.transform,CATransform3DMakeRotation(M_PI, 0.0, 1.0, 0.0f)));
Try this code
CGSize newSize = CGSizeMake(yourview.frame.size.width , yourview.frame.size.height);
UIGraphicsBeginImageContextWithOptions(newSize,YES,2.0f);
CGContextRef context = UIGraphicsGetCurrentContext();
CGContextSetInterpolationQuality(context, kCGInterpolationHigh);
[yourview.layer renderInContext:context];
[yourview drawRect:yourview.frame];
UIImage *screenShot = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
This might work, try it:
CGRect grabRect = CGRectMake(40,40,300,200);
//for retina displays
if ([[UIScreen mainScreen] respondsToSelector:#selector(scale)]) {
UIGraphicsBeginImageContextWithOptions(grabRect.size, NO, [UIScreen mainScreen].scale);
} else {
UIGraphicsBeginImageContext(grabRect.size);
}
CGContextRef ctx = UIGraphicsGetCurrentContext();
CGContextTranslateCTM(ctx, -grabRect.origin.x, -grabRect.origin.y);
[self.view.layer renderInContext:ctx];
UIImage *viewImage = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
UIImageWriteToSavedPhotosAlbum(viewImage, nil, nil, nil);
i have achieved this in one of my application by doing a little tweak like first i capture the whole screen's screen shot and then crop it with the desired frame i need here is a sample code from my app.
- (UIImage *) croppedPhoto
{
[imgcropRectangle setHidden:TRUE];
UIGraphicsBeginImageContext(self.view.frame.size);
[self.view.layer renderInContext:UIGraphicsGetCurrentContext()];
UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
// Create bitmap image from original image data,
// using rectangle to specify desired crop area
CGImageRef imageRef = CGImageCreateWithImageInRect([image CGImage], self.imgcropRectangle.frame);
UIImage *result = [UIImage imageWithCGImage:imageRef];
CGImageRelease(imageRef);
[imgcropRectangle setHidden:FALSE];
return result;
}
here imgcropRectangle is the UIImageView's object that defines my desired rectangle so i use it's frame for cropping from full screen to desired output. Hope it will help you :)
Try rendering view.layer.presentationLayer instead of view.layer
use this and before passing the view check its subviews :
+ (UIImage *) imageWithView:(UIView *)view
{
UIGraphicsBeginImageContext(CGSizeMake(view.frame.size.width, view.frame.size.height));
[view.layer renderInContext:UIGraphicsGetCurrentContext()];
UIImage *viewImage = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
return viewImage
}