Simple Accelerometer Data Conversion to Degrees

Here is a handy lua Corona Labs code chunk to convert xyz accelerometer data to degrees.

I am building an augmented reality app that needs to know when the user tilts and rolls a phone around so it can update the user interface with augmented reality elements. Corona already has the accelerometer acquisition code but now I want to display this data in human readable degrees (e.g if you were looking half way up the sky you would expect 45° and the horizon 0°)

A shout out goes to Doug McFarland here for the original c/Arduino code (http://wizmoz.blogspot.com.au/2013/01/simple-accelerometer-data-conversion-to.html) that I converted to Lua.

Code:

            --Input Data
            local xAxisData = --insert xaxis sensor data here
            local yAxisData = --insert yaxis sensor data here
            local zAxisData = --insert zaxis sensor data here
            --Convert raw 0.0 ~ 1.0 sensor datad to degrees.
            local xAngle = math.atan(tonumber(xAxisData) / (math.sqrt((tonumber(yAxisData) * tonumber(yAxisData))) + (tonumber(zAxisData) * tonumber(zAxisData))))
            local yAngle = math.atan(tonumber(yAxisData) / (math.sqrt((tonumber(xAxisData) * tonumber(xAxisData)) +  (tonumber(zAxisData) * tonumber(zAxisData)))))
            local zAngle = math.atan(math.sqrt((tonumber(xAxisData) * tonumber(xAxisData)) + (tonumber(yAxisData) * tonumber(yAxisData))) / tonumber(zAxisData));
            xAngle = xAngle * 180.00
            yAngle = yAngle * 180.00
            zAngle = zAngle * 180.00
            xAngle = xAngle / 3.141592
            yAngle = yAngle / 3.141592
            zAngle = zAngle / 3.141592
            --Round down a bit and display
            print("X Degrees: " .. tostring( math.round(xAngle,1)) .. " (Original X: " .. tonumber(xAxisData) .. ")")
            print("Y Degrees: " .. tostring( math.round(yAngle,1)) .. " (Original Y: " .. tonumber(yAxisData) .. ")")
            print("Z Degrees: " .. tostring( math.round(zAngle,1)) .. " (Original Z: " .. tonumber(zAxisData) .. ")")

Output Data:

    Accelerometer X Data: -0.0264 = -1&deg
    Accelerometer Y Data: -68 = -68&deg
    Accelerometer Z Data: 0.3682 = 68&deg

Comments:

This does not look too handy to some but this is gold in plotting the horizon and calculating far away objects with trigonometry.

Don’t forget to detect what orientation the mobile device is in (portrait, landscape, upside down portrait and upside down landscape). You will need to factor these display modes into the calculation before converting to degrees. Sometimes it is easier to just develop portrait or landscape apps (not both).

Calculating the distance and bearing between two GPS points

I have been searching for a solution to calculate the distance and bearing of a target gps location for a while now. This page always popped up but my brain hurt every time I tried to convert this to lua.

I am happy to say I have cracked it and here is my code.

function Geo_Angle( lat1, lon1, lat2, lon2)
  local dLon = math.rad(lon2-lon1);
  local y = math.sin(dLon) * math.cos(math.rad(lat2));
  local x = math.cos(math.rad(lat1)) * math.sin(math.rad(lat2)) - math.sin(math.rad(lat1)) * math.cos(math.rad(lat2)) * math.cos(dLon);
  local brng = math.deg(math.atan2(y, x));
  return ((brng + 360) % 360);
end

The distance code was created by roaminggamer else on the Corona forums (can’t find their name).

 
function Geo_Distance(lat1, lon1, lat2, lon2)
  if lat1 == nil or lon1 == nil or lat2 == nil or lon2 == nil then
    return nil
  end
  local dlat = math.rad(lat2-lat1)
  local dlon = math.rad(lon2-lon1)
  local sin_dlat = math.sin(dlat/2)
  local sin_dlon = math.sin(dlon/2)
  local a = sin_dlat * sin_dlat + math.cos(math.rad(lat1)) * math.cos(math.rad(lat2)) * sin_dlon * sin_dlon
  local c = 2 * math.atan2(math.sqrt(a), math.sqrt(1-a))
  -- 6378 km is the earth's radius at the equator.
  -- 6357 km would be the radius at the poles (earth isn't a perfect circle).
  -- Thus, high latitude distances will be slightly overestimated
  -- To get miles, use 3963 as the constant (equator again)
  local d = 6378 * c
  return d
end

Here is how I call the code

print("Bearing between Tamworth and Armidale: " .. tonumber(GeoAngle(-31.1063157, 150.9307341,-30.5143425, 151.66696439999998)))
print("Distance between Tamworth and Armidale: " .. tonumber(GeoDistance(-31.1063157, 150.9307341,-30.5143425, 151.66696439999998)) .. "km")

Results:

Corona Simulator[4155:693467] Bearing between Tamworth and Armidale: 47.07677793374
Corona Simulator[4155:693467] Distance between Tamworth and Armidale: 96.419986257454km

When comparing my results with this site my bearing results are within 0.18677793374 degree and 0.078686257454 km for distance (good enough for my simple augmented reality app).

I tried to trick it by putting the source/dest either side of GMT and it did not measure the longest route around the globe.

Corona Simulator[4288:936166] Bearing between -179 lon and 179 lon: 270
Corona Simulator[4288:936166] Distance between -179 lon and 179 lon: 222.6341993844km

Also putting a source/dest near each pole calculated the approximate right distance between the coordinates.

Corona Simulator[4288:936166] Bearing between -89 lat and 89 lat: 180°
Corona Simulator[4288:936166] Distance between 89 lat and 89 lat: 19814.443745211km

Arduino GPS Code for GPS/GPRS/GSM Module V3.0 (SKU:TEL0051) loaded

Arduino GPS Code for GPS/GPRS/GSM Module V3.0 (SKU:TEL0051) loaded.

20140727-031035-11435603.jpg

http://www.dfrobot.com/wiki/index.php/GPS/GPRS/GSM_Module_V3.0_%28SKU:TEL0051%29#How_to_drive_the_GPS_Mode_via_USB_port

Quite a bit of research to get the boards code, configure the arduino IDE and latest GitHub code.

Now I have to go outside to get a GPS signal.

20140727-031152-11512745.jpg

Update: Was able to send a text message from the Arduino/gsm module Telstra pre paid sim via power pack alone. It turns out we need to redirect pins 3/4/5 to 11/12/13 :)

20140727-162112-58872675.jpg

20140727-162734-59254900.jpg