OLD | NEW |
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 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 | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "content/browser/geolocation/geolocation_provider.h" | 5 #include "content/browser/geolocation/geolocation_provider.h" |
6 | 6 |
7 #include "base/bind.h" | 7 #include "base/bind.h" |
8 #include "base/bind_helpers.h" | 8 #include "base/bind_helpers.h" |
9 #include "base/memory/singleton.h" | 9 #include "base/memory/singleton.h" |
10 #include "base/threading/thread_restrictions.h" | 10 #include "base/threading/thread_restrictions.h" |
(...skipping 15 matching lines...) Expand all Loading... |
26 DCHECK(observers_.empty()); // observers must unregister. | 26 DCHECK(observers_.empty()); // observers must unregister. |
27 Stop(); | 27 Stop(); |
28 DCHECK(!arbitrator_); | 28 DCHECK(!arbitrator_); |
29 } | 29 } |
30 | 30 |
31 void GeolocationProvider::AddObserver(GeolocationObserver* observer, | 31 void GeolocationProvider::AddObserver(GeolocationObserver* observer, |
32 const GeolocationObserverOptions& update_options) { | 32 const GeolocationObserverOptions& update_options) { |
33 DCHECK(OnClientThread()); | 33 DCHECK(OnClientThread()); |
34 observers_[observer] = update_options; | 34 observers_[observer] = update_options; |
35 OnObserversChanged(); | 35 OnObserversChanged(); |
36 if (position_.IsInitialized()) | 36 if (position_.Validate() || |
| 37 position_.error_code != content::Geoposition::ERROR_CODE_NONE) |
37 observer->OnLocationUpdate(position_); | 38 observer->OnLocationUpdate(position_); |
38 } | 39 } |
39 | 40 |
40 bool GeolocationProvider::RemoveObserver(GeolocationObserver* observer) { | 41 bool GeolocationProvider::RemoveObserver(GeolocationObserver* observer) { |
41 DCHECK(OnClientThread()); | 42 DCHECK(OnClientThread()); |
42 size_t remove = observers_.erase(observer); | 43 size_t remove = observers_.erase(observer); |
43 OnObserversChanged(); | 44 OnObserversChanged(); |
44 return remove > 0; | 45 return remove > 0; |
45 } | 46 } |
46 | 47 |
(...skipping 13 matching lines...) Expand all Loading... |
60 | 61 |
61 // The high accuracy requirement may have changed. | 62 // The high accuracy requirement may have changed. |
62 task = base::Bind(&GeolocationProvider::StartProviders, | 63 task = base::Bind(&GeolocationProvider::StartProviders, |
63 base::Unretained(this), | 64 base::Unretained(this), |
64 GeolocationObserverOptions::Collapse(observers_)); | 65 GeolocationObserverOptions::Collapse(observers_)); |
65 } | 66 } |
66 | 67 |
67 message_loop()->PostTask(FROM_HERE, task); | 68 message_loop()->PostTask(FROM_HERE, task); |
68 } | 69 } |
69 | 70 |
70 void GeolocationProvider::NotifyObservers(const Geoposition& position) { | 71 void GeolocationProvider::NotifyObservers( |
| 72 const content::Geoposition& position) { |
71 DCHECK(OnClientThread()); | 73 DCHECK(OnClientThread()); |
72 DCHECK(position.IsInitialized()); | 74 DCHECK(position.Validate() || |
| 75 position.error_code != content::Geoposition::ERROR_CODE_NONE); |
73 position_ = position; | 76 position_ = position; |
74 ObserverMap::const_iterator it = observers_.begin(); | 77 ObserverMap::const_iterator it = observers_.begin(); |
75 while (it != observers_.end()) { | 78 while (it != observers_.end()) { |
76 // Advance iterator before callback to guard against synchronous unregister. | 79 // Advance iterator before callback to guard against synchronous unregister. |
77 GeolocationObserver* observer = it->first; | 80 GeolocationObserver* observer = it->first; |
78 ++it; | 81 ++it; |
79 observer->OnLocationUpdate(position_); | 82 observer->OnLocationUpdate(position_); |
80 } | 83 } |
81 } | 84 } |
82 | 85 |
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
119 DCHECK(!arbitrator_); | 122 DCHECK(!arbitrator_); |
120 arbitrator_ = GeolocationArbitrator::Create(this); | 123 arbitrator_ = GeolocationArbitrator::Create(this); |
121 } | 124 } |
122 | 125 |
123 void GeolocationProvider::CleanUp() { | 126 void GeolocationProvider::CleanUp() { |
124 DCHECK(OnGeolocationThread()); | 127 DCHECK(OnGeolocationThread()); |
125 delete arbitrator_; | 128 delete arbitrator_; |
126 arbitrator_ = NULL; | 129 arbitrator_ = NULL; |
127 } | 130 } |
128 | 131 |
129 void GeolocationProvider::OnLocationUpdate(const Geoposition& position) { | 132 void GeolocationProvider::OnLocationUpdate( |
| 133 const content::Geoposition& position) { |
130 DCHECK(OnGeolocationThread()); | 134 DCHECK(OnGeolocationThread()); |
131 // Will be true only in testing. | 135 // Will be true only in testing. |
132 if (ignore_location_updates_) | 136 if (ignore_location_updates_) |
133 return; | 137 return; |
134 client_loop_->PostTask( | 138 client_loop_->PostTask( |
135 FROM_HERE, | 139 FROM_HERE, |
136 base::Bind(&GeolocationProvider::NotifyObservers, | 140 base::Bind(&GeolocationProvider::NotifyObservers, |
137 base::Unretained(this), position)); | 141 base::Unretained(this), position)); |
138 } | 142 } |
139 | 143 |
140 void GeolocationProvider::OverrideLocationForTesting( | 144 void GeolocationProvider::OverrideLocationForTesting( |
141 const Geoposition& position) { | 145 const content::Geoposition& position) { |
142 DCHECK(OnClientThread()); | 146 DCHECK(OnClientThread()); |
143 position_ = position; | 147 position_ = position; |
144 ignore_location_updates_ = true; | 148 ignore_location_updates_ = true; |
145 NotifyObservers(position); | 149 NotifyObservers(position); |
146 } | 150 } |
147 | 151 |
148 bool GeolocationProvider::HasPermissionBeenGranted() const { | 152 bool GeolocationProvider::HasPermissionBeenGranted() const { |
149 DCHECK(OnClientThread()); | 153 DCHECK(OnClientThread()); |
150 return is_permission_granted_; | 154 return is_permission_granted_; |
151 } | 155 } |
152 | 156 |
153 bool GeolocationProvider::OnClientThread() const { | 157 bool GeolocationProvider::OnClientThread() const { |
154 return client_loop_->BelongsToCurrentThread(); | 158 return client_loop_->BelongsToCurrentThread(); |
155 } | 159 } |
156 | 160 |
157 bool GeolocationProvider::OnGeolocationThread() const { | 161 bool GeolocationProvider::OnGeolocationThread() const { |
158 return MessageLoop::current() == message_loop(); | 162 return MessageLoop::current() == message_loop(); |
159 } | 163 } |
OLD | NEW |