measurement 0.2 → 0.2.1

Sign up to get free protection for your applications and to get access to all the features.
data/CHANGELOG CHANGED
@@ -1,3 +1,5 @@
1
+ v0.2.1 Added methods to Float, Fixnum and String - to_measurement
2
+
1
3
  v0.2 Documentation
2
4
 
3
5
  v0.1 First version
data/lib/measurement.rb CHANGED
@@ -22,6 +22,8 @@ module Measurement
22
22
  # Length.new(10).to_s(:qt, 3) => 0.005qt
23
23
  #
24
24
  class Base
25
+ include Comparable
26
+
25
27
  # Define the base measurement unit. This method accepts
26
28
  # a list of names for the base measurement, followed
27
29
  # by the standard unit options. See #unit
@@ -39,14 +41,33 @@ module Measurement
39
41
  # base unit.
40
42
  #
41
43
  def self.base(*args)
42
- if args.any?
44
+ if args.any? || !@base
43
45
  @base = Unit.new(1.0, *args)
44
46
  add_unit(@base)
47
+ register_measurement
45
48
  else
46
49
  @base
47
50
  end
48
51
  end
49
52
 
53
+ def self.register_measurement
54
+ method_name = name.gsub(/\s/, '_').gsub(/.[A-Z]/) do |s|
55
+ s[0,1] + '_' + s[1,1].downcase
56
+ end.downcase
57
+
58
+ [Fixnum, Float].each do |klass|
59
+ klass.class_eval %Q{
60
+ def to_#{method_name}
61
+ #{name}.new(self)
62
+ end}
63
+ end
64
+
65
+ String.class_eval %Q{
66
+ def to_#{method_name}
67
+ #{name}.parse(self)
68
+ end}
69
+ end
70
+
50
71
  def self.units # :nodoc:
51
72
  @units ||= []
52
73
  end
@@ -70,8 +91,8 @@ module Measurement
70
91
  # * <tt>prefix</tt> - A prefix to use when formatting the unit.
71
92
  # * <tt>suffix</tt> - A suffix to use when formatting the unit.
72
93
  #
73
- def self.unit(scale, *args)
74
- add_unit(Unit.new(scale, *args))
94
+ def self.unit(unit, *args)
95
+ add_unit(Unit.new(unit, *args))
75
96
  end
76
97
 
77
98
  def self.add_unit(unit) # :nodoc:
@@ -91,16 +112,16 @@ module Measurement
91
112
  end
92
113
  end
93
114
 
94
- def self.from(amount, scale) # :nodoc:
95
- fetch_scale(scale).from(amount)
115
+ def self.from(amount, unit) # :nodoc:
116
+ fetch_scale(unit).from(amount)
96
117
  end
97
118
 
98
- def self.to(amount, scale = nil) # :nodoc:
99
- fetch_scale(scale).to(amount)
119
+ def self.to(amount, unit = nil) # :nodoc:
120
+ fetch_scale(unit).to(amount)
100
121
  end
101
122
 
102
- def self.format(amount, scale = nil, precision = 2) #:nodoc:
103
- fetch_scale(scale).format(amount, precision)
123
+ def self.format(amount, unit = nil, precision = 2) #:nodoc:
124
+ fetch_scale(unit).format(amount, precision)
104
125
  end
105
126
 
106
127
  # Parse a string containing this measurement. The string
@@ -114,7 +135,7 @@ module Measurement
114
135
  #
115
136
  # If a valid unit cannot be found an error is raised:
116
137
  #
117
- # Weight.parse("180cm") => Measurement::NoScaleException
138
+ # Weight.parse("180cm") => Measurement::NoUnitException
118
139
  #
119
140
  def self.parse(string)
120
141
  string = string.dup
@@ -122,15 +143,15 @@ module Measurement
122
143
 
123
144
  while string =~ /(\d+(\.\d+)?)([^\d]*)/
124
145
  amount = $1.to_f
125
- scale = $3 && $3.strip
146
+ unit = $3 && $3.strip
126
147
 
127
- if scale && scale.length > 0
128
- scale = find_scale(scale)
148
+ if unit && unit.length > 0
149
+ unit = find_scale(unit)
129
150
 
130
- if scale.nil?
131
- raise NoUnitFoundException.new(scale)
151
+ if unit.nil?
152
+ raise NoUnitFoundException.new(unit)
132
153
  else
133
- base_amount += scale.from(amount)
154
+ base_amount += unit.from(amount)
134
155
  end
135
156
  else
136
157
  base_amount += amount
@@ -142,8 +163,8 @@ module Measurement
142
163
  self.new(base_amount)
143
164
  end
144
165
 
145
- def initialize(amount = 0, scale = nil)
146
- @amount = self.class.from(amount, scale)
166
+ def initialize(amount = 0, unit = nil)
167
+ @amount = self.class.from(amount, unit)
147
168
  end
148
169
 
149
170
  # The base unit as an integer
@@ -155,6 +176,18 @@ module Measurement
155
176
  def to_f
156
177
  @amount.to_f
157
178
  end
179
+
180
+ def <=>(anOther)
181
+ to_f <=> anOther.to_f
182
+ end
183
+
184
+ %w(+ - / *).each do |operator|
185
+ class_eval %Q{
186
+ def #{operator}(anOther)
187
+ self.class.new(self.to_f #{operator} anOther.to_f)
188
+ end
189
+ }
190
+ end
158
191
 
159
192
  # This measurement converted to the specified unit.
160
193
  #
@@ -173,11 +206,11 @@ module Measurement
173
206
 
174
207
  def method_missing(method, *args) # :nodoc:
175
208
  if method.to_s =~ /^(as|in)_(.*)/
176
- scale = $2
177
- if scale =~ /and/
178
- to_s(scale, *args)
209
+ unit = $2
210
+ if unit =~ /and/
211
+ to_s(unit, *args)
179
212
  else
180
- as(scale.to_sym, *args)
213
+ as(unit.to_sym, *args)
181
214
  end
182
215
  else
183
216
  super
data/measurement.gemspec CHANGED
@@ -2,11 +2,11 @@
2
2
 
3
3
  Gem::Specification.new do |s|
4
4
  s.name = %q{measurement}
5
- s.version = "0.2"
5
+ s.version = "0.2.1"
6
6
 
7
7
  s.required_rubygems_version = Gem::Requirement.new(">= 1.2") if s.respond_to? :required_rubygems_version=
8
8
  s.authors = ["Jeremy Wells"]
9
- s.date = %q{2010-02-27}
9
+ s.date = %q{2010-02-28}
10
10
  s.description = %q{A library for holding, converting and formatting measurements}
11
11
  s.email = %q{jemmyw@gmail.com}
12
12
  s.extra_rdoc_files = ["CHANGELOG", "LICENSE", "README.rdoc", "lib/measurement.rb", "lib/measurement/length.rb", "lib/measurement/unit.rb", "lib/measurement/weight.rb"]
@@ -1,6 +1,22 @@
1
1
  require 'spec_helper'
2
2
 
3
3
  describe Measurement::Base do
4
+ describe '::base' do
5
+ it 'should define to_measurement on Fixnum and Float' do
6
+ Length
7
+ 1.to_length.should be_a(Length)
8
+ 1.to_length.to_f.should == 1.0
9
+ 1.5.to_length.should be_a(Length)
10
+ 1.5.to_length.to_f.should == 1.5
11
+ end
12
+
13
+ it 'should define to_measurement on String' do
14
+ Length
15
+ "10cm".to_length.should be_a(Length)
16
+ "10cm".to_length.to_s(:metre, 1).should == "0.1m"
17
+ end
18
+ end
19
+
4
20
  describe '::parse' do
5
21
  it 'should parse in the base unit if no unit is specified' do
6
22
  Length.parse('113').to_f.should == 113.0
@@ -33,6 +49,30 @@ describe Measurement::Base do
33
49
  end
34
50
  end
35
51
 
52
+ describe 'operators' do
53
+ before do
54
+ @length_1 = Length.new(1)
55
+ @length_2 = Length.new(2)
56
+ end
57
+
58
+ %w(+ - / *).each do |operator|
59
+ it 'should return a new object of the same type' do
60
+ @length_1.send(operator, @length_2).should be_a(Length)
61
+ end
62
+
63
+ it 'should perform the operator' do
64
+ @value = @length_1.to_f.send(operator, @length_2.to_f)
65
+ @length_1.send(operator, @length_2).to_f.should == @value
66
+ end
67
+ end
68
+ end
69
+
70
+ describe '#<=>' do
71
+ it 'should return the difference between the objects' do
72
+ (Length.new(1) <=> Length.new(2)).should == (1.0 <=> 2.0)
73
+ end
74
+ end
75
+
36
76
  describe '#method_missing' do
37
77
  it 'should call as if passed in_scale' do
38
78
  Length.new(10).in_cm.should == Length.new(10).as(:cm)
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: measurement
3
3
  version: !ruby/object:Gem::Version
4
- version: "0.2"
4
+ version: 0.2.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Jeremy Wells
@@ -9,7 +9,7 @@ autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
11
 
12
- date: 2010-02-27 00:00:00 +13:00
12
+ date: 2010-02-28 00:00:00 +13:00
13
13
  default_executable:
14
14
  dependencies: []
15
15