OLD | NEW |
---|---|
1 // Copyright 2016 The Chromium Authors. All rights reserved. | 1 // Copyright 2016 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 "modules/sensor/Sensor.h" | 5 #include "modules/sensor/Sensor.h" |
6 | 6 |
7 #include "core/dom/Document.h" | 7 #include "core/dom/Document.h" |
8 #include "core/dom/ExceptionCode.h" | 8 #include "core/dom/ExceptionCode.h" |
9 #include "core/dom/ExecutionContextTask.h" | 9 #include "core/dom/ExecutionContextTask.h" |
10 #include "core/inspector/ConsoleMessage.h" | 10 #include "core/inspector/ConsoleMessage.h" |
11 #include "device/generic_sensor/public/interfaces/sensor.mojom-blink.h" | 11 #include "device/generic_sensor/public/interfaces/sensor.mojom-blink.h" |
12 #include "modules/sensor/SensorErrorEvent.h" | 12 #include "modules/sensor/SensorErrorEvent.h" |
13 #include "modules/sensor/SensorPollingStrategy.h" | |
14 #include "modules/sensor/SensorProviderProxy.h" | 13 #include "modules/sensor/SensorProviderProxy.h" |
15 #include "modules/sensor/SensorReading.h" | 14 #include "modules/sensor/SensorReading.h" |
15 #include "modules/sensor/SensorUpdateNotificationStrategy.h" | |
16 | 16 |
17 using namespace device::mojom::blink; | 17 using namespace device::mojom::blink; |
18 | 18 |
19 namespace blink { | 19 namespace blink { |
20 | 20 |
21 Sensor::Sensor(ScriptState* scriptState, | 21 Sensor::Sensor(ScriptState* scriptState, |
22 const SensorOptions& sensorOptions, | 22 const SensorOptions& sensorOptions, |
23 ExceptionState& exceptionState, | 23 ExceptionState& exceptionState, |
24 SensorType type) | 24 SensorType type) |
25 : ActiveScriptWrappable(this), | 25 : ActiveScriptWrappable(this), |
26 ContextLifecycleObserver(scriptState->getExecutionContext()), | 26 ContextLifecycleObserver(scriptState->getExecutionContext()), |
27 PageVisibilityObserver( | |
28 toDocument(scriptState->getExecutionContext())->page()), | |
29 m_sensorOptions(sensorOptions), | 27 m_sensorOptions(sensorOptions), |
30 m_type(type), | 28 m_type(type), |
31 m_state(Sensor::SensorState::Idle) { | 29 m_state(Sensor::SensorState::Idle) { |
32 // Check secure context. | 30 // Check secure context. |
33 String errorMessage; | 31 String errorMessage; |
34 if (!scriptState->getExecutionContext()->isSecureContext(errorMessage)) { | 32 if (!scriptState->getExecutionContext()->isSecureContext(errorMessage)) { |
35 exceptionState.throwDOMException(SecurityError, errorMessage); | 33 exceptionState.throwDOMException(SecurityError, errorMessage); |
36 return; | 34 return; |
37 } | 35 } |
38 | 36 |
(...skipping 81 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
120 if (m_state != Sensor::SensorState::Active) | 118 if (m_state != Sensor::SensorState::Active) |
121 return nullptr; | 119 return nullptr; |
122 DCHECK(m_sensorProxy); | 120 DCHECK(m_sensorProxy); |
123 return m_sensorProxy->sensorReading(); | 121 return m_sensorProxy->sensorReading(); |
124 } | 122 } |
125 | 123 |
126 DEFINE_TRACE(Sensor) { | 124 DEFINE_TRACE(Sensor) { |
127 visitor->trace(m_sensorProxy); | 125 visitor->trace(m_sensorProxy); |
128 ActiveScriptWrappable::trace(visitor); | 126 ActiveScriptWrappable::trace(visitor); |
129 ContextLifecycleObserver::trace(visitor); | 127 ContextLifecycleObserver::trace(visitor); |
130 PageVisibilityObserver::trace(visitor); | |
131 EventTargetWithInlineData::trace(visitor); | 128 EventTargetWithInlineData::trace(visitor); |
132 } | 129 } |
133 | 130 |
134 bool Sensor::hasPendingActivity() const { | 131 bool Sensor::hasPendingActivity() const { |
135 if (m_state == Sensor::SensorState::Idle || | 132 if (m_state == Sensor::SensorState::Idle || |
136 m_state == Sensor::SensorState::Errored) | 133 m_state == Sensor::SensorState::Errored) |
137 return false; | 134 return false; |
138 return hasEventListeners(); | 135 return hasEventListeners(); |
139 } | 136 } |
140 | 137 |
(...skipping 19 matching lines...) Expand all Loading... | |
160 return; | 157 return; |
161 | 158 |
162 Document* document = toDocument(getExecutionContext()); | 159 Document* document = toDocument(getExecutionContext()); |
163 if (!document || !document->frame()) | 160 if (!document || !document->frame()) |
164 return; | 161 return; |
165 | 162 |
166 auto provider = SensorProviderProxy::from(document->frame()); | 163 auto provider = SensorProviderProxy::from(document->frame()); |
167 m_sensorProxy = provider->getSensor(m_type); | 164 m_sensorProxy = provider->getSensor(m_type); |
168 | 165 |
169 if (!m_sensorProxy) { | 166 if (!m_sensorProxy) { |
167 Page* page = toDocument(getExecutionContext())->page(); | |
haraken
2016/11/16 04:31:47
toDocument(getExecutionContext()) => document
Mikhail
2016/11/17 17:07:35
Done.
| |
168 DCHECK(page); | |
170 m_sensorProxy = | 169 m_sensorProxy = |
171 provider->createSensor(m_type, createSensorReadingFactory()); | 170 provider->createSensor(m_type, page, createSensorReadingFactory()); |
172 } | 171 } |
173 } | 172 } |
174 | 173 |
175 void Sensor::contextDestroyed() { | 174 void Sensor::contextDestroyed() { |
176 if (m_state == Sensor::SensorState::Active || | 175 if (m_state == Sensor::SensorState::Active || |
177 m_state == Sensor::SensorState::Activating) | 176 m_state == Sensor::SensorState::Activating) |
178 stopListening(); | 177 stopListening(); |
179 } | 178 } |
180 | 179 |
181 void Sensor::onSensorInitialized() { | 180 void Sensor::onSensorInitialized() { |
182 if (m_state != Sensor::SensorState::Activating) | 181 if (m_state != Sensor::SensorState::Activating) |
183 return; | 182 return; |
184 | 183 |
185 startListening(); | 184 startListening(); |
186 } | 185 } |
187 | 186 |
188 void Sensor::onSensorReadingChanged() { | 187 void Sensor::onSensorReadingChanged() { |
189 if (m_polling) | 188 if (m_sensorUpdateNotifier && m_state == Sensor::SensorState::Active) |
190 m_polling->onSensorReadingChanged(); | 189 m_sensorUpdateNotifier->onSensorReadingChanged(); |
191 } | 190 } |
192 | 191 |
193 void Sensor::onSensorError(ExceptionCode code, | 192 void Sensor::onSensorError(ExceptionCode code, |
194 const String& sanitizedMessage, | 193 const String& sanitizedMessage, |
195 const String& unsanitizedMessage) { | 194 const String& unsanitizedMessage) { |
196 reportError(code, sanitizedMessage, unsanitizedMessage); | 195 reportError(code, sanitizedMessage, unsanitizedMessage); |
197 } | 196 } |
198 | 197 |
199 void Sensor::onStartRequestCompleted(bool result) { | 198 void Sensor::onStartRequestCompleted(bool result) { |
200 if (m_state != Sensor::SensorState::Activating) | 199 if (m_state != Sensor::SensorState::Activating) |
201 return; | 200 return; |
202 | 201 |
203 if (!result) { | 202 if (!result) { |
204 reportError( | 203 reportError( |
205 OperationError, | 204 OperationError, |
206 "start() call has failed possibly due to inappropriate options."); | 205 "start() call has failed possibly due to inappropriate options."); |
207 return; | 206 return; |
208 } | 207 } |
209 | 208 |
210 DCHECK(m_configuration); | 209 DCHECK(m_configuration); |
211 DCHECK(m_sensorProxy); | 210 DCHECK(m_sensorProxy); |
212 auto pollCallback = WTF::bind(&Sensor::pollForData, wrapWeakPersistent(this)); | 211 auto updateCallback = |
212 WTF::bind(&Sensor::onSensorUpdateNotification, wrapWeakPersistent(this)); | |
213 DCHECK_GT(m_configuration->frequency, 0); | 213 DCHECK_GT(m_configuration->frequency, 0); |
214 m_polling = SensorPollingStrategy::create(1 / m_configuration->frequency, | 214 m_sensorUpdateNotifier = SensorUpdateNotificationStrategy::create( |
215 std::move(pollCallback), | 215 m_configuration->frequency, std::move(updateCallback)); |
216 m_sensorProxy->reportingMode()); | |
217 updateState(Sensor::SensorState::Active); | 216 updateState(Sensor::SensorState::Active); |
218 } | 217 } |
219 | 218 |
220 void Sensor::onStopRequestCompleted(bool result) { | |
221 if (m_state == Sensor::SensorState::Idle) | |
222 return; | |
223 | |
224 if (!result) | |
225 reportError(OperationError); | |
226 | |
227 DCHECK(m_sensorProxy); | |
228 m_sensorProxy->removeObserver(this); | |
229 } | |
230 | |
231 void Sensor::pageVisibilityChanged() { | |
232 updatePollingStatus(); | |
233 | |
234 if (!m_sensorProxy || !m_sensorProxy->isInitialized()) | |
235 return; | |
236 | |
237 if (page()->visibilityState() != PageVisibilityStateVisible) { | |
238 m_sensorProxy->suspend(); | |
239 } else { | |
240 m_sensorProxy->resume(); | |
241 } | |
242 } | |
243 | |
244 void Sensor::startListening() { | 219 void Sensor::startListening() { |
245 DCHECK(m_sensorProxy); | 220 DCHECK(m_sensorProxy); |
246 updateState(Sensor::SensorState::Activating); | 221 updateState(Sensor::SensorState::Activating); |
247 | 222 |
248 m_sensorProxy->addObserver(this); | 223 m_sensorProxy->addObserver(this); |
249 if (!m_sensorProxy->isInitialized()) { | 224 if (!m_sensorProxy->isInitialized()) { |
250 m_sensorProxy->initialize(); | 225 m_sensorProxy->initialize(); |
251 return; | 226 return; |
252 } | 227 } |
253 | 228 |
254 if (!m_configuration) { | 229 if (!m_configuration) { |
255 m_configuration = createSensorConfig(); | 230 m_configuration = createSensorConfig(); |
256 DCHECK(m_configuration); | 231 DCHECK(m_configuration); |
257 DCHECK(m_configuration->frequency > 0 && | 232 DCHECK(m_configuration->frequency > 0 && |
258 m_configuration->frequency <= m_sensorProxy->maximumFrequency()); | 233 m_configuration->frequency <= m_sensorProxy->maximumFrequency()); |
259 } | 234 } |
260 | 235 |
261 auto startCallback = | 236 auto startCallback = |
262 WTF::bind(&Sensor::onStartRequestCompleted, wrapWeakPersistent(this)); | 237 WTF::bind(&Sensor::onStartRequestCompleted, wrapWeakPersistent(this)); |
263 m_sensorProxy->addConfiguration(m_configuration->Clone(), | 238 m_sensorProxy->addConfiguration(m_configuration->Clone(), |
264 std::move(startCallback)); | 239 std::move(startCallback)); |
265 } | 240 } |
266 | 241 |
267 void Sensor::stopListening() { | 242 void Sensor::stopListening() { |
268 DCHECK(m_sensorProxy); | 243 DCHECK(m_sensorProxy); |
269 updateState(Sensor::SensorState::Idle); | 244 updateState(Sensor::SensorState::Idle); |
270 | 245 |
271 if (m_sensorProxy->isInitialized()) { | 246 if (m_sensorProxy->isInitialized()) { |
272 auto callback = | |
273 WTF::bind(&Sensor::onStopRequestCompleted, wrapWeakPersistent(this)); | |
274 DCHECK(m_configuration); | 247 DCHECK(m_configuration); |
275 m_sensorProxy->removeConfiguration(m_configuration->Clone(), | 248 m_sensorProxy->removeConfiguration(m_configuration->Clone()); |
276 std::move(callback)); | |
277 } else { | |
278 m_sensorProxy->removeObserver(this); | |
279 } | 249 } |
250 m_sensorProxy->removeObserver(this); | |
280 } | 251 } |
281 | 252 |
282 void Sensor::pollForData() { | 253 void Sensor::onSensorUpdateNotification() { |
283 if (m_state != Sensor::SensorState::Active) { | 254 if (m_state != Sensor::SensorState::Active) |
284 DCHECK(m_polling); | |
285 m_polling->stopPolling(); | |
286 return; | 255 return; |
287 } | |
288 | 256 |
289 DCHECK(m_sensorProxy); | 257 DCHECK(m_sensorProxy); |
290 DCHECK(m_sensorProxy->isInitialized()); | 258 DCHECK(m_sensorProxy->isInitialized()); |
291 m_sensorProxy->updateSensorReading(); | 259 DCHECK(m_sensorProxy->sensorReading()); |
292 | 260 |
293 DCHECK(m_sensorProxy->sensorReading()); | |
294 if (getExecutionContext() && | 261 if (getExecutionContext() && |
295 m_sensorProxy->sensorReading()->isReadingUpdated(m_storedData)) { | 262 m_sensorProxy->sensorReading()->isReadingUpdated(m_storedData)) { |
296 getExecutionContext()->postTask( | 263 getExecutionContext()->postTask( |
297 BLINK_FROM_HERE, | 264 BLINK_FROM_HERE, |
298 createSameThreadTask(&Sensor::notifySensorReadingChanged, | 265 createSameThreadTask(&Sensor::notifySensorReadingChanged, |
299 wrapWeakPersistent(this))); | 266 wrapWeakPersistent(this))); |
300 } | 267 } |
301 | 268 |
302 m_storedData = m_sensorProxy->sensorReading()->data(); | 269 m_storedData = m_sensorProxy->sensorReading()->data(); |
303 } | 270 } |
304 | 271 |
305 void Sensor::updateState(Sensor::SensorState newState) { | 272 void Sensor::updateState(Sensor::SensorState newState) { |
306 if (newState == m_state) | 273 if (newState == m_state) |
307 return; | 274 return; |
308 | 275 |
309 if (newState == SensorState::Active && getExecutionContext()) { | 276 if (newState == SensorState::Active && getExecutionContext()) { |
310 DCHECK_EQ(SensorState::Activating, m_state); | 277 DCHECK_EQ(SensorState::Activating, m_state); |
311 getExecutionContext()->postTask( | 278 getExecutionContext()->postTask( |
312 BLINK_FROM_HERE, createSameThreadTask(&Sensor::notifyOnActivate, | 279 BLINK_FROM_HERE, createSameThreadTask(&Sensor::notifyOnActivate, |
313 wrapWeakPersistent(this))); | 280 wrapWeakPersistent(this))); |
314 } | 281 } |
315 | 282 |
316 m_state = newState; | 283 m_state = newState; |
317 updatePollingStatus(); | |
318 } | 284 } |
319 | 285 |
320 void Sensor::reportError(ExceptionCode code, | 286 void Sensor::reportError(ExceptionCode code, |
321 const String& sanitizedMessage, | 287 const String& sanitizedMessage, |
322 const String& unsanitizedMessage) { | 288 const String& unsanitizedMessage) { |
323 updateState(Sensor::SensorState::Errored); | 289 updateState(Sensor::SensorState::Errored); |
324 if (getExecutionContext()) { | 290 if (getExecutionContext()) { |
325 auto error = | 291 auto error = |
326 DOMException::create(code, sanitizedMessage, unsanitizedMessage); | 292 DOMException::create(code, sanitizedMessage, unsanitizedMessage); |
327 getExecutionContext()->postTask( | 293 getExecutionContext()->postTask( |
328 BLINK_FROM_HERE, | 294 BLINK_FROM_HERE, |
329 createSameThreadTask(&Sensor::notifyError, wrapWeakPersistent(this), | 295 createSameThreadTask(&Sensor::notifyError, wrapWeakPersistent(this), |
330 wrapPersistent(error))); | 296 wrapPersistent(error))); |
331 } | 297 } |
332 } | 298 } |
333 | 299 |
334 void Sensor::updatePollingStatus() { | 300 void Sensor::onSuspended() { |
335 if (!m_polling) | 301 if (m_sensorUpdateNotifier) |
336 return; | 302 m_sensorUpdateNotifier->cancelPendingNotifications(); |
337 | |
338 if (m_state != Sensor::SensorState::Active || | |
339 page()->visibilityState() != PageVisibilityStateVisible) { | |
340 m_polling->stopPolling(); | |
341 } else { | |
342 m_polling->startPolling(); | |
343 } | |
344 } | 303 } |
345 | 304 |
346 void Sensor::notifySensorReadingChanged() { | 305 void Sensor::notifySensorReadingChanged() { |
347 dispatchEvent(Event::create(EventTypeNames::change)); | 306 dispatchEvent(Event::create(EventTypeNames::change)); |
348 } | 307 } |
349 | 308 |
350 void Sensor::notifyOnActivate() { | 309 void Sensor::notifyOnActivate() { |
351 dispatchEvent(Event::create(EventTypeNames::activate)); | 310 dispatchEvent(Event::create(EventTypeNames::activate)); |
352 } | 311 } |
353 | 312 |
354 void Sensor::notifyError(DOMException* error) { | 313 void Sensor::notifyError(DOMException* error) { |
355 dispatchEvent( | 314 dispatchEvent( |
356 SensorErrorEvent::create(EventTypeNames::error, std::move(error))); | 315 SensorErrorEvent::create(EventTypeNames::error, std::move(error))); |
357 } | 316 } |
358 | 317 |
359 } // namespace blink | 318 } // namespace blink |
OLD | NEW |