blob: 4b0c21bbd77373896abb599dc089688b8e69bf70 [file] [log] [blame]
license.botbf09a502008-08-24 00:55:551// Copyright (c) 2006-2008 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.
initial.commit09911bf2008-07-26 23:55:294
5#include "chrome/browser/icon_manager.h"
6
7#include "base/file_util.h"
8#include "base/scoped_ptr.h"
[email protected]807204142009-05-05 03:31:449#include "base/stl_util-inl.h"
initial.commit09911bf2008-07-26 23:55:2910#include "SkBitmap.h"
11#include "SkCanvas.h"
12
13IconManager::IconManager() {
14}
15
16IconManager::~IconManager() {
17 STLDeleteValues(&icon_cache_);
18}
19
[email protected]7ced67af2009-04-14 23:25:1620SkBitmap* IconManager::LookupIcon(const FilePath& file_name,
initial.commit09911bf2008-07-26 23:55:2921 IconLoader::IconSize size) {
[email protected]7ced67af2009-04-14 23:25:1622 FilePath path = file_name;
23 FilePath::StringType extension = file_util::GetFileExtensionFromPath(path);
24#if defined(OS_WIN)
initial.commit09911bf2008-07-26 23:55:2925 if (extension != L"exe" && extension != L"dll" && extension != L"ico")
[email protected]7ced67af2009-04-14 23:25:1626 path = FilePath(L'.' + extension);
27#endif
initial.commit09911bf2008-07-26 23:55:2928
29 IconMap::iterator it = icon_cache_.find(CacheKey(path, size));
30 if (it != icon_cache_.end())
31 return it->second;
32
33 return NULL;
34}
35
36IconManager::Handle IconManager::LoadIcon(
[email protected]7ced67af2009-04-14 23:25:1637 const FilePath& file_name,
initial.commit09911bf2008-07-26 23:55:2938 IconLoader::IconSize size,
39 CancelableRequestConsumerBase* consumer,
40 IconRequestCallback* callback) {
[email protected]7ced67af2009-04-14 23:25:1641 FilePath path = file_name;
42 FilePath::StringType extension = file_util::GetFileExtensionFromPath(path);
43#if defined(OS_WIN)
initial.commit09911bf2008-07-26 23:55:2944 if (extension != L"exe" && extension != L"dll" && extension != L"ico")
[email protected]7ced67af2009-04-14 23:25:1645 path = FilePath(L'.' + extension);
46#endif
initial.commit09911bf2008-07-26 23:55:2947
48 IconRequest* request = new IconRequest(callback);
49 AddRequest(request, consumer);
50
51 IconLoader* loader =
52 IconLoader::CreateIconLoaderForFileResource(path, size, this);
53 loader->Start();
54 ClientRequest client_request = { request, path, size };
55 requests_[loader] = client_request;
56 return request->handle();
57}
58
59// IconLoader::Delegate implementation -----------------------------------------
60
61bool IconManager::OnSkBitmapLoaded(IconLoader* source, SkBitmap* result) {
62 scoped_ptr<IconLoader> scoped_source(source);
63
64 // Look up our client state.
65 ClientRequests::iterator rit = requests_.find(source);
66 if (rit == requests_.end()) {
67 NOTREACHED();
[email protected]cf2ef752008-09-11 21:19:2968 return false; // Return false to indicate result should be deleted.
initial.commit09911bf2008-07-26 23:55:2969 }
70
71 ClientRequest client_request = rit->second;
72 if (client_request.request->canceled()) {
73 requests_.erase(rit);
[email protected]cf2ef752008-09-11 21:19:2974 return false; // Return false to indicate result should be deleted.
initial.commit09911bf2008-07-26 23:55:2975 }
76
[email protected]e79f10f32008-11-07 16:13:3177 // Cache the bitmap. Watch out: |result| or the cached bitmap may be NULL to
78 // indicate a current or past failure.
initial.commit09911bf2008-07-26 23:55:2979 CacheKey key(client_request.file_name, client_request.size);
80 IconMap::iterator it = icon_cache_.find(key);
[email protected]e79f10f32008-11-07 16:13:3181 if (it != icon_cache_.end() && result && it->second) {
initial.commit09911bf2008-07-26 23:55:2982 it->second->swap(*result);
83 delete result;
[email protected]cf2ef752008-09-11 21:19:2984 result = it->second;
initial.commit09911bf2008-07-26 23:55:2985 } else {
86 icon_cache_[key] = result;
87 }
88
89 // Inform our client that the request has completed.
90 IconRequest* icon_request = client_request.request;
91 icon_request->ForwardResult(IconRequest::TupleType(icon_request->handle(),
92 result));
93 requests_.erase(rit);
94
[email protected]cf2ef752008-09-11 21:19:2995 return true; // Indicates we took ownership of result.
initial.commit09911bf2008-07-26 23:55:2996}
97
[email protected]7ced67af2009-04-14 23:25:1698IconManager::CacheKey::CacheKey(const FilePath& file_name,
initial.commit09911bf2008-07-26 23:55:2999 IconLoader::IconSize size)
100 : file_name(file_name),
101 size(size) {
102}
103
104bool IconManager::CacheKey::operator<(const CacheKey &other) const {
105 if (file_name != other.file_name)
106 return file_name < other.file_name;
107 return size < other.size;
108}