BookmarkManager: Fix 'new folder text field size changes on clicking it' issue.
[chromium-blink-merge.git] / chrome / browser / ui / cocoa / table_row_nsimage_cache.mm
blob6fddd2d0eb71630cb0a0875136fe75d23e7ef04e
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #include "chrome/browser/ui/cocoa/table_row_nsimage_cache.h"
7 #include "base/logging.h"
8 #include "ui/gfx/image/image_skia.h"
9 #include "ui/gfx/image/image_skia_util_mac.h"
11 TableRowNSImageCache::TableRowNSImageCache(Table* model)
12     : model_(model),
13       icon_images_([[NSPointerArray alloc] initWithOptions:
14           NSPointerFunctionsStrongMemory |
15           NSPointerFunctionsObjectPersonality]) {
16   int count = model_->RowCount();
17   [icon_images_ setCount:count];
20 TableRowNSImageCache::~TableRowNSImageCache() {}
22 void TableRowNSImageCache::OnModelChanged() {
23   int count = model_->RowCount();
24   [icon_images_ setCount:0];
25   [icon_images_ setCount:count];
28 void TableRowNSImageCache::OnItemsChanged(int start, int length) {
29   DCHECK_LE(start + length, static_cast<int>([icon_images_ count]));
30   for (int i = start; i < (start + length); ++i) {
31     [icon_images_ replacePointerAtIndex:i withPointer:NULL];
32   }
33   DCHECK_EQ(model_->RowCount(),
34             static_cast<int>([icon_images_ count]));
37 void TableRowNSImageCache::OnItemsAdded(int start, int length) {
38   DCHECK_LE(start, static_cast<int>([icon_images_ count]));
40   // -[NSPointerArray insertPointer:atIndex:] throws if index == count.
41   // Instead expand the array with NULLs.
42   if (start == static_cast<int>([icon_images_ count])) {
43     [icon_images_ setCount:start + length];
44   } else {
45     for (int i = 0; i < length; ++i) {
46       [icon_images_ insertPointer:NULL atIndex:start];  // Values slide up.
47     }
48   }
49   DCHECK_EQ(model_->RowCount(),
50             static_cast<int>([icon_images_ count]));
53 void TableRowNSImageCache::OnItemsRemoved(int start, int length) {
54   DCHECK_LE(start + length, static_cast<int>([icon_images_ count]));
55   for (int i = 0; i < length; ++i) {
56     [icon_images_ removePointerAtIndex:start];  // Values slide down.
57   }
58   DCHECK_EQ(model_->RowCount(),
59             static_cast<int>([icon_images_ count]));
62 NSImage* TableRowNSImageCache::GetImageForRow(int row) {
63   DCHECK_EQ(model_->RowCount(),
64             static_cast<int>([icon_images_ count]));
65   DCHECK_GE(row, 0);
66   DCHECK_LT(row, static_cast<int>([icon_images_ count]));
67   NSImage* image = static_cast<NSImage*>([icon_images_ pointerAtIndex:row]);
68   if (!image) {
69     const gfx::ImageSkia image_skia_icon =
70         model_->GetIcon(row);
71     // This means GetIcon() will get called until it returns a non-empty image.
72     // Empty images are intentionally not cached.
73     if (!image_skia_icon.isNull()) {
74       image = gfx::NSImageFromImageSkia(image_skia_icon);
75       DCHECK(image);
76       [icon_images_ replacePointerAtIndex:row withPointer:image];
77     }
78   }
79   return image;