lib/progress_bar.rb in progress_bar-0.1.0 vs lib/progress_bar.rb in progress_bar-0.2.0
- old
+ new
@@ -1,72 +1,156 @@
require 'options'
require 'highline'
-require File.join(File.dirname(__FILE__), 'progress_bar', 'time_formatter')
-require File.join(File.dirname(__FILE__), 'progress_bar', 'meter')
-require File.join(File.dirname(__FILE__), 'progress_bar', 'meters')
-
class ProgressBar
- attr_accessor :count, :max, :start
+ attr_accessor :count, :max, :start, :meters
- def initialize *args, &block
- args, options = Options.parse args
+ def initialize(max = 100, meters = :all)
- @count = options[:count] || 0
- @max = options[:max] || 100
- @start = Time.now
+ @count = 0
+ @max = max
+ @start = Time.now
+ if meters == :all
+ @meters = [:bar, :counter, :percentage, :elapsed, :eta, :rate]
+ else
+ @meters = meters
+ end
+
@hl = HighLine.new
end
- def increment!
- self.count = count.succ
+ def increment!(count = 1)
+ self.count += count
write
end
def write
clear!
print to_s
end
- def bar(width = terminal_width)
- Bar.new(count, max, width)
+ def remaining
+ max - count
end
- def counter
- Counter.new(count, max)
+ def ratio
+ count.to_f / max
end
def percentage
- Percentage.new(count, max)
+ ratio * 100
end
def elapsed
- Elapsed.new(start)
+ Time.now - start
end
+ def rate
+ if count > 0
+ count / elapsed
+ else
+ 0
+ end
+ end
+
def eta
- ETA.new(start, count, max)
+ remaining / rate
end
def to_s
- width = terminal_width -
- (counter.width + 1) -
- (percentage.width + 1) -
- (elapsed.width + 1) -
- (eta.width + 1)
- "#{bar(width)} #{counter} #{percentage} #{elapsed} #{eta}"
+ meters.inject("") do |text, meter|
+ text << render(meter) + " "
+ end.strip
end
protected
def clear!
print "\r"
end
+ def render(meter)
+ send(:"render_#{meter}")
+ end
+
+ def width_of(meter)
+ send(:"#{meter}_width")
+ end
+
+ def render_bar
+ "[" +
+ "#" * (ratio * (bar_width - 2)).ceil +
+ " " * ((1-ratio) * (bar_width - 2)).floor +
+ "]"
+ end
+
+ def render_counter
+ "[%#{max.to_s.length}i/%i]" % [count, max]
+ end
+
+ def render_percentage
+ format = (max % 10 == 0 ? "%3i" : "%6.2f")
+ "[#{format}%%]" % percentage
+ end
+
+ def render_elapsed
+ "[#{format_interval(elapsed)}]"
+ end
+
+ def render_eta
+ "[#{format_interval(eta)}]"
+ end
+
+ def render_rate
+ "[%.2f/s]" % rate
+ end
+
def terminal_width
@hl.output_cols.to_i
+ end
+
+ def bar_width
+ terminal_width - non_bar_width
+ end
+
+ def non_bar_width
+ meters.reject { |m| m == :bar }.inject(0) do |width, meter|
+ width += width_of(meter) + 1
+ end
+ end
+
+ def counter_width # [ 1/100]
+ max.to_s.length * 2 + 3
+ end
+
+ def percentage_width
+ if max == 100 # [ 24%]
+ 6
+ else # [ 24.0%]
+ 8
+ end
+ end
+
+ def elapsed_width
+ format_interval(elapsed).length + 2
+ end
+
+ def eta_width
+ format_interval(eta).length + 2
+ end
+
+ def rate_width # [ 23.45/s]
+ render_rate.length
+ end
+
+ def format_interval(interval)
+ if interval > 3600
+ "%02i:%02i:%02i" % [interval/3600, interval%3600/60, interval%60]
+ else
+ "%02i:%02i" % [interval/60, interval%60]
+ end
end
end