timerizer 0.2.1 → 0.3.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 0356b2737bb29434b5946aaeefd72a6d031fed12
4
- data.tar.gz: 4ceffb7da4b98e9b149f589dccd04c9486edcd7c
3
+ metadata.gz: 4180c0ffb871e50a47486d122ae17fc42f37cab8
4
+ data.tar.gz: dad648d7c6fb1f996b61d5aa1c55a7c2637abc52
5
5
  SHA512:
6
- metadata.gz: 11e0ee504f1b44ec22a1364ea9395602727b29050cf9dd8386bcdee8491a053ca2e7608e3a033f469d3bd4b59cc8d3a5a14e8bb1436ebe6da4921183f6ed908a
7
- data.tar.gz: 5f45158efea1cdfae177b0460388fd489062bf8e75df7c3ab2ae8c12513a4826d844bf1f5e8469b72fc0528a6e34996f75adf3d85e425553c6641fabe49af712
6
+ metadata.gz: 369ea12d3065905306b0649f81b6517fe49d50cd2ddd601cb7d7132571ea07b21846760bc24e75b3dee56aab841c7b42a6107f54283472e014905910ba1bbca5
7
+ data.tar.gz: 02487b58f59677d6cf481f3a3a78a6fe10f04bb598a67a445e8e1e81cb73395267526913041a53c95477882f3bd7fe95868da9a2c190bf13791775b31b4a1510
data/lib/timerizer.rb CHANGED
@@ -1,621 +1,7 @@
1
- require 'date'
1
+ require "date"
2
+ require_relative "./timerizer/core"
2
3
 
3
- # Represents a relative amount of time. For example, '`5 days`', '`4 years`', and '`5 years, 4 hours, 3 minutes, 2 seconds`' are all RelativeTimes.
4
- class RelativeTime
5
- @@units = {
6
- :second => :seconds,
7
- :minute => :minutes,
8
- :hour => :hours,
9
- :day => :days,
10
- :week => :weeks,
11
- :month => :months,
12
- :year => :years,
13
- :decade => :decades,
14
- :century => :centuries,
15
- :millennium => :millennia
16
- }
17
-
18
- @@in_seconds = {
19
- :second => 1,
20
- :minute => 60,
21
- :hour => 3600,
22
- :day => 86400,
23
- :week => 604800
24
- }
25
-
26
- @@in_months = {
27
- :month => 1,
28
- :year => 12,
29
- :decade => 120,
30
- :century => 1200,
31
- :millennium => 12000
32
- }
33
-
34
- # Average amount of time in a given unit. Used internally within the {#average} and {#unaverage} methods.
35
- @@average_seconds = {
36
- :month => 2629746,
37
- :year => 31556952
38
- }
39
-
40
- # Default syntax formats that can be used with #to_s
41
- # @see #to_s
42
- @@syntaxes = {
43
- :micro => {
44
- :units => {
45
- :seconds => 's',
46
- :minutes => 'm',
47
- :hours => 'h',
48
- :days => 'd',
49
- :weeks => 'w',
50
- :months => 'mn',
51
- :years => 'y',
52
- },
53
- :separator => '',
54
- :delimiter => ' ',
55
- :count => 1
56
- },
57
- :short => {
58
- :units => {
59
- :seconds => 'sec',
60
- :minutes => 'min',
61
- :hours => 'hr',
62
- :days => 'd',
63
- :weeks => 'wk',
64
- :months => 'mn',
65
- :years => 'yr',
66
- :centuries => 'ct',
67
- :millenia => 'ml'
68
- },
69
- :separator => '',
70
- :delimiter => ' ',
71
- :count => 2
72
- },
73
- :long => {
74
- :units => {
75
- :seconds => ['second', 'seconds'],
76
- :minutes => ['minute', 'minutes'],
77
- :hours => ['hour', 'hours'],
78
- :days => ['day', 'days'],
79
- :weeks => ['week', 'weeks'],
80
- :months => ['month', 'months'],
81
- :years => ['year', 'years'],
82
- :centuries => ['century', 'centuries'],
83
- :millennia => ['millenium', 'millenia'],
84
- }
85
- }
86
- }
87
-
88
- # All potential units. Key is the unit name, and the value is its plural form.
89
- def self.units
90
- @@units
91
- end
92
-
93
- # Unit values in seconds. If a unit is not present in this hash, it is assumed to be in the {@@in_months} hash.
94
- def self.units_in_seconds
95
- @@in_seconds
96
- end
97
-
98
- # Unit values in months. If a unit is not present in this hash, it is assumed to be in the {@@in_seconds} hash.
99
- def self.units_in_months
100
- @@in_months
101
- end
102
-
103
- # Initialize a new instance of RelativeTime.
104
- # @overload new(hash)
105
- # @param [Hash] units The base units to initialize with
106
- # @option units [Integer] :seconds The number of seconds
107
- # @option units [Integer] :months The number of months
108
- # @overload new(count, unit)
109
- # @param [Integer] count The number of units to initialize with
110
- # @param [Symbol] unit The unit to initialize. See {RelativeTime#units}
111
- def initialize(count = 0, unit = :second)
112
- if count.is_a? Hash
113
- units = count
114
- units.default = 0
115
- @seconds, @months = units.values_at(:seconds, :months)
116
- else
117
- @seconds = @months = 0
118
-
119
- if @@in_seconds.has_key?(unit)
120
- @seconds = count * @@in_seconds.fetch(unit)
121
- elsif @@in_months.has_key?(unit)
122
- @months = count * @@in_months.fetch(unit)
123
- end
124
- end
125
- end
126
-
127
- # Compares two RelativeTimes to determine if they are equal
128
- # @param [RelativeTime] time The RelativeTime to compare
129
- # @return [Boolean] True if both RelativeTimes are equal
130
- # @note Be weary of rounding; this method compares both RelativeTimes' base units
131
- def ==(time)
132
- if time.is_a?(RelativeTime)
133
- @seconds == time.get(:seconds) && @months == time.get(:months)
134
- else
135
- false
136
- end
137
- end
138
-
139
- # Return the number of base units in a RelativeTime.
140
- # @param [Symbol] unit The unit to return, either :seconds or :months
141
- # @return [Integer] The requested unit count
142
- # @raise [ArgumentError] Unit requested was not :seconds or :months
143
- def get(unit)
144
- if unit == :seconds
145
- @seconds
146
- elsif unit == :months
147
- @months
148
- else
149
- raise ArgumentError
150
- end
151
- end
152
-
153
- # Determines the time between RelativeTime and the given time.
154
- # @param [Time] time The initial time.
155
- # @return [Time] The difference between the current RelativeTime and the given time
156
- # @example 5 hours before January 1st, 2000 at noon
157
- # 5.minutes.before(Time.new(2000, 1, 1, 12, 00, 00))
158
- # => 2000-01-01 11:55:00 -0800
159
- # @see #ago
160
- # @see #after
161
- # @see #from_now
162
- def before(time)
163
- time = time.to_time - @seconds
164
-
165
- new_month = time.month - self.months
166
- new_year = time.year - self.years
167
- while new_month < 1
168
- new_month += 12
169
- new_year -= 1
170
- end
171
- if Date.valid_date?(new_year, new_month, time.day)
172
- new_day = time.day
173
- else
174
- new_day = Date.new(new_year, new_month).days_in_month
175
- end
176
-
177
- new_time = Time.new(
178
- new_year, new_month, new_day,
179
- time.hour, time.min, time.sec
180
- )
181
- Time.at(new_time.to_i, time.nsec/1000)
182
- end
183
-
184
- # Return the time between the RelativeTime and the current time.
185
- # @return [Time] The difference between the current RelativeTime and Time#now
186
- # @see #before
187
- def ago
188
- self.before(Time.now)
189
- end
190
-
191
- # Return the time after the given time according to the current RelativeTime.
192
- # @param [Time] time The starting time
193
- # @return [Time] The time after the current RelativeTime and the given time
194
- # @see #before
195
- def after(time)
196
- time = time.to_time + @seconds
197
-
198
- new_year = time.year + self.years
199
- new_month = time.month + self.months
200
- while new_month > 12
201
- new_year += 1
202
- new_month -= 12
203
- end
204
- if Date.valid_date?(new_year, new_month, time.day)
205
- new_day = time.day
206
- else
207
- new_day = Date.new(new_year, new_month).days_in_month
208
- end
209
-
210
-
211
- new_time = Time.new(
212
- new_year, new_month, new_day,
213
- time.hour, time.min, time.sec
214
- )
215
- Time.at(new_time.to_i, time.nsec/1000.0)
216
- end
217
-
218
- # Return the time after the current time and the RelativeTime.
219
- # @return [Time] The time after the current time
220
- def from_now
221
- self.after(Time.now)
222
- end
223
-
224
- @@units.each do |unit, plural|
225
- in_method = "in_#{plural}"
226
- count_method = plural
227
- superior_unit = @@units.keys.index(unit) + 1
228
-
229
- if @@in_seconds.has_key? unit
230
- class_eval "
231
- def #{in_method}
232
- @seconds / #{@@in_seconds[unit]}
233
- end
234
- "
235
- elsif @@in_months.has_key? unit
236
- class_eval "
237
- def #{in_method}
238
- @months / #{@@in_months[unit]}
239
- end
240
- "
241
- end
242
-
243
- in_superior = "in_#{@@units.values[superior_unit]}"
244
- count_superior = @@units.keys[superior_unit]
245
-
246
-
247
- class_eval "
248
- def #{count_method}
249
- time = self.#{in_method}
250
- if @@units.length > #{superior_unit}
251
- time -= self.#{in_superior}.#{count_superior}.#{in_method}
252
- end
253
- time
254
- end
255
- "
256
- end
257
-
258
- # Average second-based units to month-based units.
259
- # @return [RelativeTime] The averaged RelativeTime
260
- # @example
261
- # 5.weeks.average
262
- # => 1 month, 4 days, 13 hours, 30 minutes, 54 seconds
263
- # @see #average!
264
- # @see #unaverage
265
- def average
266
- if @seconds > 0
267
- months = (@seconds / @@average_seconds[:month])
268
- seconds = @seconds - months.months.unaverage.get(:seconds)
269
- RelativeTime.new(
270
- :seconds => seconds,
271
- :months => months + @months
272
- )
273
- else
274
- self
275
- end
276
- end
277
-
278
- # Destructively average second-based units to month-based units.
279
- # @see #average
280
- def average!
281
- averaged = self.average
282
- @seconds = averaged.get(:seconds)
283
- @months = averaged.get(:months)
284
- self
285
- end
286
-
287
- # Average month-based units to second-based units.
288
- # @return [RelativeTime] the unaveraged RelativeTime.
289
- # @example
290
- # 1.month.unaverage
291
- # => 4 weeks, 2 days, 10 hours, 29 minutes, 6 seconds
292
- # @see #average
293
- # @see #unaverage!
294
- def unaverage
295
- seconds = @@average_seconds[:month] * @months
296
- seconds += @seconds
297
- RelativeTime.new(:seconds => seconds)
298
- end
299
-
300
- # Destructively average month-based units to second-based units.
301
- # @see #unaverage
302
- def unaverage!
303
- unaveraged = self.average
304
- @seconds = unaverage.get(:seconds)
305
- @months = unaverage.get(:months)
306
- self
307
- end
308
-
309
- # Add two {RelativeTime}s together.
310
- # @raise ArgumentError Argument isn't a {RelativeTime}
311
- # @see #-
312
- def +(time)
313
- raise ArgumentError unless time.is_a?(RelativeTime)
314
- RelativeTime.new({
315
- :seconds => @seconds + time.get(:seconds),
316
- :months => @months + time.get(:months)
317
- })
318
- end
319
-
320
- # Find the difference between two {RelativeTime}s.
321
- # @raise ArgumentError Argument isn't a {RelativeTime}
322
- # @see #+
323
- def -(time)
324
- raise ArgumentError unless time.is_a?(RelativeTime)
325
- RelativeTime.new({
326
- :seconds => @seconds - time.get(:seconds),
327
- :months => @months - time.get(:months)
328
- })
329
- end
330
-
331
- # Converts {RelativeTime} to {WallClock}
332
- # @return [WallClock] {RelativeTime} as {WallClock}
333
- # @example
334
- # (17.hours 30.minutes).to_wall
335
- # # => 5:30:00 PM
336
- def to_wall
337
- raise WallClock::TimeOutOfBoundsError if @months > 0
338
- WallClock.new(:second => @seconds)
339
- end
340
-
341
- # Convert {RelativeTime} to a human-readable format.
342
- # @overload to_s(syntax)
343
- # @param [Symbol] syntax The syntax from @@syntaxes to use
344
- # @overload to_s(hash)
345
- # @param [Hash] hash The custom hash to use
346
- # @option hash [Hash] :units The unit names to use. See @@syntaxes for examples
347
- # @option hash [Integer] :count The maximum number of units to output. `1` would output only the unit of greatest example (such as the hour value in `1.hour 3.minutes 2.seconds`).
348
- # @option hash [String] :separator The separator to use in between a unit and its value
349
- # @option hash [String] :delimiter The delimiter to use in between different unit-value pairs
350
- # @example
351
- # (14.months 49.hours).to_s
352
- # => 2 years, 2 months, 3 days, 1 hour
353
- # (1.day 3.hours 4.minutes).to_s(:short)
354
- # => 1d 3hr
355
- # @raise KeyError Symbol argument isn't in @@syntaxes
356
- # @raise ArgumentError Argument isn't a hash (if not a symbol)
357
- # @see @@syntaxes
358
- def to_s(syntax = :long)
359
- if syntax.is_a? Symbol
360
- syntax = @@syntaxes.fetch(syntax)
361
- end
362
-
363
- raise ArgumentError unless syntax.is_a? Hash
364
- times = []
365
-
366
- if syntax[:count].nil? || syntax[:count] == :all
367
- syntax[:count] = @@units.count
368
- end
369
- units = syntax.fetch(:units)
370
-
371
- count = 0
372
- units = Hash[units.to_a.reverse]
373
- units.each do |unit, (singular, plural)|
374
- if count < syntax.fetch(:count)
375
- time = self.respond_to?(unit) ? self.send(unit) : 0
376
-
377
- if time > 1 && !plural.nil?
378
- times << [time, plural]
379
- count += 1
380
- elsif time > 0
381
- times << [time, singular]
382
- count += 1
383
- end
384
- end
385
- end
386
-
387
- times.map do |time|
388
- time.join(syntax[:separator] || ' ')
389
- end.join(syntax[:delimiter] || ', ')
390
- end
391
- end
392
-
393
- # Represents a time, but not a date. '`7:00 PM`' would be an example of a WallClock object
394
- class WallClock
395
- # Represents an error where an invalid meridiem was passed to WallClock.
396
- # @see #new
397
- class InvalidMeridiemError < ArgumentError; end
398
- # Represents an error where a time beyond 24 hours was passed to WallClock.
399
- # @see #new
400
- class TimeOutOfBoundsError < ArgumentError; end
401
-
402
- # Initialize a new instance of WallClock
403
- # @overload new(hash)
404
- # @param [Hash] units The units to initialize with
405
- # @option units [Integer] :hour The hour to initialize with
406
- # @option units [Integer] :minute The minute to initialize with
407
- # @option units [Integer] :second The second to initialize with
408
- # @overload new(hour, minute, meridiem)
409
- # @param [Integer] hour The hour to initialize with
410
- # @param [Integer] minute The minute to initialize with
411
- # @param [Symbol] meridiem The meridiem to initialize with (`:am` or `:pm`)
412
- # @overload new(hour, minute, second, meridiem)
413
- # @param [Integer] hour The hour to initialize with
414
- # @param [Integer] minute The minute to initialize with
415
- # @param [Integer] second The second to initialize with
416
- # @param [Symbol] meridiem The meridiem to initialize with (`:am` or `:pm`)
417
- # @overload new(seconds)
418
- # @param [Integer] seconds The number of seconds to initialize with (for use with #to_i)
419
- # @raise InvalidMeridiemError Meridiem is not `:am` or `:pm`
420
- def initialize(hour = nil, minute = nil, second = 0, meridiem = :am)
421
- units = nil
422
- if hour.is_a?(Integer) && minute.nil?
423
- units = {:second => hour}
424
- elsif hour.is_a?(Hash)
425
- units = hour
426
- end
427
-
428
- if !units.nil?
429
- second = units[:second] || 0
430
- minute = units[:minute] || 0
431
- hour = units[:hour] || 0
432
- else
433
- if second.is_a?(String) || second.is_a?(Symbol)
434
- meridiem = second
435
- second = 0
436
- end
437
-
438
- meridiem = meridiem.downcase.to_sym
439
- if !(meridiem == :am || meridiem == :pm)
440
- raise InvalidMeridiemError
441
- elsif meridiem == :pm && hour > 12
442
- raise TimeOutOfBoundsError, "hour must be <= 12 for PM"
443
- elsif hour >= 24 || minute >= 60 || second >= 60
444
- raise TimeOutOfBoundsError
445
- end
446
-
447
- hour += 12 if (meridiem == :pm and !(hour == 12))
448
- end
449
-
450
- @seconds =
451
- RelativeTime.units_in_seconds.fetch(:hour) * hour +
452
- RelativeTime.units_in_seconds.fetch(:minute) * minute +
453
- second
454
-
455
- if @seconds >= RelativeTime.units_in_seconds.fetch(:day)
456
- raise TimeOutOfBoundsError
457
- end
458
- end
459
-
460
- # Takes a string and turns it into a WallClock time
461
- # @param [String] string The string to convert
462
- # @return [WallClock] The time as a WallClock
463
- # @example
464
- # WallClock.from_string("10:30 PM")
465
- # # => 10:30:00 PM
466
- # WallClock.from_string("13:01:23")
467
- # # => 1:01:23 PM
468
- # @see #to_s
469
- def self.from_string(string)
470
- time, meridiem = string.split(' ', 2)
471
- hour, minute, second = time.split(':', 3)
472
- WallClock.new(hour.to_i, minute.to_i, second.to_i || 0, meridiem || :am)
473
- end
474
-
475
- # Returns the time of the WallClock on a date
476
- # @param [Date] date The date to apply the time on
477
- # @return [Time] The time after the given date
478
- # @example yesterday at 5:00
479
- # time = WallClock.new(5, 00, :pm)
480
- # time.on(Date.yesterday)
481
- # => 2000-1-1 17:00:00 -0800
482
- def on(date)
483
- date.to_date.to_time + @seconds
484
- end
485
-
486
- # Comparse two {WallClock}s.
487
- # @return [Boolean] True if the WallClocks are identical
488
- def ==(time)
489
- if time.is_a? WallClock
490
- self.in_seconds == time.in_seconds
491
- else
492
- false
493
- end
494
- end
495
-
496
- # Get the time of the WallClock, in seconds
497
- # @return [Integer] The total time of the WallClock, in seconds
498
- def in_seconds
499
- @seconds
500
- end
501
-
502
- # Get the time of the WallClock, in minutes
503
- # @return [Integer] The total time of the WallClock, in minutes
504
- def in_minutes
505
- @seconds / RelativeTime.units_in_seconds[:minute]
506
- end
507
-
508
- # Get the time of the WallClock, in hours
509
- # @return [Integer] The total time of the WallClock, in hours
510
- def in_hours
511
- @seconds / RelativeTime.units_in_seconds[:hour]
512
- end
513
-
514
- # Get the second of the WallClock.
515
- # @return [Integer] The second component of the WallClock
516
- def second
517
- self.to_relative.seconds
518
- end
519
-
520
- # Get the minute of the WallClock.
521
- # @return [Integer] The minute component of the WallClock
522
- def minute
523
- self.to_relative.minutes
524
- end
525
-
526
- # Get the hour of the WallClock.
527
- # @param [Symbol] system The houring system to use (either `:twelve_hour` or `:twenty_four_hour`; default `:twenty_four_hour`)
528
- # @return [Integer] The hour component of the WallClock
529
- def hour(system = :twenty_four_hour)
530
- hour = self.to_relative.hours
531
- if system == :twelve_hour
532
- if hour == 0
533
- 12
534
- elsif hour > 12
535
- hour - 12
536
- else
537
- hour
538
- end
539
- elsif (system == :twenty_four_hour)
540
- hour
541
- else
542
- raise ArgumentError, "system should be :twelve_hour or :twenty_four_hour"
543
- end
544
- end
545
-
546
- # Get the meridiem of the WallClock.
547
- # @return [Symbol] The meridiem (either `:am` or `:pm`)
548
- def meridiem
549
- if self.hour > 12 || self.hour == 0
550
- :pm
551
- else
552
- :am
553
- end
554
- end
555
-
556
- # Converts self to {WallClock}
557
- # @see Time#to_wall
558
- def to_wall
559
- self
560
- end
561
-
562
- # Converts {WallClock} to {RelativeTime}
563
- # @return [RelativeTime] {WallClock} as {RelativeTime}
564
- # @example
565
- # time = WallClock.new(5, 30, :pm)
566
- # time.to_relative
567
- # => 5 hours, 30 minutes
568
- def to_relative
569
- @seconds.seconds
570
- end
571
-
572
- # Get the time of the WallClock in a more portable format (for a database, for example)
573
- # @see #in_seconds
574
- def to_i
575
- self.in_seconds
576
- end
577
-
578
- # Convert {WallClock} to a human-readable format.
579
- # @param [Symbol] system The hour system to use (`:twelve_hour` or `:twenty_four_hour`; default `:twelve_hour`)
580
- # @param [Hash] options Extra options for the string to use
581
- # @option options [Boolean] :use_seconds Whether or not to include seconds in the conversion to a string
582
- # @option options [Boolean] :include_meridian Whether or not to include the meridian for a twelve-hour time
583
- # @example
584
- # time = WallClock.new(5, 37, 41, :pm)
585
- # time.to_s
586
- # => "5:37:41 PM"
587
- # time.to_s(:twenty_four_hour, :use_seconds => true)
588
- # => "17:37:41"
589
- # time.to_s(:twelve_hour, :use_seconds => false, :include_meridiem => false)
590
- # => "5:37"
591
- # time.to_s(:twenty_four_hour, :use_seconds =>false)
592
- # => "17:37"
593
- # @raise ArgumentError Argument isn't a proper system
594
- def to_s(system = :twelve_hour, options = {})
595
- options = {:use_seconds => true, :include_meridiem => true}.merge(options)
596
- pad = "%02d"
597
- meridiem = self.meridiem.to_s.upcase
598
- hour = self.hour(system)
599
- minute = pad % self.minute
600
- second = pad % self.second
601
-
602
- string = [hour, minute].join(':')
603
- if options[:use_seconds]
604
- string = [string, second].join(':')
605
- end
606
-
607
- case system
608
- when :twelve_hour
609
- options[:include_meridiem] ? [string, meridiem].join(' ') : string
610
- when :twenty_four_hour
611
- string
612
- else
613
- raise ArgumentError, "system should be :twelve_hour or :twenty_four_hour"
614
- end
615
- end
616
- end
617
-
618
- # {Time} class monkeywrenched with {RelativeTime} support.
4
+ # {Time} class monkey-patched with {Timerizer::Duration} support.
619
5
  class Time
620
6
  # Represents an error where two times were expected to be in the future, but were in the past.
621
7
  # @see #until
@@ -650,7 +36,7 @@ class Time
650
36
 
651
37
  alias_method :add, :+
652
38
  def +(time)
653
- if time.is_a? RelativeTime
39
+ if time.is_a?(Timerizer::Duration)
654
40
  time.after(self)
655
41
  else
656
42
  self.add(time)
@@ -659,7 +45,7 @@ class Time
659
45
 
660
46
  alias_method :subtract, :-
661
47
  def -(time)
662
- if time.is_a? RelativeTime
48
+ if time.is_a?(Timerizer::Duration)
663
49
  time.before(self)
664
50
  else
665
51
  self.subtract(time)
@@ -668,7 +54,7 @@ class Time
668
54
 
669
55
  # Calculates the time until a given time
670
56
  # @param [Time] time The time until now to calculate
671
- # @return [RelativeTime] The time until the provided time
57
+ # @return [Duration] The time until the provided time
672
58
  # @raise[TimeIsInThePastException] The provided time is in the past
673
59
  # @example
674
60
  # Time.until(Time.new(2012, 12, 25))
@@ -683,7 +69,7 @@ class Time
683
69
 
684
70
  # Calculates the time since a given time
685
71
  # @param [Time] time The time to calculate since now
686
- # @return [RelativeTime] The time since the provided time
72
+ # @return [Duration] The time since the provided time
687
73
  # @raise[TimeIsInTheFutureException] The provided time is in the future
688
74
  # @example
689
75
  # Time.since(Time.new(2011, 10, 31))
@@ -699,7 +85,7 @@ class Time
699
85
  # Calculate the amount of time between two times.
700
86
  # @param [Time] time1 The initial time
701
87
  # @param [Time] time2 The final time
702
- # @return [RelativeTime] Calculated time between time1 and time2
88
+ # @return [Duration] Calculated time between time1 and time2
703
89
  # @example
704
90
  # Time.between(1.minute.ago, 1.hour.ago)
705
91
  # => 59.minutes
@@ -709,7 +95,7 @@ class Time
709
95
  def self.between(time1, time2)
710
96
  time_between = (time2.to_time - time1.to_time).abs
711
97
 
712
- RelativeTime.new(time_between.round)
98
+ Timerizer::Duration.new(seconds: time_between.round)
713
99
  end
714
100
 
715
101
  # Convert {Time} to {Date}.
@@ -727,19 +113,19 @@ class Time
727
113
  self
728
114
  end
729
115
 
730
- # Converts {Time} to {WallClock}
731
- # @return [WallClock] {Time} as {WallClock}
116
+ # Converts {Time} to {Timerizer::WallClock}
117
+ # @return [Timerizer::WallClock] {Time} as {Timerizer::WallClock}
732
118
  # @example
733
119
  # time = Time.now.to_wall
734
120
  # Date.tomorrow.at(time)
735
121
  # => 2000-1-2 13:13:27 -0800
736
122
  # # "Same time tomorrow?"
737
123
  def to_wall
738
- WallClock.new(self.hour, self.min, self.sec)
124
+ Timerizer::WallClock.new(self.hour, self.min, self.sec)
739
125
  end
740
126
  end
741
127
 
742
- # {Date} class monkeywrenched with {RelativeTime} helpers.
128
+ # {Date} class monkey-patched with {Timerizer::Duration} helpers.
743
129
  class Date
744
130
  # Return the number of days in a given month.
745
131
  # @return [Integer] Number of days in the month of the {Date}.
@@ -783,19 +169,66 @@ class Date
783
169
  end
784
170
  end
785
171
 
786
- # Monkeywrenched {Integer} class enabled to return {RelativeTime} objects.
172
+ # Monkey-patched {Integer} class enabled to return {Timerizer::Duration}s.
787
173
  # @example
788
174
  # 5.minutes
789
- # => 5 minutes
790
- # @see {RelativeTime#units}
175
+ # # => 5 minutes
176
+ # @see Timerizer::Duration::UNITS
791
177
  class Integer
792
- RelativeTime.units.each do |unit, plural|
793
- class_eval "
794
- def #{unit}(added_time = RelativeTime.new)
795
- time = RelativeTime.new(self, :#{unit})
796
- time + added_time unless added_time.nil?
178
+ private
179
+
180
+ # @!macro [attach] _define_duration_unit
181
+ # @method $1(other = nil)
182
+ #
183
+ # Return a {Timerizer::Duration} with `self` of the given unit. This
184
+ # method is a helper that is equivalent to
185
+ # `Timerizer::Duration::new($1: self)`.
186
+ #
187
+ # @param [Timerizer::Duration, nil] other Another duration to add to the
188
+ # resulting duration, if present. This argument allows "chaining" multiple
189
+ # durations together, to combine multiple units succiently.
190
+ #
191
+ # @return [Timerizer::Duration] the quantity of the unit in the duration.
192
+ #
193
+ # @see Timerizer::Duration#initialize
194
+ #
195
+ # @example
196
+ # n.$1 == Timerizer::Duration.new($1: n)
197
+ # 5.minutes == Timerizer::Duration.new(minutes: 5)
198
+ # (1.week 1.day) == 8.days # "Chaining" multiple units
199
+ # (n.$1 x.minutes) == (n.$1 + x.minutes)
200
+ def self._define_duration_unit(unit)
201
+ define_method(unit) do |other = nil|
202
+ duration = Timerizer::Duration.new(unit => self)
203
+
204
+ if other.nil?
205
+ duration
206
+ else
207
+ duration + other
797
208
  end
798
- "
799
- alias_method(plural, unit)
209
+ end
800
210
  end
211
+
212
+ public
213
+
214
+ self._define_duration_unit(:seconds)
215
+ self._define_duration_unit(:minutes)
216
+ self._define_duration_unit(:hours)
217
+ self._define_duration_unit(:days)
218
+ self._define_duration_unit(:weeks)
219
+ self._define_duration_unit(:months)
220
+ self._define_duration_unit(:years)
221
+ self._define_duration_unit(:decades)
222
+ self._define_duration_unit(:centuries)
223
+ self._define_duration_unit(:millennia)
224
+ self._define_duration_unit(:second)
225
+ self._define_duration_unit(:minute)
226
+ self._define_duration_unit(:hour)
227
+ self._define_duration_unit(:day)
228
+ self._define_duration_unit(:week)
229
+ self._define_duration_unit(:month)
230
+ self._define_duration_unit(:year)
231
+ self._define_duration_unit(:decade)
232
+ self._define_duration_unit(:century)
233
+ self._define_duration_unit(:millennium)
801
234
  end