 Chromium Code Reviews
 Chromium Code Reviews Issue 10755002:
  Refactors DeviceOrientation to make it more extensible  (Closed) 
  Base URL: http://git.chromium.org/chromium/src.git@master
    
  
    Issue 10755002:
  Refactors DeviceOrientation to make it more extensible  (Closed) 
  Base URL: http://git.chromium.org/chromium/src.git@master| 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/device_orientation/accelerometer_mac.h" | 5 #include "content/browser/device_orientation/accelerometer_mac.h" | 
| 6 | 6 | 
| 7 #include <math.h> | 7 #include <math.h> | 
| 8 | 8 | 
| 9 #include "base/logging.h" | 9 #include "base/logging.h" | 
| 10 #include "content/browser/device_orientation/orientation.h" | 10 #include "content/browser/device_orientation/orientation.h" | 
| 11 #include "third_party/sudden_motion_sensor/sudden_motion_sensor_mac.h" | 11 #include "third_party/sudden_motion_sensor/sudden_motion_sensor_mac.h" | 
| 12 | 12 | 
| 13 namespace device_orientation { | 13 namespace device_orientation { | 
| 14 | 14 | 
| 15 // Create a AccelerometerMac object and return NULL if no valid sensor found. | 15 // Create a AccelerometerMac object and return NULL if no valid sensor found. | 
| 16 DataFetcher* AccelerometerMac::Create() { | 16 DataFetcher* AccelerometerMac::Create() { | 
| 17 scoped_ptr<AccelerometerMac> accelerometer(new AccelerometerMac); | 17 scoped_ptr<AccelerometerMac> accelerometer(new AccelerometerMac); | 
| 18 return accelerometer->Init() ? accelerometer.release() : NULL; | 18 return accelerometer->Init() ? accelerometer.release() : NULL; | 
| 19 } | 19 } | 
| 20 | 20 | 
| 21 AccelerometerMac::~AccelerometerMac() { | 21 AccelerometerMac::~AccelerometerMac() { | 
| 22 } | 22 } | 
| 23 | 23 | 
| 24 AccelerometerMac::AccelerometerMac() { | 24 AccelerometerMac::AccelerometerMac() { | 
| 25 } | 25 } | 
| 26 | 26 | 
| 27 DeviceData* AccelerometerMac::GetDeviceData( | |
| 28 DeviceData::DeviceDataType device_data_type) { | |
| 29 switch (device_data_type()) { | |
| 
bulach
2012/07/12 10:43:27
nit: since this is not expected to grow, it'd be c
 
aousterh
2012/07/12 17:13:57
Done.
 | |
| 30 case DeviceData::kDeviceOrientationData: | |
| 31 return GetOrientation(); | |
| 32 default: | |
| 33 return NULL; | |
| 34 } | |
| 35 } | |
| 36 | |
| 27 // Retrieve per-axis orientation values. | 37 // Retrieve per-axis orientation values. | 
| 28 // | 38 // | 
| 29 // Axes and angles are defined according to the W3C DeviceOrientation Draft. | 39 // Axes and angles are defined according to the W3C DeviceOrientation Draft. | 
| 30 // See here: http://dev.w3.org/geo/api/spec-source-orientation.html | 40 // See here: http://dev.w3.org/geo/api/spec-source-orientation.html | 
| 31 // | 41 // | 
| 32 // Note: only beta and gamma angles are provided. Alpha is set to zero. | 42 // Note: only beta and gamma angles are provided. Alpha is set to zero. | 
| 33 // | 43 // | 
| 34 // Returns false in case of error. | 44 // Returns false in case of error. | 
| 35 // | 45 // | 
| 36 bool AccelerometerMac::GetOrientation(Orientation* orientation) { | 46 Orientation* AccelerometerMac::GetOrientation() { | 
| 37 DCHECK(sudden_motion_sensor_.get()); | 47 DCHECK(sudden_motion_sensor_.get()); | 
| 38 | 48 | 
| 39 // Retrieve per-axis calibrated values. | 49 // Retrieve per-axis calibrated values. | 
| 40 float axis_value[3]; | 50 float axis_value[3]; | 
| 41 if (!sudden_motion_sensor_->ReadSensorValues(axis_value)) | 51 if (!sudden_motion_sensor_->ReadSensorValues(axis_value)) | 
| 42 return false; | 52 return NULL; | 
| 43 | 53 | 
| 44 // Transform the accelerometer values to W3C draft angles. | 54 // Transform the accelerometer values to W3C draft angles. | 
| 45 // | 55 // | 
| 46 // Accelerometer values are just dot products of the sensor axes | 56 // Accelerometer values are just dot products of the sensor axes | 
| 47 // by the gravity vector 'g' with the result for the z axis inverted. | 57 // by the gravity vector 'g' with the result for the z axis inverted. | 
| 48 // | 58 // | 
| 49 // To understand this transformation calculate the 3rd row of the z-x-y | 59 // To understand this transformation calculate the 3rd row of the z-x-y | 
| 50 // Euler angles rotation matrix (because of the 'g' vector, only 3rd row | 60 // Euler angles rotation matrix (because of the 'g' vector, only 3rd row | 
| 51 // affects to the result). Note that z-x-y matrix means R = Ry * Rx * Rz. | 61 // affects to the result). Note that z-x-y matrix means R = Ry * Rx * Rz. | 
| 52 // Then, assume alpha = 0 and you get this: | 62 // Then, assume alpha = 0 and you get this: | 
| 53 // | 63 // | 
| 54 // x_acc = sin(gamma) | 64 // x_acc = sin(gamma) | 
| 55 // y_acc = - cos(gamma) * sin(beta) | 65 // y_acc = - cos(gamma) * sin(beta) | 
| 56 // z_acc = cos(beta) * cos(gamma) | 66 // z_acc = cos(beta) * cos(gamma) | 
| 57 // | 67 // | 
| 58 // After that the rest is just a bit of trigonometry. | 68 // After that the rest is just a bit of trigonometry. | 
| 59 // | 69 // | 
| 60 // Also note that alpha can't be provided but it's assumed to be always zero. | 70 // Also note that alpha can't be provided but it's assumed to be always zero. | 
| 61 // This is necessary in order to provide enough information to solve | 71 // This is necessary in order to provide enough information to solve | 
| 62 // the equations. | 72 // the equations. | 
| 63 // | 73 // | 
| 64 const double kRad2deg = 180.0 / M_PI; | 74 const double kRad2deg = 180.0 / M_PI; | 
| 65 | 75 | 
| 76 scoped_ptr<Orientation> orientation(new Orientation()); | |
| 77 | |
| 66 orientation->set_beta(kRad2deg * atan2(-axis_value[1], axis_value[2])); | 78 orientation->set_beta(kRad2deg * atan2(-axis_value[1], axis_value[2])); | 
| 67 orientation->set_gamma(kRad2deg * asin(axis_value[0])); | 79 orientation->set_gamma(kRad2deg * asin(axis_value[0])); | 
| 68 // TODO(aousterh): should absolute_ be set to false here? | 80 // TODO(aousterh): should absolute_ be set to false here? | 
| 69 // See crbug.com/136010. | 81 // See crbug.com/136010. | 
| 70 | 82 | 
| 71 // Make sure that the interval boundaries comply with the specification. At | 83 // Make sure that the interval boundaries comply with the specification. At | 
| 72 // this point, beta is [-180, 180] and gamma is [-90, 90], but the spec has | 84 // this point, beta is [-180, 180] and gamma is [-90, 90], but the spec has | 
| 73 // the upper bound open on both. | 85 // the upper bound open on both. | 
| 74 if (orientation->beta() == 180.0) { | 86 if (orientation->beta() == 180.0) { | 
| 75 orientation->set_beta(-180.0); // -180 == 180 (upside-down) | 87 orientation->set_beta(-180.0); // -180 == 180 (upside-down) | 
| 76 } | 88 } | 
| 77 if (orientation->gamma() == 90.0) { | 89 if (orientation->gamma() == 90.0) { | 
| 78 static double just_less_than_90 = nextafter(90, 0); | 90 static double just_less_than_90 = nextafter(90, 0); | 
| 79 orientation->set_gamma(just_less_than_90); | 91 orientation->set_gamma(just_less_than_90); | 
| 80 } | 92 } | 
| 81 | 93 | 
| 82 // At this point, DCHECKing is paranoia. Never hurts. | 94 // At this point, DCHECKing is paranoia. Never hurts. | 
| 83 DCHECK_GE(orientation->beta(), -180.0); | 95 DCHECK_GE(orientation->beta(), -180.0); | 
| 84 DCHECK_LT(orientation->beta(), 180.0); | 96 DCHECK_LT(orientation->beta(), 180.0); | 
| 85 DCHECK_GE(orientation->gamma(), -90.0); | 97 DCHECK_GE(orientation->gamma(), -90.0); | 
| 86 DCHECK_LT(orientation->gamma(), 90.0); | 98 DCHECK_LT(orientation->gamma(), 90.0); | 
| 87 | 99 | 
| 88 return true; | 100 return orientation.release(); | 
| 89 } | 101 } | 
| 90 | 102 | 
| 91 bool AccelerometerMac::Init() { | 103 bool AccelerometerMac::Init() { | 
| 92 sudden_motion_sensor_.reset(SuddenMotionSensor::Create()); | 104 sudden_motion_sensor_.reset(SuddenMotionSensor::Create()); | 
| 93 return sudden_motion_sensor_.get() != NULL; | 105 return sudden_motion_sensor_.get() != NULL; | 
| 94 } | 106 } | 
| 95 | 107 | 
| 96 } // namespace device_orientation | 108 } // namespace device_orientation | 
| OLD | NEW |