我正在用几个图层组成一个视图,其中一些是旋转的。这些图层的显示效果很好,但是当我尝试制作图像时,所有的旋转/变换都会被忽略。
例如,如果我有一个包含箭头指向左侧的图像的CALayer,在围绕z轴旋转(使用CATransform3DMakeRotation)后,它指向顶部,并且图层被正确显示。但是,如果我得到该图层的图像(使用renderInContext),箭头仍然指向左侧,忽略任何转换。
任何人都知道为什么,以及如何获得我想要的结果? : - )
示例代码:
// ViewController.m
#import "ViewController.h"
#import <QuartzCore/QuartzCore.h>
// Don't forget to add the QuartzCore framework to your target.
@interface ViewController ()
@end
@implementation ViewController
- (void)loadView {
self.view = [[UIView alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
self.view.backgroundColor = [UIColor lightGrayColor];
}
- (void)viewDidLoad {
[super viewDidLoad];
// Get the arrow image (tip to the left, 50 x 50 pixels).
// (Download the image from here: http://www.4shared.com/photo/uQfor7vC/arrow.html )
UIImage *arrowImage = [UIImage imageNamed:@"arrow"];
// The arrow layer in it's starting orientation (tip to the left).
CGRect layerFrame = CGRectMake(50.0, 50.0, arrowImage.size.width, arrowImage.size.height);
CALayer *arrowLayerStart = [CALayer new];
arrowLayerStart.frame = layerFrame;
[arrowLayerStart setContents:(id)[arrowImage CGImage]];
[self.view.layer addSublayer:arrowLayerStart];
// The arrow layer rotated around the z axis by 90 degrees.
layerFrame.origin = CGPointMake(layerFrame.origin.x + layerFrame.size.width + 25.0, layerFrame.origin.y);
CALayer *arrowLayerZ90 = [CALayer new];
arrowLayerZ90.frame = layerFrame;
[arrowLayerZ90 setContents:(id)[arrowImage CGImage]];
arrowLayerZ90.transform = CATransform3DMakeRotation(M_PI/2.0, 0.0, 0.0, 1.0);
[self.view.layer addSublayer:arrowLayerZ90];
// Now make images of each of these layers and display them in a second row.
// The starting layer without any rotation.
UIGraphicsBeginImageContext(arrowLayerStart.frame.size);
[arrowLayerStart renderInContext:UIGraphicsGetCurrentContext()];
UIImage *arrowStartImage = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
layerFrame.origin = CGPointMake(arrowLayerStart.frame.origin.x,
arrowLayerStart.frame.origin.y + arrowLayerStart.frame.size.height + 25.0);
CALayer *arrowLayerStartCaptured = [CALayer new];
arrowLayerStartCaptured.frame = layerFrame;
[arrowLayerStartCaptured setContents:(id)[arrowStartImage CGImage]];
[self.view.layer addSublayer:arrowLayerStartCaptured];
// The second layer, rotated around the z axis by 90 degrees.
UIGraphicsBeginImageContext(arrowLayerZ90.frame.size);
[arrowLayerZ90 renderInContext:UIGraphicsGetCurrentContext()];
UIImage *arrowZ90Image = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
layerFrame.origin = CGPointMake(arrowLayerZ90.frame.origin.x,
arrowLayerZ90.frame.origin.y + arrowLayerZ90.frame.size.height + 25.0);
CALayer *arrowLayerZ90Captured = [CALayer new];
arrowLayerZ90Captured.frame = layerFrame;
[arrowLayerZ90Captured setContents:(id)[arrowZ90Image CGImage]];
[self.view.layer addSublayer:arrowLayerZ90Captured];
}
@end
// ViewController.h
#import <UIKit/UIKit.h>
@interface ViewController : UIViewController
@end
// AppDelegate.h
#import <UIKit/UIKit.h>
@interface AppDelegate : UIResponder <UIApplicationDelegate>
@property (strong, nonatomic) UIWindow *window;
@end
// AppDelegate.m
#import "AppDelegate.h"
#import "ViewController.h"
@implementation AppDelegate
@synthesize window = _window;
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
self.window.rootViewController = [[ViewController alloc] init];
[self.window makeKeyAndVisible];
return YES;
}
@end
答案 0 :(得分:1)
The documentation for -[CALayer renderInContext:]
说:
此方法的Mac OS X v10.5实现没有 支持整个Core Animation组合模型。 QCCompositionLayer,CAOpenGLLayer和QTMovieLayer图层不是 渲染。此外,使用3D变换的图层不是 渲染,也不是指定backgroundFilters,filters的图层, compositingFilter,或掩码值。未来版本的Mac OS X可能会 添加对渲染这些图层和属性的支持。
(此限制也出现在iOS上。)
标题CALayer.h
也说:
* WARNING: currently this method does not implement the full
* CoreAnimation composition model, use with caution. */
基本上,-renderInContext:
在一些简单的情况下很有用,但在更复杂的情况下不会按预期工作。您将需要找到一些其他方式来绘图。 Quartz(核心图形)适用于2D,但对于3D,你可以自己使用。
答案 1 :(得分:0)
您可以使用Core Graphaic而不是CATransform3DMakeRotation:)
CGAffineTransform flip = CGAffineTransformMakeScale(1.0, -1.0);