学習バンザイITエンジニアの精神安穏日記

ITエンジニアというより、IT系雑務者

Rubyでgemを使わずにプログレスバー

なんとなくgemを使いたくなかったので自前で作った。

require 'io/console/size'

class ProgressBar
  def initialize(finished_count)
    # ref: https://docs.ruby-lang.org/ja/latest/method/IO/i/sync=3d.html
    $stdout.sync = true
    @finished_count = finished_count
  end

  def run(i)
    i = @finished_count if i > @finished_count
    print "\r#{bar(i)} #{display_percent(i)}%"
  end

  private

  # @return [String]
  def bar(i)
    ('#' * bar_width(i)).ljust(max_bar_width)
  end

  # @return [Float]
  def bar_width(i)
    i * max_bar_width.to_f / @finished_count
  end

  # @param  [Integer]
  # @return [String] "100.0%"
  def display_percent(i)
    '%3.1f' % percent(i)
  end

  # param  [Integer]
  # @return [Float] 0 <= n <= 100.0
  def percent(i)
    i * 100.0 / @finished_count
  end

  # @return [Integer]
  def max_bar_width
    console_width - indicator_width
  end

  # @return [Integer]
  def indicator_width
    " 100.0%".length
  end

  # @return [Integer]
  def console_width
    IO.console_size.last
  end
end

使い方

bar = ProgressBar.new(1000)

(0..1000).each do |i|
  sleep 0.001
  bar.run(i)
end

# => ############################################################################################################# 100.0%

参考

めちゃくちゃ参考になりました。 進行状況をプログレスバーで表示 - Qiita