Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(308)

Side by Side Diff: content/browser/geolocation/geolocation_provider.cc

Issue 6597044: Revert 76228 - Move core pieces of geolocation from chrome to content.This is... (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src/
Patch Set: Created 9 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
(Empty)
1 // Copyright (c) 2010 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.
4
5 #include "content/browser/geolocation/geolocation_provider.h"
6
7 #include "base/singleton.h"
8 #include "base/threading/thread_restrictions.h"
9 #include "content/browser/geolocation/location_arbitrator.h"
10
11 // This class is guaranteed to outlive its internal thread, so ref counting
12 // is not required.
13 DISABLE_RUNNABLE_METHOD_REFCOUNT(GeolocationProvider);
14
15 GeolocationProvider* GeolocationProvider::GetInstance() {
16 return Singleton<GeolocationProvider>::get();
17 }
18
19 GeolocationProvider::GeolocationProvider()
20 : base::Thread("Geolocation"),
21 client_loop_(base::MessageLoopProxy::CreateForCurrentThread()),
22 arbitrator_(NULL) {
23 }
24
25 GeolocationProvider::~GeolocationProvider() {
26 DCHECK(observers_.empty()); // observers must unregister.
27 Stop();
28 DCHECK(!arbitrator_);
29 }
30
31 void GeolocationProvider::AddObserver(GeolocationObserver* observer,
32 const GeolocationObserverOptions& update_options) {
33 DCHECK(OnClientThread());
34 observers_[observer] = update_options;
35 OnObserversChanged();
36 if (position_.IsInitialized())
37 observer->OnLocationUpdate(position_);
38 }
39
40 bool GeolocationProvider::RemoveObserver(GeolocationObserver* observer) {
41 DCHECK(OnClientThread());
42 size_t remove = observers_.erase(observer);
43 OnObserversChanged();
44 return remove > 0;
45 }
46
47 void GeolocationProvider::OnObserversChanged() {
48 DCHECK(OnClientThread());
49 Task* task = NULL;
50 if (observers_.empty()) {
51 DCHECK(IsRunning());
52 task = NewRunnableMethod(this, &GeolocationProvider::StopProviders);
53 } else {
54 if (!IsRunning()) {
55 Start();
56 if (HasPermissionBeenGranted())
57 InformProvidersPermissionGranted(most_recent_authorized_frame_);
58 }
59 // The high accuracy requirement may have changed.
60 task = NewRunnableMethod(
61 this,
62 &GeolocationProvider::StartProviders,
63 GeolocationObserverOptions::Collapse(observers_));
64 }
65 message_loop()->PostTask(FROM_HERE, task);
66 }
67
68 void GeolocationProvider::NotifyObservers(const Geoposition& position) {
69 DCHECK(OnClientThread());
70 DCHECK(position.IsInitialized());
71 position_ = position;
72 ObserverMap::const_iterator it = observers_.begin();
73 while (it != observers_.end()) {
74 // Advance iterator before callback to guard against synchronous unregister.
75 GeolocationObserver* observer = it->first;
76 ++it;
77 observer->OnLocationUpdate(position_);
78 }
79 }
80
81 void GeolocationProvider::StartProviders(
82 const GeolocationObserverOptions& options) {
83 DCHECK(OnGeolocationThread());
84 DCHECK(arbitrator_);
85 arbitrator_->StartProviders(options);
86 }
87
88 void GeolocationProvider::StopProviders() {
89 DCHECK(OnGeolocationThread());
90 DCHECK(arbitrator_);
91 arbitrator_->StopProviders();
92 }
93
94 void GeolocationProvider::OnPermissionGranted(const GURL& requesting_frame) {
95 DCHECK(OnClientThread());
96 most_recent_authorized_frame_ = requesting_frame;
97 if (IsRunning())
98 InformProvidersPermissionGranted(requesting_frame);
99 }
100
101 void GeolocationProvider::InformProvidersPermissionGranted(
102 const GURL& requesting_frame) {
103 DCHECK(IsRunning());
104 DCHECK(requesting_frame.is_valid());
105 if (!OnGeolocationThread()) {
106 Task* task = NewRunnableMethod(
107 this,
108 &GeolocationProvider::InformProvidersPermissionGranted,
109 requesting_frame);
110 message_loop()->PostTask(FROM_HERE, task);
111 return;
112 }
113 DCHECK(OnGeolocationThread());
114 DCHECK(arbitrator_);
115 arbitrator_->OnPermissionGranted(requesting_frame);
116 }
117
118 void GeolocationProvider::Init() {
119 DCHECK(OnGeolocationThread());
120 DCHECK(!arbitrator_);
121 arbitrator_ = GeolocationArbitrator::Create(this);
122 }
123
124 void GeolocationProvider::CleanUp() {
125 DCHECK(OnGeolocationThread());
126 delete arbitrator_;
127 arbitrator_ = NULL;
128 }
129
130 void GeolocationProvider::OnLocationUpdate(const Geoposition& position) {
131 DCHECK(OnGeolocationThread());
132 Task* task = NewRunnableMethod(this,
133 &GeolocationProvider::NotifyObservers,
134 position);
135 client_loop_->PostTask(FROM_HERE, task);
136 }
137
138 bool GeolocationProvider::HasPermissionBeenGranted() const {
139 DCHECK(OnClientThread());
140 return most_recent_authorized_frame_.is_valid();
141 }
142
143 bool GeolocationProvider::OnClientThread() const {
144 return client_loop_->BelongsToCurrentThread();
145 }
146
147 bool GeolocationProvider::OnGeolocationThread() const {
148 return MessageLoop::current() == message_loop();
149 }
OLDNEW
« no previous file with comments | « content/browser/geolocation/geolocation_provider.h ('k') | content/browser/geolocation/geolocation_provider_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698