blob: ad7097792ee1ffee2853c5bfd42994899e739ca7 [file] [log] [blame]
[email protected]9f76c1e2012-03-05 15:15:581// Copyright (c) 2012 The Chromium Authors. All rights reserved.
[email protected]40bd6582009-12-04 23:49:512// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
[email protected]5c9250872012-01-30 17:24:055#include "content/browser/host_zoom_map_impl.h"
[email protected]40bd6582009-12-04 23:49:516
[email protected]b9e7c479f2013-04-12 04:33:247#include <cmath>
8
9#include "base/strings/string_piece.h"
[email protected]40bd6582009-12-04 23:49:5110#include "base/utf_string_conversions.h"
[email protected]d407cc02011-09-13 16:01:4611#include "base/values.h"
[email protected]f3b1a082011-11-18 00:34:3012#include "content/browser/renderer_host/render_process_host_impl.h"
[email protected]b3c41c0b2012-03-06 15:48:3213#include "content/browser/renderer_host/render_view_host_impl.h"
[email protected]4e2a25a2012-01-27 00:42:0814#include "content/common/view_messages.h"
15#include "content/public/browser/browser_context.h"
[email protected]c38831a12011-10-28 12:44:4916#include "content/public/browser/browser_thread.h"
[email protected]ad50def52011-10-19 23:17:0717#include "content/public/browser/notification_service.h"
[email protected]0d6e9bd2011-10-18 04:29:1618#include "content/public/browser/notification_types.h"
[email protected]5fe3713a2012-02-22 08:31:5619#include "content/public/browser/resource_context.h"
[email protected]0f083402011-11-22 02:59:0120#include "content/public/common/page_zoom.h"
[email protected]9d797f32010-04-23 07:17:5421#include "googleurl/src/gurl.h"
22#include "net/base/net_util.h"
[email protected]8bd0fe62011-01-17 06:44:3723#include "third_party/WebKit/Source/WebKit/chromium/public/WebView.h"
[email protected]b75b8292010-10-01 07:28:2524
25using WebKit::WebView;
[email protected]40bd6582009-12-04 23:49:5126
[email protected]5fe3713a2012-02-22 08:31:5627static const char* kHostZoomMapKeyName = "content_host_zoom_map";
28
[email protected]5c9250872012-01-30 17:24:0529namespace content {
30
[email protected]5fe3713a2012-02-22 08:31:5631HostZoomMap* HostZoomMap::GetForBrowserContext(BrowserContext* context) {
32 HostZoomMapImpl* rv = static_cast<HostZoomMapImpl*>(
33 context->GetUserData(kHostZoomMapKeyName));
34 if (!rv) {
35 rv = new HostZoomMapImpl();
36 context->SetUserData(kHostZoomMapKeyName, rv);
37 }
38 return rv;
[email protected]5c9250872012-01-30 17:24:0539}
40
[email protected]5c9250872012-01-30 17:24:0541HostZoomMapImpl::HostZoomMapImpl()
[email protected]4e2a25a2012-01-27 00:42:0842 : default_zoom_level_(0.0) {
[email protected]b75b8292010-10-01 07:28:2543 registrar_.Add(
[email protected]46488322012-10-30 03:22:2044 this, NOTIFICATION_RENDER_VIEW_HOST_WILL_CLOSE_RENDER_VIEW,
45 NotificationService::AllSources());
[email protected]40bd6582009-12-04 23:49:5146}
47
[email protected]5c9250872012-01-30 17:24:0548void HostZoomMapImpl::CopyFrom(HostZoomMap* copy_interface) {
[email protected]4e2a25a2012-01-27 00:42:0849 // This can only be called on the UI thread to avoid deadlocks, otherwise
50 // UI: a.CopyFrom(b);
51 // IO: b.CopyFrom(a);
52 // can deadlock.
53 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
[email protected]5c9250872012-01-30 17:24:0554 HostZoomMapImpl* copy = static_cast<HostZoomMapImpl*>(copy_interface);
[email protected]4e2a25a2012-01-27 00:42:0855 base::AutoLock auto_lock(lock_);
56 base::AutoLock copy_auto_lock(copy->lock_);
[email protected]367c5c1d2013-03-11 18:59:0257 host_zoom_levels_.
58 insert(copy->host_zoom_levels_.begin(), copy->host_zoom_levels_.end());
59 for (SchemeHostZoomLevels::const_iterator i(copy->
60 scheme_host_zoom_levels_.begin());
61 i != copy->scheme_host_zoom_levels_.end(); ++i) {
62 scheme_host_zoom_levels_[i->first] = HostZoomLevels();
63 scheme_host_zoom_levels_[i->first].
64 insert(i->second.begin(), i->second.end());
[email protected]4e2a25a2012-01-27 00:42:0865 }
[email protected]19d26692013-01-12 19:56:3366 default_zoom_level_ = copy->default_zoom_level_;
[email protected]4e2a25a2012-01-27 00:42:0867}
68
[email protected]367c5c1d2013-03-11 18:59:0269double HostZoomMapImpl::GetZoomLevelForHost(const std::string& host) const {
[email protected]20305ec2011-01-21 04:55:5270 base::AutoLock auto_lock(lock_);
[email protected]40bd6582009-12-04 23:49:5171 HostZoomLevels::const_iterator i(host_zoom_levels_.find(host));
[email protected]d0b8d092010-10-25 04:05:1772 return (i == host_zoom_levels_.end()) ? default_zoom_level_ : i->second;
[email protected]40bd6582009-12-04 23:49:5173}
74
[email protected]367c5c1d2013-03-11 18:59:0275double HostZoomMapImpl::GetZoomLevelForHostAndScheme(
76 const std::string& scheme,
77 const std::string& host) const {
78 {
79 base::AutoLock auto_lock(lock_);
80 SchemeHostZoomLevels::const_iterator scheme_iterator(
81 scheme_host_zoom_levels_.find(scheme));
82 if (scheme_iterator != scheme_host_zoom_levels_.end()) {
83 HostZoomLevels::const_iterator i(scheme_iterator->second.find(host));
84 if (i != scheme_iterator->second.end())
85 return i->second;
86 }
87 }
88 return GetZoomLevelForHost(host);
89}
90
91void HostZoomMapImpl::SetZoomLevelForHost(const std::string& host,
92 double level) {
[email protected]f8b3ef82010-10-11 02:45:5293 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
[email protected]3ef4bc632010-04-09 04:25:3194
[email protected]40bd6582009-12-04 23:49:5195 {
[email protected]20305ec2011-01-21 04:55:5296 base::AutoLock auto_lock(lock_);
[email protected]0f083402011-11-22 02:59:0197
[email protected]46488322012-10-30 03:22:2098 if (ZoomValuesEqual(level, default_zoom_level_))
[email protected]40bd6582009-12-04 23:49:5199 host_zoom_levels_.erase(host);
100 else
101 host_zoom_levels_[host] = level;
102 }
103
[email protected]4e2a25a2012-01-27 00:42:08104 // Notify renderers from this browser context.
105 for (RenderProcessHost::iterator i(RenderProcessHost::AllHostsIterator());
106 !i.IsAtEnd(); i.Advance()) {
107 RenderProcessHost* render_process_host = i.GetCurrentValue();
[email protected]5fe3713a2012-02-22 08:31:56108 if (HostZoomMap::GetForBrowserContext(
109 render_process_host->GetBrowserContext()) == this) {
[email protected]4e2a25a2012-01-27 00:42:08110 render_process_host->Send(
[email protected]367c5c1d2013-03-11 18:59:02111 new ViewMsg_SetZoomLevelForCurrentURL(std::string(), host, level));
112 }
113 }
114 HostZoomMap::ZoomLevelChange change;
115 change.mode = HostZoomMap::ZOOM_CHANGED_FOR_HOST;
116 change.host = host;
117 change.zoom_level = level;
118
119 for (size_t i = 0; i < zoom_level_changed_callbacks_.size(); i++)
120 zoom_level_changed_callbacks_[i].Run(change);
121}
122
123void HostZoomMapImpl::SetZoomLevelForHostAndScheme(const std::string& scheme,
124 const std::string& host,
125 double level) {
126 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
127 {
128 base::AutoLock auto_lock(lock_);
129 scheme_host_zoom_levels_[scheme][host] = level;
130 }
131
132 // Notify renderers from this browser context.
133 for (RenderProcessHost::iterator i(RenderProcessHost::AllHostsIterator());
134 !i.IsAtEnd(); i.Advance()) {
135 RenderProcessHost* render_process_host = i.GetCurrentValue();
136 if (HostZoomMap::GetForBrowserContext(
137 render_process_host->GetBrowserContext()) == this) {
138 render_process_host->Send(
139 new ViewMsg_SetZoomLevelForCurrentURL(scheme, host, level));
[email protected]4e2a25a2012-01-27 00:42:08140 }
141 }
142
[email protected]367c5c1d2013-03-11 18:59:02143 HostZoomMap::ZoomLevelChange change;
144 change.mode = HostZoomMap::ZOOM_CHANGED_FOR_SCHEME_AND_HOST;
145 change.host = host;
146 change.scheme = scheme;
147 change.zoom_level = level;
148
[email protected]89c9aca2013-02-07 15:08:42149 for (size_t i = 0; i < zoom_level_changed_callbacks_.size(); i++)
[email protected]367c5c1d2013-03-11 18:59:02150 zoom_level_changed_callbacks_[i].Run(change);
[email protected]40bd6582009-12-04 23:49:51151}
152
[email protected]5c9250872012-01-30 17:24:05153double HostZoomMapImpl::GetDefaultZoomLevel() const {
154 return default_zoom_level_;
155}
156
157void HostZoomMapImpl::SetDefaultZoomLevel(double level) {
158 default_zoom_level_ = level;
159}
160
[email protected]89c9aca2013-02-07 15:08:42161void HostZoomMapImpl::AddZoomLevelChangedCallback(
162 const ZoomLevelChangedCallback& callback) {
163 zoom_level_changed_callbacks_.push_back(callback);
164}
165
166void HostZoomMapImpl::RemoveZoomLevelChangedCallback(
167 const ZoomLevelChangedCallback& callback) {
168 for (size_t i = 0; i < zoom_level_changed_callbacks_.size(); i++) {
169 if (zoom_level_changed_callbacks_[i].Equals(callback)) {
170 zoom_level_changed_callbacks_.erase(
171 zoom_level_changed_callbacks_.begin() + i);
172 return;
173 }
174 }
175}
176
[email protected]5c9250872012-01-30 17:24:05177double HostZoomMapImpl::GetTemporaryZoomLevel(int render_process_id,
178 int render_view_id) const {
[email protected]20305ec2011-01-21 04:55:52179 base::AutoLock auto_lock(lock_);
[email protected]b75b8292010-10-01 07:28:25180 for (size_t i = 0; i < temporary_zoom_levels_.size(); ++i) {
181 if (temporary_zoom_levels_[i].render_process_id == render_process_id &&
182 temporary_zoom_levels_[i].render_view_id == render_view_id) {
183 return temporary_zoom_levels_[i].zoom_level;
184 }
185 }
186 return 0;
187}
188
[email protected]5c9250872012-01-30 17:24:05189void HostZoomMapImpl::SetTemporaryZoomLevel(int render_process_id,
190 int render_view_id,
191 double level) {
[email protected]f8b3ef82010-10-11 02:45:52192 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
[email protected]b75b8292010-10-01 07:28:25193
194 {
[email protected]20305ec2011-01-21 04:55:52195 base::AutoLock auto_lock(lock_);
[email protected]b75b8292010-10-01 07:28:25196 size_t i;
197 for (i = 0; i < temporary_zoom_levels_.size(); ++i) {
198 if (temporary_zoom_levels_[i].render_process_id == render_process_id &&
199 temporary_zoom_levels_[i].render_view_id == render_view_id) {
200 if (level) {
201 temporary_zoom_levels_[i].zoom_level = level;
202 } else {
203 temporary_zoom_levels_.erase(temporary_zoom_levels_.begin() + i);
204 }
205 break;
206 }
207 }
208
209 if (level && i == temporary_zoom_levels_.size()) {
210 TemporaryZoomLevel temp;
211 temp.render_process_id = render_process_id;
212 temp.render_view_id = render_view_id;
213 temp.zoom_level = level;
214 temporary_zoom_levels_.push_back(temp);
215 }
216 }
217
[email protected]367c5c1d2013-03-11 18:59:02218 HostZoomMap::ZoomLevelChange change;
219 change.mode = HostZoomMap::ZOOM_CHANGED_TEMPORARY_ZOOM;
220 change.zoom_level = level;
221
[email protected]89c9aca2013-02-07 15:08:42222 for (size_t i = 0; i < zoom_level_changed_callbacks_.size(); i++)
[email protected]367c5c1d2013-03-11 18:59:02223 zoom_level_changed_callbacks_[i].Run(change);
[email protected]b75b8292010-10-01 07:28:25224}
225
[email protected]46488322012-10-30 03:22:20226void HostZoomMapImpl::Observe(int type,
227 const NotificationSource& source,
228 const NotificationDetails& details) {
[email protected]432115822011-07-10 15:52:27229 switch (type) {
[email protected]46488322012-10-30 03:22:20230 case NOTIFICATION_RENDER_VIEW_HOST_WILL_CLOSE_RENDER_VIEW: {
[email protected]20305ec2011-01-21 04:55:52231 base::AutoLock auto_lock(lock_);
[email protected]46488322012-10-30 03:22:20232 int render_view_id = Source<RenderViewHost>(source)->GetRoutingID();
[email protected]6c2381d2011-10-19 02:52:53233 int render_process_id =
[email protected]46488322012-10-30 03:22:20234 Source<RenderViewHost>(source)->GetProcess()->GetID();
[email protected]3ef4bc632010-04-09 04:25:31235
[email protected]b75b8292010-10-01 07:28:25236 for (size_t i = 0; i < temporary_zoom_levels_.size(); ++i) {
237 if (temporary_zoom_levels_[i].render_process_id == render_process_id &&
238 temporary_zoom_levels_[i].render_view_id == render_view_id) {
239 temporary_zoom_levels_.erase(temporary_zoom_levels_.begin() + i);
240 break;
241 }
242 }
243 break;
[email protected]3ef4bc632010-04-09 04:25:31244 }
[email protected]b75b8292010-10-01 07:28:25245 default:
246 NOTREACHED() << "Unexpected preference observed.";
[email protected]3ef4bc632010-04-09 04:25:31247 }
[email protected]779c3362010-01-30 01:09:33248}
249
[email protected]5c9250872012-01-30 17:24:05250HostZoomMapImpl::~HostZoomMapImpl() {
[email protected]40bd6582009-12-04 23:49:51251}
[email protected]46488322012-10-30 03:22:20252
253} // namespace content