summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authoravi@chromium.org <avi@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2009-07-27 16:34:17 +0000
committeravi@chromium.org <avi@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2009-07-27 16:34:17 +0000
commit39e5624b02994bf4bb5d3799136c2f39902695dd (patch)
treeb47c03b47e17232c04d94577777929c1af423526
parent1c84c82c18f7bae04a6b6f309979fc0ad979ec3f (diff)
downloadchromium_src-39e5624b02994bf4bb5d3799136c2f39902695dd.zip
chromium_src-39e5624b02994bf4bb5d3799136c2f39902695dd.tar.gz
chromium_src-39e5624b02994bf4bb5d3799136c2f39902695dd.tar.bz2
Give crashed tabs the crashed tab icon on the Mac.
BUG=none TEST=crash a page and see if the icon shows up (animated) Review URL: http://codereview.chromium.org/160113 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@21648 0039d316-1c4b-4281-b951-d872f2087c98
-rw-r--r--chrome/app/nibs/ClearBrowsingData.xib62
-rw-r--r--chrome/browser/cocoa/clear_browsing_data_controller.h1
-rw-r--r--chrome/browser/cocoa/clear_browsing_data_controller.mm10
-rw-r--r--chrome/browser/cocoa/tab_controller.h1
-rw-r--r--chrome/browser/cocoa/tab_strip_controller.mm15
-rw-r--r--chrome/browser/cocoa/throbber_view.h37
-rw-r--r--chrome/browser/cocoa/throbber_view.mm260
-rw-r--r--chrome/browser/cocoa/throbber_view_unittest.mm3
-rw-r--r--chrome/chrome.gyp1
9 files changed, 266 insertions, 124 deletions
diff --git a/chrome/app/nibs/ClearBrowsingData.xib b/chrome/app/nibs/ClearBrowsingData.xib
index bb2a675..cb5229f 100644
--- a/chrome/app/nibs/ClearBrowsingData.xib
+++ b/chrome/app/nibs/ClearBrowsingData.xib
@@ -2,10 +2,10 @@
<archive type="com.apple.InterfaceBuilder3.Cocoa.XIB" version="7.03">
<data>
<int key="IBDocument.SystemTarget">1050</int>
- <string key="IBDocument.SystemVersion">9F33</string>
+ <string key="IBDocument.SystemVersion">9J61</string>
<string key="IBDocument.InterfaceBuilderVersion">677</string>
- <string key="IBDocument.AppKitVersion">949.34</string>
- <string key="IBDocument.HIToolboxVersion">352.00</string>
+ <string key="IBDocument.AppKitVersion">949.46</string>
+ <string key="IBDocument.HIToolboxVersion">353.00</string>
<object class="NSMutableArray" key="IBDocument.EditedObjectIDs">
<bool key="EncodedWithXMLCoder">YES</bool>
<integer value="2"/>
@@ -358,12 +358,15 @@
<int key="NSPeriodicInterval">25</int>
</object>
</object>
- <object class="NSCustomView" id="1005756006">
+ <object class="NSProgressIndicator" id="139484523">
<reference key="NSNextResponder" ref="1006"/>
- <int key="NSvFlags">268</int>
- <string key="NSFrame">{{20, 24}, {16, 16}}</string>
+ <int key="NSvFlags">1292</int>
+ <object class="NSPSMatrix" key="NSDrawMatrix"/>
+ <string key="NSFrame">{{20, 20}, {16, 16}}</string>
<reference key="NSSuperview" ref="1006"/>
- <string key="NSClassName">ThrobberView</string>
+ <int key="NSpiFlags">20746</int>
+ <double key="NSMinValue">1.600000e+01</double>
+ <double key="NSMaxValue">1.000000e+02</double>
</object>
</object>
<string key="NSFrameSize">{331, 299}</string>
@@ -372,6 +375,9 @@
<string key="NSScreenRect">{{0, 0}, {1680, 1028}}</string>
<string key="NSMaxSize">{3.40282e+38, 3.40282e+38}</string>
</object>
+ <object class="NSUserDefaultsController" id="475014300">
+ <bool key="NSSharedInstance">YES</bool>
+ </object>
</object>
<object class="IBObjectContainer" key="IBDocument.Objects">
<object class="NSMutableArray" key="connectionRecords">
@@ -576,10 +582,10 @@
<object class="IBConnectionRecord">
<object class="IBBindingConnection" key="connection">
<string key="label">hidden: isClearing</string>
- <reference key="source" ref="1005756006"/>
+ <reference key="source" ref="139484523"/>
<reference key="destination" ref="1001"/>
<object class="NSNibBindingConnector" key="connector">
- <reference key="NSSource" ref="1005756006"/>
+ <reference key="NSSource" ref="139484523"/>
<reference key="NSDestination" ref="1001"/>
<string key="NSLabel">hidden: isClearing</string>
<string key="NSBinding">hidden</string>
@@ -591,15 +597,7 @@
<int key="NSNibBindingConnectorVersion">2</int>
</object>
</object>
- <int key="connectionID">70</int>
- </object>
- <object class="IBConnectionRecord">
- <object class="IBOutletConnection" key="connection">
- <string key="label">progress_</string>
- <reference key="source" ref="1001"/>
- <reference key="destination" ref="1005756006"/>
- </object>
- <int key="connectionID">71</int>
+ <int key="connectionID">77</int>
</object>
</object>
<object class="IBMutableOrderedSet" key="objectRecords">
@@ -656,7 +654,7 @@
<reference ref="712572294"/>
<reference ref="340114853"/>
<reference ref="110601986"/>
- <reference ref="1005756006"/>
+ <reference ref="139484523"/>
</object>
<reference key="parent" ref="1005"/>
</object>
@@ -851,10 +849,15 @@
<reference key="parent" ref="485872479"/>
</object>
<object class="IBObjectRecord">
- <int key="objectID">64</int>
- <reference key="object" ref="1005756006"/>
+ <int key="objectID">72</int>
+ <reference key="object" ref="139484523"/>
<reference key="parent" ref="1006"/>
</object>
+ <object class="IBObjectRecord">
+ <int key="objectID">73</int>
+ <reference key="object" ref="475014300"/>
+ <reference key="parent" ref="1002"/>
+ </object>
</object>
</object>
<object class="NSMutableDictionary" key="flattenedProperties">
@@ -897,8 +900,8 @@
<string>4.IBPluginDependency</string>
<string>5.IBPluginDependency</string>
<string>6.IBPluginDependency</string>
- <string>64.IBPluginDependency</string>
<string>7.IBPluginDependency</string>
+ <string>72.IBPluginDependency</string>
<string>8.IBPluginDependency</string>
</object>
<object class="NSMutableArray" key="dict.values">
@@ -964,7 +967,7 @@
</object>
</object>
<nil key="sourceID"/>
- <int key="maxID">71</int>
+ <int key="maxID">77</int>
</object>
<object class="IBClassDescriber" key="IBDocument.Classes">
<object class="NSMutableArray" key="referencedPartialClassDescriptions">
@@ -985,10 +988,6 @@
<string>id</string>
</object>
</object>
- <object class="NSMutableDictionary" key="outlets">
- <string key="NS.key.0">progress_</string>
- <string key="NS.object.0">ThrobberView</string>
- </object>
<object class="IBClassDescriptionSource" key="sourceIdentifier">
<string key="majorKey">IBProjectSource</string>
<string key="minorKey">browser/cocoa/clear_browsing_data_controller.h</string>
@@ -998,21 +997,20 @@
<string key="className">NSObject</string>
<object class="IBClassDescriptionSource" key="sourceIdentifier">
<string key="majorKey">IBProjectSource</string>
- <string key="minorKey">browser/cocoa/tab_strip_model_observer_bridge.h</string>
+ <string key="minorKey">browser/cocoa/status_bubble_mac.h</string>
</object>
</object>
<object class="IBPartialClassDescription">
- <string key="className">ThrobberView</string>
- <string key="superclassName">NSView</string>
+ <string key="className">NSObject</string>
<object class="IBClassDescriptionSource" key="sourceIdentifier">
<string key="majorKey">IBProjectSource</string>
- <string key="minorKey">browser/cocoa/throbber_view.h</string>
+ <string key="minorKey">browser/cocoa/tab_strip_model_observer_bridge.h</string>
</object>
</object>
</object>
</object>
<int key="IBDocument.localizationMode">0</int>
- <string key="IBDocument.LastKnownRelativeProjectPath">../../../chrome.xcodeproj</string>
+ <string key="IBDocument.LastKnownRelativeProjectPath">../../chrome.xcodeproj</string>
<int key="IBDocument.defaultPropertyAccessControl">3</int>
</data>
</archive>
diff --git a/chrome/browser/cocoa/clear_browsing_data_controller.h b/chrome/browser/cocoa/clear_browsing_data_controller.h
index d954981..3a8150b 100644
--- a/chrome/browser/cocoa/clear_browsing_data_controller.h
+++ b/chrome/browser/cocoa/clear_browsing_data_controller.h
@@ -27,7 +27,6 @@ class Profile;
BrowsingDataRemover* remover_;
scoped_ptr<ClearBrowsingObserver> observer_;
BOOL isClearing_; // YES while clearing data is ongoing.
- IBOutlet ThrobberView* progress_;
// Values for checkboxes, kept in sync with bindings. These values get
// persisted into prefs if the user accepts the dialog.
diff --git a/chrome/browser/cocoa/clear_browsing_data_controller.mm b/chrome/browser/cocoa/clear_browsing_data_controller.mm
index 9910d28..03863f36 100644
--- a/chrome/browser/cocoa/clear_browsing_data_controller.mm
+++ b/chrome/browser/cocoa/clear_browsing_data_controller.mm
@@ -63,16 +63,6 @@ class ClearBrowsingObserver : public BrowsingDataRemover::Observer {
[super dealloc];
}
-// Called when outlets are available. Set the throbber icon.
-- (void)awakeFromNib {
- NSString *imagePath = [mac_util::MainAppBundle()
- pathForResource:@"throbber"
- ofType:@"png"];
- scoped_nsobject<NSImage> throbberImage(
- [[NSImage alloc] initWithContentsOfFile:imagePath]);
- [progress_ setImage:throbberImage];
-}
-
// Run application modal.
- (void)runModalDialog {
[[NSApplication sharedApplication] runModalForWindow:[self window]];
diff --git a/chrome/browser/cocoa/tab_controller.h b/chrome/browser/cocoa/tab_controller.h
index ba1d626..bffdf7f 100644
--- a/chrome/browser/cocoa/tab_controller.h
+++ b/chrome/browser/cocoa/tab_controller.h
@@ -16,6 +16,7 @@ enum TabLoadingState {
kTabDone,
kTabLoading,
kTabWaiting,
+ kTabCrashed,
};
@class TabView;
diff --git a/chrome/browser/cocoa/tab_strip_controller.mm b/chrome/browser/cocoa/tab_strip_controller.mm
index efd4f1b..a15244f 100644
--- a/chrome/browser/cocoa/tab_strip_controller.mm
+++ b/chrome/browser/cocoa/tab_strip_controller.mm
@@ -571,6 +571,8 @@ static const float kUseFullAvailableWidth = -1.0;
[nsimage_cache::ImageNamed(@"throbber_waiting.png") retain];
static NSImage* throbberLoadingImage =
[nsimage_cache::ImageNamed(@"throbber.png") retain];
+ static NSImage* sadFaviconImage =
+ [nsimage_cache::ImageNamed(@"sadfavicon.png") retain];
TabController* tabController = [tabArray_ objectAtIndex:index];
@@ -584,17 +586,24 @@ static const float kUseFullAvailableWidth = -1.0;
} else if (contents->is_loading()) {
newState = kTabLoading;
throbberImage = throbberLoadingImage;
+ } else if (contents->is_crashed()) {
+ newState = kTabCrashed;
}
if (oldState != newState || newState == kTabDone) {
NSView* iconView = nil;
if (newState == kTabDone) {
iconView = [self favIconImageViewForContents:contents];
+ } else if (newState == kTabCrashed) {
+ NSImage* oldImage = [[self favIconImageViewForContents:contents] image];
+ NSRect frame = NSMakeRect(0, 0, 16, 16);
+ iconView = [ThrobberView toastThrobberViewWithFrame:frame
+ beforeImage:oldImage
+ afterImage:sadFaviconImage];
} else {
NSRect frame = NSMakeRect(0, 0, 16, 16);
- iconView =
- [[[ThrobberView alloc] initWithFrame:frame
- image:throbberImage] autorelease];
+ iconView = [ThrobberView filmstripThrobberViewWithFrame:frame
+ image:throbberImage];
}
[tabController setLoadingState:newState];
diff --git a/chrome/browser/cocoa/throbber_view.h b/chrome/browser/cocoa/throbber_view.h
index e0b06ba..ef334fb 100644
--- a/chrome/browser/cocoa/throbber_view.h
+++ b/chrome/browser/cocoa/throbber_view.h
@@ -9,32 +9,35 @@
#include "base/scoped_nsobject.h"
-@class TimerTarget;
+@class ThrobberTimerTarget;
+@protocol ThrobberDataDelegate;
// A class that knows how to draw an animated state to indicate progress.
-// Currently draws via a sequence of frames in an image, but may ultimately be
-// written to render paths that are rotated around a center origin. Creating
-// the class starts the animation, destroying it stops it. There is no state
-// where the class is frozen on an image and not animating.
+// Creating the class starts the animation, destroying it stops it. There are
+// two types:
+//
+// - Filmstrip: Draws via a sequence of frames in an image. There is no state
+// where the class is frozen on an image and not animating. The image needs to
+// be made of squares such that the height divides evently into the width.
+//
+// - Toast: Draws an image animating down to the bottom and then another image
+// animating up from the bottom. Stops once the animation is complete.
@interface ThrobberView : NSView {
@private
- scoped_nsobject<CIImage> image_;
- scoped_nsobject<TimerTarget> target_; // Target of animation timer.
+ scoped_nsobject<ThrobberTimerTarget> target_; // Target of animation timer.
+ id<ThrobberDataDelegate> dataDelegate_;
NSTimer* timer_; // Animation timer. Weak, owned by runloop.
- unsigned int numFrames_; // Number of frames in this animation.
- unsigned int animationFrame_; // Current frame of the animation,
- // [0..numFrames_)
}
-// Creates the view with |frame| and the image strip desginated by |image|. The
-// image needs to be made of squares such that the height divides evently into
-// the width. Takes ownership of |image|.
-- (id)initWithFrame:(NSRect)frame image:(NSImage*)image;
+// Creates a filmstrip view with |frame| and image |image|.
++ (id)filmstripThrobberViewWithFrame:(NSRect)frame
+ image:(NSImage*)image;
-// Allows changing the image once the view has been created, such as when the
-// view is loaded from a nib. The same restrictions as above apply.
-- (void)setImage:(NSImage*)image;
+// Creates a toast view with |frame| and specified images.
++ (id)toastThrobberViewWithFrame:(NSRect)frame
+ beforeImage:(NSImage*)beforeImage
+ afterImage:(NSImage*)afterImage;
@end
diff --git a/chrome/browser/cocoa/throbber_view.mm b/chrome/browser/cocoa/throbber_view.mm
index bfdf4bb..696ada7 100644
--- a/chrome/browser/cocoa/throbber_view.mm
+++ b/chrome/browser/cocoa/throbber_view.mm
@@ -9,20 +9,171 @@
static const float kAnimationIntervalSeconds = 0.03; // 30ms, same as windows
@interface ThrobberView(PrivateMethods)
+- (id)initWithFrame:(NSRect)frame delegate:(id<ThrobberDataDelegate>)delegate;
- (void)animate;
@end
+@protocol ThrobberDataDelegate <NSObject>
+// Is the current frame the last frame of the animation?
+- (BOOL)animationIsComplete;
+
+// Draw the current frame into the current graphics context.
+- (void)drawFrameInRect:(NSRect)rect;
+
+// Update the frame counter.
+- (void)advanceFrame;
+@end
+
+@interface ThrobberFilmstripDelegate : NSObject
+ <ThrobberDataDelegate> {
+ scoped_nsobject<CIImage> image_;
+ unsigned int numFrames_; // Number of frames in this animation.
+ unsigned int animationFrame_; // Current frame of the animation,
+ // [0..numFrames_)
+}
+
+- (id)initWithImage:(NSImage*)image;
+
+@end
+
+@implementation ThrobberFilmstripDelegate
+
+// Stores the internal representation of the image from |image|. We use
+// CoreImage for speed (though this doesn't seem to help perf issues). We
+// validate that the image is of the appropriate ratio.
+- (id)initWithImage:(NSImage*)image {
+ if ((self = [super init])) {
+ // Reset the animation counter so there's no chance we are off the end.
+ animationFrame_ = 0;
+
+ // Ensure that the height divides evenly into the width. Cache the
+ // number of frames in the animation for later.
+ NSSize imageSize = [image size];
+ DCHECK(imageSize.height && imageSize.width);
+ if (!imageSize.height)
+ return nil;
+ DCHECK((int)imageSize.width % (int)imageSize.height == 0);
+ numFrames_ = (int)imageSize.width / (int)imageSize.height;
+ DCHECK(numFrames_);
+
+ // First check if we have a bitmap image rep and use it, otherwise fall
+ // back to creating one.
+ NSBitmapImageRep* rep = [[image representations] objectAtIndex:0];
+ if (![rep isKindOfClass:[NSBitmapImageRep class]]) {
+ [image lockFocus];
+ NSRect imageRect = NSMakeRect(0, 0, imageSize.width, imageSize.height);
+ rep = [[[NSBitmapImageRep alloc] initWithFocusedViewRect:imageRect]
+ autorelease];
+ [image unlockFocus];
+ }
+ image_.reset([[CIImage alloc] initWithBitmapImageRep:rep]);
+ }
+ return self;
+}
+
+- (BOOL)animationIsComplete {
+ return NO;
+}
+
+- (void)drawFrameInRect:(NSRect)rect {
+ float imageDimension = [image_ extent].size.height;
+ float xOffset = animationFrame_ * imageDimension;
+ NSRect sourceImageRect =
+ NSMakeRect(xOffset, 0, imageDimension, imageDimension);
+ [image_ drawInRect:rect
+ fromRect:sourceImageRect
+ operation:NSCompositeSourceOver
+ fraction:1.0];
+}
+
+- (void)advanceFrame {
+ animationFrame_ = ++animationFrame_ % numFrames_;
+}
+
+@end
+
+@interface ThrobberToastDelegate : NSObject
+ <ThrobberDataDelegate> {
+ scoped_nsobject<NSImage> image1_;
+ scoped_nsobject<NSImage> image2_;
+ NSSize image1Size_;
+ NSSize image2Size_;
+ int animationFrame_; // Current frame of the animation,
+}
+
+- (id)initWithImage1:(NSImage*)image1 image2:(NSImage*)image2;
+
+@end
+
+@implementation ThrobberToastDelegate
+
+- (id)initWithImage1:(NSImage*)image1 image2:(NSImage*)image2 {
+ if ((self = [super init])) {
+ image1_.reset([image1 retain]);
+ image2_.reset([image2 retain]);
+ image1Size_ = [image1 size];
+ image2Size_ = [image2 size];
+ animationFrame_ = 0;
+ }
+ return self;
+}
+
+- (BOOL)animationIsComplete {
+ if (animationFrame_ >= image1Size_.height + image2Size_.height)
+ return YES;
+
+ return NO;
+}
+
+// From [0..image1Height) we draw image1, at image1Height we draw nothing, and
+// from [image1Height+1..image1Hight+image2Height] we draw the second image.
+- (void)drawFrameInRect:(NSRect)rect {
+ NSImage* image = nil;
+ NSSize srcSize;
+ NSRect destRect;
+
+ if (animationFrame_ < image1Size_.height) {
+ image = image1_.get();
+ srcSize = image1Size_;
+ destRect = NSMakeRect(0, -animationFrame_,
+ image1Size_.width, image1Size_.height);
+ } else if (animationFrame_ == image1Size_.height) {
+ // nothing; intermediate blank frame
+ } else {
+ image = image2_.get();
+ srcSize = image2Size_;
+ destRect = NSMakeRect(0, animationFrame_ -
+ (image1Size_.height + image2Size_.height),
+ image2Size_.width, image2Size_.height);
+ }
+
+ if (image) {
+ NSRect sourceImageRect =
+ NSMakeRect(0, 0, srcSize.width, srcSize.height);
+ [image drawInRect:destRect
+ fromRect:sourceImageRect
+ operation:NSCompositeSourceOver
+ fraction:1.0];
+ }
+}
+
+- (void)advanceFrame {
+ ++animationFrame_;
+}
+
+@end
+
// A very simple object that is the target for the animation timer so that
// the view isn't. We do this to avoid retain cycles as the timer
// retains its target.
-@interface TimerTarget : NSObject {
+@interface ThrobberTimerTarget : NSObject {
@private
ThrobberView* throbber_; // Weak, owns us
}
- (id)initWithThrobber:(ThrobberView*)view;
@end
-@implementation TimerTarget
+@implementation ThrobberTimerTarget
- (id)initWithThrobber:(ThrobberView*)view {
if ((self = [super init])) {
throbber_ = view;
@@ -37,15 +188,50 @@ static const float kAnimationIntervalSeconds = 0.03; // 30ms, same as windows
@implementation ThrobberView
-- (id)initWithFrame:(NSRect)frame image:(NSImage*)image {
++ (id)filmstripThrobberViewWithFrame:(NSRect)frame
+ image:(NSImage*)image {
+ ThrobberFilmstripDelegate* delegate =
+ [[[ThrobberFilmstripDelegate alloc] initWithImage:image] autorelease];
+ if (!delegate)
+ return nil;
+
+ return [[[ThrobberView alloc] initWithFrame:frame
+ delegate:delegate] autorelease];
+}
+
++ (id)toastThrobberViewWithFrame:(NSRect)frame
+ beforeImage:(NSImage*)beforeImage
+ afterImage:(NSImage*)afterImage {
+ ThrobberToastDelegate* delegate =
+ [[[ThrobberToastDelegate alloc] initWithImage1:beforeImage
+ image2:afterImage] autorelease];
+ if (!delegate)
+ return nil;
+
+ return [[[ThrobberView alloc] initWithFrame:frame
+ delegate:delegate] autorelease];
+}
+
+- (id)initWithFrame:(NSRect)frame delegate:(id<ThrobberDataDelegate>)delegate {
if ((self = [super initWithFrame:frame])) {
- [self setImage:image];
+ dataDelegate_ = [delegate retain];
+
+ // Start a timer for the animation frames.
+ target_.reset([[ThrobberTimerTarget alloc] initWithThrobber:self]);
+ timer_ = [NSTimer scheduledTimerWithTimeInterval:kAnimationIntervalSeconds
+ target:target_.get()
+ selector:@selector(animate:)
+ userInfo:nil
+ repeats:YES];
}
return self;
}
- (void)dealloc {
- [timer_ invalidate];
+ [dataDelegate_ release];
+ if (timer_)
+ [timer_ invalidate];
+
[super dealloc];
}
@@ -56,67 +242,21 @@ static const float kAnimationIntervalSeconds = 0.03; // 30ms, same as windows
[super removeFromSuperview];
}
-// Called when the TimerTarget gets tickled by our timer. Increment the frame
-// counter and mark as needing display.
+// Called when the ThrobberTimerTarget gets tickled by our timer. Advance the
+// frame, dirty the display, and kill the timer when it's no longer needed.
- (void)animate {
- animationFrame_ = ++animationFrame_ % numFrames_;
+ [dataDelegate_ advanceFrame];
[self setNeedsDisplay:YES];
+
+ if ([dataDelegate_ animationIsComplete]) {
+ [timer_ invalidate];
+ timer_ = nil;
+ }
}
// Overridden to draw the appropriate frame in the image strip.
- (void)drawRect:(NSRect)rect {
- float imageDimension = [image_ extent].size.height;
- float xOffset = animationFrame_ * imageDimension;
- NSRect sourceImageRect =
- NSMakeRect(xOffset, 0, imageDimension, imageDimension);
- [image_ drawInRect:[self bounds]
- fromRect:sourceImageRect
- operation:NSCompositeSourceOver
- fraction:1.0];
-}
-
-// Stores the internal representation of the image from |image|. We use
-// CoreImage for speed (though this doesn't seem to help perf issues). We
-// validate that the image is of the appropriate ratio. If the image has more
-// than one frame, restarts the timer.
-- (void)setImage:(NSImage*)image {
- // Reset the animation counter so there's no chance we are off the end.
- animationFrame_ = 0;
- [timer_ invalidate];
- timer_ = nil;
-
- // Ensure that the height divides evenly into the width. Cache the
- // number of frames in the animation for later.
- NSSize imageSize = [image size];
- DCHECK(imageSize.height && imageSize.width);
- if (!imageSize.height)
- return;
- DCHECK((int)imageSize.width % (int)imageSize.height == 0);
- numFrames_ = (int)imageSize.width / (int)imageSize.height;
- DCHECK(numFrames_);
-
- // First check if we have a bitmap image rep and use it, otherwise fall
- // back to creating one.
- NSBitmapImageRep* rep = [[image representations] objectAtIndex:0];
- if (![rep isKindOfClass:[NSBitmapImageRep class]]) {
- [image lockFocus];
- NSRect imageRect = NSMakeRect(0, 0, imageSize.width, imageSize.height);
- rep = [[[NSBitmapImageRep alloc] initWithFocusedViewRect:imageRect]
- autorelease];
- [image unlockFocus];
- }
- image_.reset([[CIImage alloc] initWithBitmapImageRep:rep]);
-
- if (numFrames_ > 1) {
- // Start a timer for the animation frames.
- target_.reset([[TimerTarget alloc] initWithThrobber:self]);
- timer_ =
- [NSTimer scheduledTimerWithTimeInterval:kAnimationIntervalSeconds
- target:target_.get()
- selector:@selector(animate:)
- userInfo:nil
- repeats:YES];
- }
+ [dataDelegate_ drawFrameInRect:[self bounds]];
}
@end
diff --git a/chrome/browser/cocoa/throbber_view_unittest.mm b/chrome/browser/cocoa/throbber_view_unittest.mm
index 72d2240..2cf2db4 100644
--- a/chrome/browser/cocoa/throbber_view_unittest.mm
+++ b/chrome/browser/cocoa/throbber_view_unittest.mm
@@ -20,7 +20,8 @@ class ThrobberViewTest : public PlatformTest {
NSImage* image = [[[NSImage alloc] initByReferencingFile:
[bundle pathForResource:@"throbber" ofType:@"png"]]
autorelease];
- view_.reset([[ThrobberView alloc] initWithFrame:frame image:image]);
+ view_.reset([[ThrobberView filmstripThrobberViewWithFrame:frame
+ image:image] retain]);
[cocoa_helper_.contentView() addSubview:view_.get()];
}
diff --git a/chrome/chrome.gyp b/chrome/chrome.gyp
index e94ca05..f404291 100644
--- a/chrome/chrome.gyp
+++ b/chrome/chrome.gyp
@@ -2699,6 +2699,7 @@
'app/theme/pageinfo_bad.png',
'app/theme/pageinfo_good.png',
'app/theme/reload_Template.pdf',
+ 'app/theme/sadfavicon.png',
'app/theme/sadtab.png',
'app/theme/star_Template.pdf',
'app/theme/starred.pdf',