modalh 1.0.5 → 1.1.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
data/VERSION CHANGED
@@ -1 +1 @@
1
- 1.0.5
1
+ 1.1.1
@@ -69,12 +69,24 @@ module H
69
69
 
70
70
  end
71
71
 
72
- [:number, :integer, :date, :logical, :time, :datetime].each do |prefix|
72
+ [:number, :integer, :date, :logical, :time, :datetime, :dms].each do |prefix|
73
73
  define_method :"#{prefix}_h" do |attr, *options|
74
74
  _h prefix, attr, *options
75
75
  end
76
76
  end
77
77
 
78
+ def longitude_h(attr, *args)
79
+ options = args.extract_options!
80
+ options[:longitude] = true
81
+ _h prefix, attr, *(args<<options)
82
+ end
83
+
84
+ def latitude_h(attr, *args)
85
+ options = args.extract_options!
86
+ options[:latitude] = true
87
+ _h prefix, attr, *(args<<options)
88
+ end
89
+
78
90
  # TODO: support special suffix form of units, e.g. _m2 for m^2, for attribute names
79
91
 
80
92
  def units_h(name, units, options={})
data/lib/h/fields.rb CHANGED
@@ -64,6 +64,7 @@ module H
64
64
  end
65
65
  options[:precision] ||= {'m'=>1, 'mm'=>0, 'cm'=>0, 'km'=>3}[options[:units]] # TODO AppSettings
66
66
  declaration.remove_attributes! :h_precision, :units
67
+ # declaration.replace!(:type=>:float)
67
68
  model.units_h declaration.name, options[:units], options
68
69
  end
69
70
 
@@ -83,6 +84,33 @@ module H
83
84
  model.logical_h declaration.name
84
85
  end
85
86
 
87
+ def declare_dms_field(model, declaration)
88
+ options = declaration.attributes.slice(:precision, :longitude, :latitude)
89
+ if precision = declaration.attributes[:h_precision]
90
+ options[:precision] = precision
91
+ end
92
+ declaration.remove_attributes! :h_precision, :longitude, :latitude
93
+ model.dms_h declaration.name, options
94
+ end
95
+
96
+ def declare_longitude_field(model, declaration)
97
+ options = declaration.attributes.slice(:precision).merge(:longitude=>true)
98
+ if precision = declaration.attributes[:h_precision]
99
+ options[:precision] = precision
100
+ end
101
+ declaration.remove_attributes! :h_precision
102
+ model.dms_h declaration.name, options
103
+ end
104
+
105
+ def declare_latitude_field(model, declaration)
106
+ options = declaration.attributes.slice(:precision).merge(:latitude=>true)
107
+ if precision = declaration.attributes[:h_precision]
108
+ options[:precision] = precision
109
+ end
110
+ declaration.remove_attributes! :h_precision
111
+ model.dms_h declaration.name, options
112
+ end
113
+
86
114
  # This is handy to be used in all_fields to make any field with a :units parameter or a valid units suffix a units_h field
87
115
  # (and make other numberic fields _h too); If a field with a suffix corresponding to valid units should not be a measure,
88
116
  # a :units=>nil parameter should be added.
@@ -92,7 +120,9 @@ module H
92
120
  unless declaration.attributes.has_key?(:units)
93
121
  units = declaration.name.to_s.split('_').last
94
122
  end
95
- if units && H::Units.valid?(units)
123
+ if units && units.to_s=='dms'
124
+ declare_dms_field model, declaration
125
+ elsif units && H::Units.valid?(units)
96
126
  declare_units_field model, declaration, units
97
127
  else
98
128
  raise ArgumentError, "Invalid units #{declaration.attributes[:units]} in declaration of #{model.name}" if declaration.attributes[:units]
data/lib/h/h.rb CHANGED
@@ -48,11 +48,12 @@ module H
48
48
  elsif value.respond_to?(:infinite?) && value.infinite?
49
49
  inf = options[:inf] || '∞'
50
50
  return value<0 ? "-#{inf}" : inf
51
- else
51
+ else
52
52
  value = value.to_i if precision==0
53
53
  value = value.to_s
54
54
  value = value[0...-2] if value.end_with?('.0')
55
- end
55
+ end
56
+ # else: TODO recognize nan/infinite values
56
57
  end
57
58
  if options[:delimiter]
58
59
  txt = value.to_s.tr(' ','').tr('.,',options[:separator]+options[:delimiter]).tr(options[:delimiter],'')
@@ -78,11 +79,7 @@ module H
78
79
 
79
80
  return nil if txt.to_s.strip.empty? || txt==options[:blank]
80
81
 
81
- if options[:delimiter]
82
- txt = txt.tr(' ','').tr(options[:delimiter]+options[:separator], ',.').tr(',','')
83
- else
84
- txt = txt.tr(' ','').tr(options[:separator], '.')
85
- end
82
+ txt = numbers_to_ruby(txt.tr(' ',''), options)
86
83
  raise ArgumentError, "Invalid number #{txt}" unless /\A[+-]?\d+(?:\.\d*)?(?:[eE][+-]?\d+)?\Z/.match(txt)
87
84
  if type==Float
88
85
  txt.to_f
@@ -169,11 +166,160 @@ module H
169
166
  trues.include?(txt) ? true : falses.include?(txt) ? false : nil
170
167
  end
171
168
 
169
+ def dms_from(txt, options={})
170
+ original_txt = txt
171
+ options = dms_format_options(options).merge(options)
172
+
173
+ return nil if txt.to_s.strip.empty? || txt==options[:blank]
174
+
175
+ neg_signs = [options[:south], options[:west]] << '-'
176
+ pos_signs = [options[:north], options[:east]] << '+'
177
+ neg_signs, pos_signs = [neg_signs, pos_signs].map {|signs|
178
+ (signs.map{|s| s.mb_chars.upcase.to_s} + signs.map{|s| s.mb_chars.downcase.to_s}).uniq
179
+ }
180
+ signs = neg_signs + pos_signs
181
+ seps = Array(options[:deg_seps]) + Array(options[:min_seps]) + Array(options[:sec_seps])
182
+
183
+ neg = false
184
+
185
+ txt = txt.to_s.strip
186
+ neg_signs.each do |sign|
187
+ if txt.start_with?(sign)
188
+ txt = txt[sign.size..-1]
189
+ neg = true
190
+ break
191
+ end
192
+ if txt.end_with?(sign)
193
+ txt = txt[0...-sign.size]
194
+ neg = true
195
+ break
196
+ end
197
+ end
198
+ unless neg
199
+ pos_signs.each do |sign|
200
+ if txt.start_with?(sign)
201
+ txt = txt[sign.size..-1]
202
+ break
203
+ end
204
+ if txt.end_with?(sign)
205
+ txt = txt[0...-sign.size]
206
+ break
207
+ end
208
+ end
209
+ end
210
+
211
+ num_options = number_format_options(options).except(:precision).merge(options)
212
+ txt = numbers_to_ruby(txt.strip, num_options)
213
+
214
+ default_units = 0
215
+
216
+ v = 0
217
+ seps = (seps.map{|s| Regexp.escape(s)}<<"\\s+")*"|"
218
+ scanned_txt = ""
219
+ txt.scan(/((\d+(?:\.\d*)?(?:[eE][+-]?\d+)?)(#{seps})?\s*)/) do |match|
220
+ scanned_txt << match[0]
221
+ number = match[1]
222
+ sep = match[2]
223
+ if Array(options[:deg_seps]).include?(sep)
224
+ units = :deg
225
+ elsif Array(options[:min_seps]).include?(sep)
226
+ units = :min
227
+ elsif Array(options[:sec_seps]).include?(sep)
228
+ units = :sec
229
+ else
230
+ units = DMS_UNITS[default_units]
231
+ end
232
+ raise ArgumentError, "Invalid degrees-minutes-seconds value #{original_txt}" unless units
233
+ default_units = DMS_UNITS.index(units) + 1
234
+ x = number.to_f
235
+ x *= DMS_FACTORS[units]
236
+ v += x
237
+ end
238
+ raise ArgumentError, "Invalid degrees-minutes-seconds value #{original_txt} [#{txt}] [#{scanned_txt}]" unless txt==scanned_txt
239
+ v = -v if neg
240
+ v
241
+ end
242
+
243
+ def longitude_to(value, options={})
244
+ dms_to value, options.merge(:longitude=>true)
245
+ end
246
+
247
+ def latitude_to(value, options={})
248
+ dms_to value, options.merge(:latitude=>true)
249
+ end
250
+
251
+ def dms_to(value, options={})
252
+ longitude = options[:longitude]
253
+ latitude = options[:latitude]
254
+ latitude = true if longitude==false && !options.has_key?(:latitude)
255
+ longitude = true if latitude==false && !options.has_key?(:longitude)
256
+ options = dms_format_options(options).except(:precision).merge(options)
257
+ precision = options[:precision]
258
+
259
+ return options[:blank] || '' if value.nil?
260
+
261
+ if value.kind_of?(String)
262
+ # TODO: recognize nan/infinite values
263
+ value = value.to_f
264
+ else
265
+ if value.respond_to?(:nan?) && value.nan?
266
+ return options[:nan] || "--"
267
+ elsif value.respond_to?(:infinite?) && value.infinite?
268
+ inf = options[:inf] || '∞'
269
+ return value<0 ? "-#{inf}" : inf
270
+ end
271
+ end
272
+ if value.to_s.start_with?('-') # value<0 # we use to_s to handle negative zero
273
+ value = -value
274
+ neg = true
275
+ end
276
+
277
+ deg = value.floor
278
+ value -= deg
279
+ value *= 60
280
+ min = value.floor
281
+ value -= min
282
+ value *= 60
283
+ sec = value.round(SEC_PRECISION)
284
+
285
+ txt = []
286
+
287
+ txt << integer_to(deg, options.except(:precision)) + Array(options[:deg_seps]).first
288
+ if min>0 || sec>0
289
+ txt << integer_to(min, options.except(:precision)) + Array(options[:min_seps]).first
290
+ if sec>0
291
+ txt << number_to(sec, options) + Array(options[:sec_seps]).first
292
+ end
293
+ end
294
+
295
+ txt = txt*" "
296
+
297
+ if longitude || latitude
298
+ if longitude
299
+ letter = neg ? options[:west] : options[:east]
300
+ else
301
+ letter = neg ? options[:south] : options[:north]
302
+ end
303
+ txt = options[:prefix] ? "#{letter} #{txt}" : "#{txt} #{letter}"
304
+ else
305
+ txt = "-#{txt}" if neg
306
+ end
307
+
308
+ txt
309
+ end
310
+
172
311
  # TODO: currency, money, bank accounts, credit card numbers, ...
173
312
 
174
313
  private
175
314
  # include ActionView::Helpers::NumberHelper
176
315
 
316
+ DMS_UNITS = [:deg, :min, :sec]
317
+ DMS_FACTORS = {
318
+ :deg=>1, :min=>1.0/60.0, :sec=>1.0/3600.0
319
+ }
320
+ SEC_EPSILON = 1E-10
321
+ SEC_PRECISION = 10
322
+
177
323
  def number_format_options(options)
178
324
  opt = I18n.translate(:'number.format', :locale => options[:locale])
179
325
  opt.kind_of?(Hash) ? opt : {:separator=>'.'}
@@ -184,6 +330,20 @@ module H
184
330
  opt.kind_of?(Hash) ? opt : {:separator=>'.'}
185
331
  end
186
332
 
333
+ def dms_format_options(options)
334
+ opt = I18n.translate(:'number.dms.format', :locale => options[:locale])
335
+ opt.kind_of?(Hash) ? opt : {
336
+ :deg_seps => ['°', 'º'],
337
+ :min_seps => "'",
338
+ :sec_seps => '"',
339
+ :north => 'N',
340
+ :south => 'S',
341
+ :east => 'E',
342
+ :west => 'W',
343
+ :prefix => false
344
+ }
345
+ end
346
+
187
347
  def round(v, ndec)
188
348
  return v if (v.respond_to?(:nan?) && v.nan?) || (v.respond_to?(:infinite?) && v.infinite?)
189
349
  if ndec
@@ -263,6 +423,15 @@ module H
263
423
  type
264
424
  end
265
425
 
426
+ def numbers_to_ruby(txt, options)
427
+ if options[:delimiter]
428
+ txt = txt.tr(options[:delimiter]+options[:separator], ',.').tr(',','')
429
+ else
430
+ txt = txt.tr(options[:separator], '.')
431
+ end
432
+ txt
433
+ end
434
+
266
435
 
267
436
  end
268
437
 
data/lib/h/helpers.rb CHANGED
@@ -3,7 +3,7 @@ module H
3
3
  # Define methods to_h for H.to, from_h from H.from, xxx_to_h from H.xxx_to, xxx_from_h from H.xxx_from
4
4
  module Helpers
5
5
 
6
- (%w{date number integer logical magnitude}<<nil).each do |type|
6
+ (%w{date number integer logical magnitude dms}<<nil).each do |type|
7
7
  %w{from to}.each do |kind|
8
8
  name = [type,kind].compact*'_'
9
9
  define_method "#{name}_h" do |*args|
data/modalh.gemspec CHANGED
@@ -5,11 +5,11 @@
5
5
 
6
6
  Gem::Specification.new do |s|
7
7
  s.name = "modalh"
8
- s.version = "1.0.5"
8
+ s.version = "1.1.1"
9
9
 
10
10
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
11
  s.authors = ["Javier Goizueta"]
12
- s.date = "2012-05-08"
12
+ s.date = "2012-05-10"
13
13
  s.description = "Rails plugin for localization & delocalization of data values"
14
14
  s.email = "jgoizueta@gmail.com"
15
15
  s.extra_rdoc_files = [
data/test/helper.rb CHANGED
@@ -12,6 +12,7 @@ require 'shoulda'
12
12
 
13
13
  require 'i18n'
14
14
  require 'active_support'
15
+ require 'active_support/core_ext/string'
15
16
  require 'bigdecimal'
16
17
 
17
18
  $LOAD_PATH.unshift(File.join(File.dirname(__FILE__), '..', 'lib'))
data/test/test_modalh.rb CHANGED
@@ -1,3 +1,4 @@
1
+ # encoding: UTF-8
1
2
  require 'helper'
2
3
 
3
4
  class TestModalh < Test::Unit::TestCase
@@ -80,4 +81,282 @@ class TestModalh < Test::Unit::TestCase
80
81
  assert_equal -1234.567, H.from("-1,234.567", :delimiter=>',')
81
82
  end
82
83
 
84
+ should "parse dms" do
85
+ assert_equal 41.508473, H.dms_from("41° 30' 30.5028\" N")
86
+ assert_equal 41.508473, H.dms_from("41° 30' 30.5028\"")
87
+ assert_equal 41.508473, H.dms_from("41° 30' 30.5028\"N")
88
+ assert_equal 41.508473, H.dms_from("N 41° 30' 30.5028\"")
89
+ assert_equal 41.508473, H.dms_from("N41° 30' 30.5028\"")
90
+ assert_equal -41.508473, H.dms_from("41° 30' 30.5028\" S")
91
+ assert_equal -41.508473, H.dms_from("-41° 30' 30.5028\"")
92
+ assert_equal -41.508473, H.dms_from("41° 30' 30.5028\"S")
93
+ assert_equal -41.508473, H.dms_from("S 41° 30' 30.5028\"")
94
+ assert_equal -41.508473, H.dms_from("S41° 30' 30.5028\"")
95
+ assert_equal 41.508473, H.dms_from("41° 30' 30.5028\" E")
96
+ assert_equal 41.508473, H.dms_from("41° 30' 30.5028\"")
97
+ assert_equal 41.508473, H.dms_from("41° 30' 30.5028\"E")
98
+ assert_equal 41.508473, H.dms_from("E 41° 30' 30.5028\"")
99
+ assert_equal 41.508473, H.dms_from("E41° 30' 30.5028\"")
100
+ assert_equal -41.508473, H.dms_from("41° 30' 30.5028\" W")
101
+ assert_equal -41.508473, H.dms_from("-41° 30' 30.5028\"")
102
+ assert_equal -41.508473, H.dms_from("41° 30' 30.5028\"W")
103
+ assert_equal -41.508473, H.dms_from("W 41° 30' 30.5028\"")
104
+ assert_equal -41.508473, H.dms_from("W41° 30' 30.5028\"")
105
+
106
+ assert_equal 41.508473, H.dms_from("41° 30' 30.5028 N")
107
+ assert_equal 41.508473, H.dms_from("41° 30' 30.5028")
108
+ assert_equal 41.508473, H.dms_from("41° 30' 30.5028N")
109
+ assert_equal 41.508473, H.dms_from("N 41° 30' 30.5028")
110
+ assert_equal 41.508473, H.dms_from("N41° 30' 30.5028")
111
+ assert_equal -41.508473, H.dms_from("41° 30' 30.5028 S")
112
+ assert_equal -41.508473, H.dms_from("-41° 30' 30.5028")
113
+ assert_equal -41.508473, H.dms_from("41° 30' 30.5028S")
114
+ assert_equal -41.508473, H.dms_from("S 41° 30' 30.5028")
115
+ assert_equal -41.508473, H.dms_from("S41° 30' 30.5028")
116
+ assert_equal 41.508473, H.dms_from("41° 30' 30.5028 E")
117
+ assert_equal 41.508473, H.dms_from("41° 30' 30.5028")
118
+ assert_equal 41.508473, H.dms_from("41° 30' 30.5028E")
119
+ assert_equal 41.508473, H.dms_from("E 41° 30' 30.5028")
120
+ assert_equal 41.508473, H.dms_from("E41° 30' 30.5028")
121
+ assert_equal -41.508473, H.dms_from("41° 30' 30.5028 W")
122
+ assert_equal -41.508473, H.dms_from("-41° 30' 30.5028")
123
+ assert_equal -41.508473, H.dms_from("41° 30' 30.5028W")
124
+ assert_equal -41.508473, H.dms_from("W 41° 30' 30.5028")
125
+ assert_equal -41.508473, H.dms_from("W41° 30' 30.5028")
126
+
127
+ assert_equal 41.508473, H.dms_from("41 30' 30.5028\" N")
128
+ assert_equal 41.508473, H.dms_from("41 30' 30.5028\"")
129
+ assert_equal 41.508473, H.dms_from("41 30' 30.5028\"N")
130
+ assert_equal 41.508473, H.dms_from("N 41 30' 30.5028\"")
131
+ assert_equal 41.508473, H.dms_from("N41 30' 30.5028\"")
132
+ assert_equal -41.508473, H.dms_from("41 30' 30.5028\" S")
133
+ assert_equal -41.508473, H.dms_from("-41 30' 30.5028\"")
134
+ assert_equal -41.508473, H.dms_from("41 30' 30.5028\"S")
135
+ assert_equal -41.508473, H.dms_from("S 41 30' 30.5028\"")
136
+ assert_equal -41.508473, H.dms_from("S41 30' 30.5028\"")
137
+ assert_equal 41.508473, H.dms_from("41 30' 30.5028\" E")
138
+ assert_equal 41.508473, H.dms_from("41 30' 30.5028\"")
139
+ assert_equal 41.508473, H.dms_from("41 30' 30.5028\"E")
140
+ assert_equal 41.508473, H.dms_from("E 41 30' 30.5028\"")
141
+ assert_equal 41.508473, H.dms_from("E41 30' 30.5028\"")
142
+ assert_equal -41.508473, H.dms_from("41 30' 30.5028\" W")
143
+ assert_equal -41.508473, H.dms_from("-41 30' 30.5028\"")
144
+ assert_equal -41.508473, H.dms_from("41 30' 30.5028\"W")
145
+ assert_equal -41.508473, H.dms_from("W 41 30' 30.5028\"")
146
+ assert_equal -41.508473, H.dms_from("W41 30' 30.5028\"")
147
+
148
+ assert_equal 41.775, H.dms_from("41° 46.5'")
149
+ assert_equal 41.775, H.dms_from("41° 46.5' N")
150
+ assert_equal 41.775, H.dms_from("41° 46.5'N")
151
+ assert_equal 41.775, H.dms_from("N41° 46.5'")
152
+ assert_equal 41.775, H.dms_from("N 41° 46.5'")
153
+ assert_equal -41.775, H.dms_from("-41° 46.5'")
154
+ assert_equal -41.775, H.dms_from("41° 46.5' S")
155
+ assert_equal -41.775, H.dms_from("41° 46.5'S")
156
+ assert_equal -41.775, H.dms_from("S41° 46.5'")
157
+ assert_equal -41.775, H.dms_from("S 41° 46.5'")
158
+
159
+ assert_equal 41.775, H.dms_from("41 46.5'")
160
+ assert_equal 41.775, H.dms_from("41 46.5' N")
161
+ assert_equal 41.775, H.dms_from("41 46.5'N")
162
+ assert_equal 41.775, H.dms_from("N41 46.5'")
163
+ assert_equal 41.775, H.dms_from("N 41 46.5'")
164
+ assert_equal -41.775, H.dms_from("-41 46.5'")
165
+ assert_equal -41.775, H.dms_from("41 46.5' S")
166
+ assert_equal -41.775, H.dms_from("41 46.5'S")
167
+ assert_equal -41.775, H.dms_from("S41 46.5'")
168
+ assert_equal -41.775, H.dms_from("S 41 46.5'")
169
+
170
+ assert_equal 41.775, H.dms_from("41° 46.5")
171
+ assert_equal 41.775, H.dms_from("41° 46.5 N")
172
+ assert_equal 41.775, H.dms_from("41° 46.5N")
173
+ assert_equal 41.775, H.dms_from("N41° 46.5")
174
+ assert_equal 41.775, H.dms_from("N 41° 46.5")
175
+ assert_equal -41.775, H.dms_from("-41° 46.5")
176
+ assert_equal -41.775, H.dms_from("41° 46.5 S")
177
+ assert_equal -41.775, H.dms_from("41° 46.5S")
178
+ assert_equal -41.775, H.dms_from("S41° 46.5")
179
+ assert_equal -41.775, H.dms_from("S 41° 46.5")
180
+
181
+ assert_equal 41.775, H.dms_from("41.775°")
182
+ assert_equal 41.775, H.dms_from("41.775° N")
183
+ assert_equal 41.775, H.dms_from("41.775°N")
184
+ assert_equal 41.775, H.dms_from("N41.775°")
185
+ assert_equal 41.775, H.dms_from("N 41.775°")
186
+ assert_equal -41.775, H.dms_from("-41.775°")
187
+ assert_equal -41.775, H.dms_from("41.775° S")
188
+ assert_equal -41.775, H.dms_from("41.775°S")
189
+ assert_equal -41.775, H.dms_from("S41.775°")
190
+ assert_equal -41.775, H.dms_from("S 41.775°")
191
+
192
+ assert_equal 41.775, H.dms_from("41.775")
193
+ assert_equal 41.775, H.dms_from("41.775 N")
194
+ assert_equal 41.775, H.dms_from("41.775N")
195
+ assert_equal 41.775, H.dms_from("N41.775")
196
+ assert_equal 41.775, H.dms_from("N 41.775")
197
+ assert_equal -41.775, H.dms_from("-41.775")
198
+ assert_equal -41.775, H.dms_from("41.775 S")
199
+ assert_equal -41.775, H.dms_from("41.775S")
200
+ assert_equal -41.775, H.dms_from("S41.775")
201
+ assert_equal -41.775, H.dms_from("S 41.775")
202
+
203
+ assert_equal 0.508473, H.dms_from("0° 30' 30.5028\" N")
204
+ assert_equal 0.508473, H.dms_from("0° 30' 30.5028\"")
205
+ assert_equal 0.508473, H.dms_from("0° 30' 30.5028\"N")
206
+ assert_equal 0.508473, H.dms_from("N 0° 30' 30.5028\"")
207
+ assert_equal 0.508473, H.dms_from("N0° 30' 30.5028\"")
208
+ assert_equal -0.508473, H.dms_from("0° 30' 30.5028\" S")
209
+ assert_equal -0.508473, H.dms_from("-0° 30' 30.5028\"")
210
+ assert_equal -0.508473, H.dms_from("0° 30' 30.5028\"S")
211
+ assert_equal -0.508473, H.dms_from("S 0° 30' 30.5028\"")
212
+ assert_equal -0.508473, H.dms_from("S0° 30' 30.5028\"")
213
+ assert_equal 0.508473, H.dms_from("0° 30' 30.5028\" E")
214
+ assert_equal 0.508473, H.dms_from("0° 30' 30.5028\"")
215
+ assert_equal 0.508473, H.dms_from("0° 30' 30.5028\"E")
216
+ assert_equal 0.508473, H.dms_from("E 0° 30' 30.5028\"")
217
+ assert_equal 0.508473, H.dms_from("E0° 30' 30.5028\"")
218
+ assert_equal -0.508473, H.dms_from("0° 30' 30.5028\" W")
219
+ assert_equal -0.508473, H.dms_from("-0° 30' 30.5028\"")
220
+ assert_equal -0.508473, H.dms_from("0° 30' 30.5028\"W")
221
+ assert_equal -0.508473, H.dms_from("W 0° 30' 30.5028\"")
222
+ assert_equal -0.508473, H.dms_from("W0° 30' 30.5028\"")
223
+
224
+ assert_equal 0.508473, H.dms_from("0 30' 30.5028\" N")
225
+ assert_equal 0.508473, H.dms_from("0 30' 30.5028\"")
226
+ assert_equal 0.508473, H.dms_from("0 30' 30.5028\"N")
227
+ assert_equal 0.508473, H.dms_from("N 0 30' 30.5028\"")
228
+ assert_equal 0.508473, H.dms_from("N0 30' 30.5028\"")
229
+ assert_equal -0.508473, H.dms_from("0 30' 30.5028\" S")
230
+ assert_equal -0.508473, H.dms_from("-0 30' 30.5028\"")
231
+ assert_equal -0.508473, H.dms_from("0 30' 30.5028\"S")
232
+ assert_equal -0.508473, H.dms_from("S 0 30' 30.5028\"")
233
+ assert_equal -0.508473, H.dms_from("S0 30' 30.5028\"")
234
+ assert_equal 0.508473, H.dms_from("0 30' 30.5028\" E")
235
+ assert_equal 0.508473, H.dms_from("0 30' 30.5028\"")
236
+ assert_equal 0.508473, H.dms_from("0 30' 30.5028\"E")
237
+ assert_equal 0.508473, H.dms_from("E 0 30' 30.5028\"")
238
+ assert_equal 0.508473, H.dms_from("E0 30' 30.5028\"")
239
+ assert_equal -0.508473, H.dms_from("0 30' 30.5028\" W")
240
+ assert_equal -0.508473, H.dms_from("-0 30' 30.5028\"")
241
+ assert_equal -0.508473, H.dms_from("0 30' 30.5028\"W")
242
+ assert_equal -0.508473, H.dms_from("W 0 30' 30.5028\"")
243
+ assert_equal -0.508473, H.dms_from("W0 30' 30.5028\"")
244
+
245
+ assert_equal 0.508473, H.dms_from("30' 30.5028\" N")
246
+ assert_equal 0.508473, H.dms_from("30' 30.5028\"")
247
+ assert_equal 0.508473, H.dms_from("30' 30.5028\"N")
248
+ assert_equal 0.508473, H.dms_from("N 30' 30.5028\"")
249
+ assert_equal 0.508473, H.dms_from("N30' 30.5028\"")
250
+ assert_equal -0.508473, H.dms_from("30' 30.5028\" S")
251
+ assert_equal -0.508473, H.dms_from("-30' 30.5028\"")
252
+ assert_equal -0.508473, H.dms_from("30' 30.5028\"S")
253
+ assert_equal -0.508473, H.dms_from("S30' 30.5028\"")
254
+ assert_equal -0.508473, H.dms_from("S 30' 30.5028\"")
255
+ assert_equal 0.508473, H.dms_from("30' 30.5028\" E")
256
+ assert_equal 0.508473, H.dms_from("30' 30.5028\"")
257
+ assert_equal 0.508473, H.dms_from("30' 30.5028\"E")
258
+ assert_equal 0.508473, H.dms_from("E 30' 30.5028\"")
259
+ assert_equal 0.508473, H.dms_from("E30' 30.5028\"")
260
+ assert_equal -0.508473, H.dms_from("30' 30.5028\"W")
261
+ assert_equal -0.508473, H.dms_from("W 30' 30.5028\"")
262
+ assert_equal -0.508473, H.dms_from("W30' 30.5028\"")
263
+
264
+ assert_equal 0.5, H.dms_from("30' N")
265
+ assert_equal 0.5, H.dms_from("30'")
266
+ assert_equal 0.5, H.dms_from("30'N")
267
+ assert_equal 0.5, H.dms_from("N 30'")
268
+ assert_equal 0.5, H.dms_from("N30'")
269
+ assert_equal -0.5, H.dms_from("30' S")
270
+ assert_equal -0.5, H.dms_from("-30'")
271
+ assert_equal -0.5, H.dms_from("30'S")
272
+ assert_equal -0.5, H.dms_from("S30'")
273
+ assert_equal -0.5, H.dms_from("S 30'")
274
+ assert_equal 0.5, H.dms_from("30' E")
275
+ assert_equal 0.5, H.dms_from("30'E")
276
+ assert_equal 0.5, H.dms_from("E 30'")
277
+ assert_equal 0.5, H.dms_from("E30'")
278
+ assert_equal -0.5, H.dms_from("30'W")
279
+ assert_equal -0.5, H.dms_from("W 30'")
280
+ assert_equal -0.5, H.dms_from("W30'")
281
+
282
+ assert_equal 0.01235, H.dms_from("44.46\"N")
283
+ assert_equal 0.01235, H.dms_from("44.46\"")
284
+ assert_equal -0.01235, H.dms_from("-44.46\"")
285
+
286
+ assert_equal 0.0, H.dms_from("0° 0' 0\"N")
287
+ assert_equal 0.0, H.dms_from("0° 0' 0.00\"N")
288
+ assert_equal 0.0, H.dms_from("0° 0' 0\"")
289
+ assert_equal 0.0, H.dms_from("0° 0' 0.00\"")
290
+ assert_equal 0.0, H.dms_from("-0° 0' 0\"")
291
+ assert_equal 0.0, H.dms_from("0° 0' 0\"S")
292
+ assert_equal 0.0, H.dms_from("0° 0' 0.00\"S")
293
+ assert_equal 0.0, H.dms_from("S0° 0' 0\"")
294
+ assert_equal 0.0, H.dms_from("S0° 0' 0.00\"")
295
+ assert_equal 0.0, H.dms_from("S 0° 0' 0\"")
296
+ assert_equal 0.0, H.dms_from("S 0° 0' 0.00\"")
297
+ assert_equal 0.0, H.dms_from("0 0' 0\"")
298
+ assert_equal 0.0, H.dms_from("0 0' 0.00\"")
299
+ assert_equal 0.0, H.dms_from("0 0' 0\"N")
300
+ assert_equal 0.0, H.dms_from("0° 0'N")
301
+ assert_equal 0.0, H.dms_from("0° 0.00'N")
302
+ assert_equal 0.0, H.dms_from("0° 0'")
303
+ assert_equal 0.0, H.dms_from("0° 0.00'")
304
+ assert_equal 0.0, H.dms_from("0° 0'S")
305
+ assert_equal 0.0, H.dms_from("0° 0.00' S")
306
+ assert_equal 0.0, H.dms_from("0 0'")
307
+ assert_equal 0.0, H.dms_from("-0° 0'")
308
+ assert_equal 0.0, H.dms_from("-0 0'")
309
+ assert_equal 0.0, H.dms_from("0°")
310
+ assert_equal 0.0, H.dms_from("0°N")
311
+ assert_equal 0.0, H.dms_from("0.00°")
312
+ assert_equal 0.0, H.dms_from("0")
313
+ assert_equal 0.0, H.dms_from("0.0")
314
+ assert_equal 0.0, H.dms_from("0.0N")
315
+ assert_equal 0.0, H.dms_from("0.0S")
316
+ assert_equal 0.0, H.dms_from("0'")
317
+ assert_equal 0.0, H.dms_from("-0.00'")
318
+ assert_equal 0.0, H.dms_from("-0.00\"")
319
+ assert_equal 0.0, H.dms_from("0.00\"")
320
+
321
+ assert_raise(ArgumentError){H.dms_from("zdfseer")}
322
+ assert_raise(ArgumentError){H.dms_from("++0.3")}
323
+ assert_raise(ArgumentError){H.dms_from("+-0.3")}
324
+
325
+ assert_equal 41.508473, H.dms_from("41° 30min 30.5028\" N", :min_seps=>'min')
326
+ assert_equal 41.508473, H.dms_from("41° 30' 30.5028sec N", :sec_seps=>'sec')
327
+ assert_equal -41.508473, H.dms_from("41d 30m 30.5028s S", :sec_seps=>'s', :min_seps=>'m', :deg_seps=>'d')
328
+ assert_equal -41.508473, H.dms_from("41d 30m 30.5028sS", :sec_seps=>'s', :min_seps=>'m', :deg_seps=>'d')
329
+ assert_equal -41.508473, H.dms_from("S41d 30m 30.5028s", :sec_seps=>'s', :min_seps=>'m', :deg_seps=>'d')
330
+ assert_equal 41.508473, H.dms_from("41d 30m 30.5028s N", :sec_seps=>'s', :min_seps=>'m', :deg_seps=>'d')
331
+ assert_equal 41.508473, H.dms_from("41d 30m 30.5028sN", :sec_seps=>'s', :min_seps=>'m', :deg_seps=>'d')
332
+ assert_equal -41.508473, H.dms_from("-41d 30m 30.5028s", :sec_seps=>'s', :min_seps=>'m', :deg_seps=>'d')
333
+ assert_equal -41.508473, H.dms_from("41d 30m 30.5028sX", :sec_seps=>'s', :min_seps=>'m', :deg_seps=>'d', :south=>'X')
334
+ assert_equal -41.508473, H.dms_from("41d 30m 30.5028s X", :sec_seps=>'s', :min_seps=>'m', :deg_seps=>'d', :south=>'X')
335
+ assert_equal -41.508473, H.dms_from("41 30m 30.5028s X", :sec_seps=>'s', :min_seps=>'m', :deg_seps=>'d', :south=>'X')
336
+
337
+ end
338
+
339
+ should "format as dms" do
340
+ assert_equal "41° 30' 30.5028\"", H.dms_to(41.508473, :prefix=>false)
341
+ assert_equal "41° 30' 30.5028\"", H.dms_to(41.508473, :prefix=>true)
342
+ assert_equal "-41° 30' 30.5028\"", H.dms_to(-41.508473, :prefix=>false)
343
+ assert_equal "-41° 30' 30.5028\"", H.dms_to(-41.508473, :prefix=>true)
344
+ assert_equal "41° 30' 30.5028\" N", H.dms_to(41.508473, :prefix=>false, :latitude=>true)
345
+ assert_equal "N 41° 30' 30.5028\"", H.dms_to(41.508473, :prefix=>true, :latitude=>true)
346
+ assert_equal "41° 30' 30.5028\" S", H.dms_to(-41.508473, :prefix=>false, :latitude=>true)
347
+ assert_equal "S 41° 30' 30.5028\"", H.dms_to(-41.508473, :prefix=>true, :latitude=>true)
348
+ assert_equal "41° 30' 30.5028\" E", H.dms_to(41.508473, :prefix=>false, :longitude=>true)
349
+ assert_equal "E 41° 30' 30.5028\"", H.dms_to(41.508473, :prefix=>true, :longitude=>true)
350
+ assert_equal "41° 30' 30.5028\" W", H.dms_to(-41.508473, :prefix=>false, :longitude=>true)
351
+ assert_equal "W 41° 30' 30.5028\"", H.dms_to(-41.508473, :prefix=>true, :longitude=>true)
352
+ assert_equal "41° 30' N", H.dms_to(41.5, :prefix=>false, :latitude=>true)
353
+ assert_equal "41° N", H.dms_to(41.0, :prefix=>false, :latitude=>true)
354
+ assert_equal "41° N", H.dms_to(41, :prefix=>false, :latitude=>true)
355
+
356
+ assert_equal "41° 30' 30.50\"", H.dms_to(41.508473, :prefix=>false, :precision=>2)
357
+ assert_equal "41° 30' 30.503\"", H.dms_to(41.508473, :prefix=>false, :precision=>3)
358
+
359
+ end
360
+
361
+
83
362
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: modalh
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.0.5
4
+ version: 1.1.1
5
5
  prerelease:
6
6
  platform: ruby
7
7
  authors:
@@ -9,7 +9,7 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2012-05-08 00:00:00.000000000 Z
12
+ date: 2012-05-10 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: units-system
@@ -162,7 +162,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
162
162
  version: '0'
163
163
  segments:
164
164
  - 0
165
- hash: -230677022647937802
165
+ hash: -1742349848663810765
166
166
  required_rubygems_version: !ruby/object:Gem::Requirement
167
167
  none: false
168
168
  requirements: