Commit 8e953366 authored by rsesek@chromium.org's avatar rsesek@chromium.org

Move NSImage-to-CGImageRef conversion code into a common helper function in base/mac_util.h.

BUG=49571
TEST=Covered by unit_tests.

Review URL: http://codereview.chromium.org/3072005

git-svn-id: svn://svn.chromium.org/chrome/trunk/src@53997 0039d316-1c4b-4281-b951-d872f2087c98
parent 46f36a49
...@@ -17,6 +17,7 @@ class FilePath; ...@@ -17,6 +17,7 @@ class FilePath;
@class NSWindow; @class NSWindow;
#else #else
class NSBundle; class NSBundle;
class NSImage;
class NSWindow; class NSWindow;
#endif #endif
...@@ -141,6 +142,13 @@ CFTypeRef GetValueFromDictionary(CFDictionaryRef dict, ...@@ -141,6 +142,13 @@ CFTypeRef GetValueFromDictionary(CFDictionaryRef dict,
// Sets the process name as displayed in Activity Monitor to process_name. // Sets the process name as displayed in Activity Monitor to process_name.
void SetProcessName(CFStringRef process_name); void SetProcessName(CFStringRef process_name);
// Converts a NSImage to a CGImageRef. Normally, the system frameworks can do
// this fine, especially on 10.6. On 10.5, however, CGImage cannot handle
// converting a PDF-backed NSImage into a CGImageRef. This function will
// rasterize the PDF into a bitmap CGImage. The caller is responsible for
// releasing the return value.
CGImageRef CopyNSImageToCGImage(NSImage* image);
} // namespace mac_util } // namespace mac_util
#endif // BASE_MAC_UTIL_H_ #endif // BASE_MAC_UTIL_H_
...@@ -479,4 +479,37 @@ void SetProcessName(CFStringRef process_name) { ...@@ -479,4 +479,37 @@ void SetProcessName(CFStringRef process_name) {
LOG_IF(ERROR, err) << "Call to set process name failed, err " << err; LOG_IF(ERROR, err) << "Call to set process name failed, err " << err;
} }
// Converts a NSImage to a CGImageRef. Normally, the system frameworks can do
// this fine, especially on 10.6. On 10.5, however, CGImage cannot handle
// converting a PDF-backed NSImage into a CGImageRef. This function will
// rasterize the PDF into a bitmap CGImage. The caller is responsible for
// releasing the return value.
CGImageRef CopyNSImageToCGImage(NSImage* image) {
// This is based loosely on http://www.cocoadev.com/index.pl?CGImageRef .
NSSize size = [image size];
scoped_cftyperef<CGContextRef> context(
CGBitmapContextCreate(NULL, // Allow CG to allocate memory.
size.width,
size.height,
8, // bitsPerComponent
0, // bytesPerRow - CG will calculate by default.
[[NSColorSpace genericRGBColorSpace] CGColorSpace],
kCGBitmapByteOrder32Host |
kCGImageAlphaPremultipliedFirst));
if (!context.get())
return NULL;
[NSGraphicsContext saveGraphicsState];
[NSGraphicsContext setCurrentContext:
[NSGraphicsContext graphicsContextWithGraphicsPort:context.get()
flipped:NO]];
[image drawInRect:NSMakeRect(0,0, size.width, size.height)
fromRect:NSZeroRect
operation:NSCompositeCopy
fraction:1.0];
[NSGraphicsContext restoreGraphicsState];
return CGBitmapContextCreateImage(context);
}
} // namespace mac_util } // namespace mac_util
// Copyright (c) 2008-2009 The Chromium Authors. All rights reserved. // Copyright (c) 2010 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be // Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file. // found in the LICENSE file.
...@@ -165,6 +165,21 @@ TEST_F(MacUtilTest, TestGetValueFromDictionary) { ...@@ -165,6 +165,21 @@ TEST_F(MacUtilTest, TestGetValueFromDictionary) {
dict, CFSTR("no-exist"), CFStringGetTypeID())); dict, CFSTR("no-exist"), CFStringGetTypeID()));
} }
TEST_F(MacUtilTest, CopyNSImageToCGImage) {
scoped_nsobject<NSImage> nsImage(
[[NSImage alloc] initWithSize:NSMakeSize(20, 20)]);
[nsImage lockFocus];
[[NSColor redColor] set];
NSRect rect = NSZeroRect;
rect.size = [nsImage size];
NSRectFill(rect);
[nsImage unlockFocus];
scoped_cftyperef<CGImageRef> cgImage(
mac_util::CopyNSImageToCGImage(nsImage.get()));
EXPECT_TRUE(cgImage.get());
}
} // namespace } // namespace
} // namespace mac_util } // namespace mac_util
...@@ -5,6 +5,7 @@ ...@@ -5,6 +5,7 @@
#import "chrome/browser/cocoa/animatable_image.h" #import "chrome/browser/cocoa/animatable_image.h"
#include "base/logging.h" #include "base/logging.h"
#import "base/mac_util.h"
#include "base/scoped_cftyperef.h" #include "base/scoped_cftyperef.h"
#import "third_party/GTM/AppKit/GTMNSAnimation+Duration.h" #import "third_party/GTM/AppKit/GTMNSAnimation+Duration.h"
...@@ -126,36 +127,13 @@ ...@@ -126,36 +127,13 @@
[CATransaction commit]; [CATransaction commit];
} }
// CALayer expects a CGImageRef contents. If the image is a PDF, 10.5 CGImage // Sets the layer contents by converting the NSImage to a CGImageRef. This will
// cannot handle the conversion to bitmap. To get it to work, rasterize the // rasterize PDF resources.
// image into a bitmap CGImageRef. This is based loosely on
// http://www.cocoadev.com/index.pl?CGImageRef.
- (void)setLayerContents:(CALayer*)layer { - (void)setLayerContents:(CALayer*)layer {
NSSize size = [image_ size]; scoped_cftyperef<CGImageRef> image(
CGContextRef context = mac_util::CopyNSImageToCGImage(image_.get()));
CGBitmapContextCreate(NULL, // Allow CG to allocate memory.
size.width,
size.height,
8, // bitsPerComponent
0, // bytesPerRow - CG will calculate by default.
[[NSColorSpace genericRGBColorSpace] CGColorSpace],
kCGBitmapByteOrder32Host |
kCGImageAlphaPremultipliedFirst);
[NSGraphicsContext saveGraphicsState];
[NSGraphicsContext setCurrentContext:
[NSGraphicsContext graphicsContextWithGraphicsPort:context flipped:NO]];
[image_ drawInRect:NSMakeRect(0,0, size.width, size.height)
fromRect:NSZeroRect
operation:NSCompositeCopy
fraction:1.0];
[NSGraphicsContext restoreGraphicsState];
scoped_cftyperef<CGImageRef> cgImage(CGBitmapContextCreateImage(context));
CGContextRelease(context);
// Create the layer that will be animated. // Create the layer that will be animated.
[layer setContents:(id)cgImage.get()]; [layer setContents:(id)image.get()];
} }
// CAAnimation delegate method called when the animation is complete. // CAAnimation delegate method called when the animation is complete.
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment