Module: Coordinates

Defined in:
lib/coordinate-converter.rb

Class Method Summary collapse

Class Method Details

.utm_to_lat_long(reference_ellipsoid, northing, easting, zone) ⇒ Object



2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
# File 'lib/coordinate-converter.rb', line 2

def self.utm_to_lat_long(reference_ellipsoid, northing, easting, zone)    
  a  = equitorial_radius(reference_ellipsoid)
  ecc_squared = eccentricity_squared(reference_ellipsoid)
  
  e1 = (1 - Math.sqrt(1 - ecc_squared)) / (1 + Math.sqrt(1 - ecc_squared))
  
  x = easting - 500000.0 
  y = northing
  
  zone_letter = zone[-1].chr
  zone_number = zone[0..-2].to_i
  if zone_letter >= 'S'
    y -= 10000000.0   
  end
  
  long_origin = (zone_number - 1) * 6 - 180 + 3
  ecc_prime_squared = (ecc_squared) / (1 - ecc_squared)
  
  k0 = 0.9996
  m  = y / k0
  mu = m / (a * (1 - ecc_squared / 4 - 3 * ecc_squared * ecc_squared / 64 - 5 \
     * ecc_squared * ecc_squared * ecc_squared / 256))
  
  phi1_rad = (mu + (3 * e1 / 2 - 27 * e1 * e1 * e1 / 32) * Math.sin(2 * mu) \
                 + (21 * e1 * e1 / 16 - 55 * e1 * e1 * e1 * e1 / 32) \
                 * Math.sin(4 * mu) + (151 * e1 * e1 * e1 / 96) \
                 * Math.sin(6 * mu))
  
  n1 = a / Math.sqrt(1 - ecc_squared * Math.sin(phi1_rad) * Math.sin(phi1_rad))
  t1 = Math.tan(phi1_rad) * Math.tan(phi1_rad)
  c1 = ecc_prime_squared * Math.cos(phi1_rad) * Math.cos(phi1_rad)
  r1 = a * (1 - ecc_squared) / (1 - ecc_squared * Math.sin(phi1_rad) * Math.sin(phi1_rad))**1.5
  d  = x / (n1 * k0)

  lat = phi1_rad - (n1 * Math.tan(phi1_rad) / r1) * (d * d / 2 - (5 + 3 * t1 \
      + 10 * c1 - 4 * c1**2 - 9 * ecc_prime_squared) * d**4 / 24 + (61 + 90 \
      * t1 + 298 * c1 + 45 * t1**2 - 252 * ecc_prime_squared - 3 * c1**2) \
      * d**6 / 720)
  lat = lat * RAD_TO_DEG

  long = (d - (1 + 2 * t1 + c1) * d * d * d / 6 + (5 - 2 * c1 + 28 \
       * t1 - 3 * c1 * c1 + 8 * ecc_prime_squared + 24 * t1 * t1) \
       * d * d * d * d * d / 120) / Math.cos(phi1_rad)

  long = long_origin + long * RAD_TO_DEG

  { :lat => lat, :long => long }
end