A terminal spinner for tasks that have non-deterministic time frame.
TTY::Spinner provides independent spinner component for TTY toolkit.
Installation
Add this line to your application's Gemfile:
gem 'tty-spinner'
And then execute:
$ bundle
Or install it yourself as:
$ gem install tty-spinner
Contents
- 1. Usage
- 2. TTY::Spinner API
- 2.1 spin
- 2.2 auto_spin
- 2.3 run
- 2.4 start
- 2.5 stop
- 2.5.1 success
- 2.5.2 error
- 2.6 update
- 2.7 reset
- 2.8 join
- 3. Configuration
- 3.1 :format
- 3.2 :frames
- 3.3 :interval
- 3.4 :hide_cursor
- 3.5 :clear
- 3.6 :success_mark
- 3.7 :error_mark
- 3.8 :output
- 4. Events
- 4.1 done
- 4.2 success
- 4.3 error
- 5. TTY::Spinner::Multi API
- 5.1 reigster
- 5.2 auto_spin
- 5.2.1 async tasks
- 5.3 stop
- 5.3.1 success
- 5.3.2 error
- 5.4 :style
1. Usage
TTY::Spinner by default uses :classic
type of formatter and requires no paramters:
spinner = TTY::Spinner.new
In addition you can provide a message with :spinner
token and format type you would like for the spinning display:
spinner = TTY::Spinner.new("[:spinner] Loading ...", format: :pulse_2)
spinner.auto_spin # Automatic animation with default interval
sleep(2) # Perform task
spinner.stop('Done!') # Stop animation
This would produce animation in your terminal:
⎺ Loading ...
and when finished output:
_ Loading ... Done!
Use TTY::Spinner::Multi to synchornize multiple spinners:
spinners = TTY::Spinner::Multi.new("[:spinner] top")
sp1 = spinners.register "[:spinner] one"
sp2 = spinners.register "[:spinner] two"
sp1.auto_spin
sp2.auto_spin
sleep(2) # Perform work
sp1.success
sp2.success
which when done will display:
┌[✔]] top
├──[✔] one
└──[✔] two
For more usage examples please see examples directory
2. TTY::Spinner API
2.1 spin
The main workhorse of the spinner is the spin
method.
Looping over spin
method will animate a given spinner.
loop do
spinner.spin
end
2.2 auto_spin
To perform automatic spinning animation use auto_spin
method like so:
spinner.auto_spin
The speed with which the spinning happens is determined by the :interval
parameter. All the spinner formats have their default intervals specified (see).
2.3 run
Use run
with a code block that will automatically display spinning animation while the block executes and finish animation when the block terminates. Optionally you can provide a stop message to display when animation is finished.
spinner.run('Done!') { ... }
2.4 start
In order to set start time or reuse the same spinner after it has stopped, call start
method:
spinner.start
2.5 stop
In order to stop the spinner call stop
. This will finish drawing the spinning animation and return to new line.
spinner.stop
You can further pass a message to print when animation is finished.
spinner.stop('Done!')
2.5.1 success
Use success
call to stop the spinning animation and replace the spinning symbol with checkmark character to indicate successful completion.
spinner = TTY::Spinner.new("[:spinner] Task name")
spinner.success('(successful)')
This will produce:
[✔] Task name (successful)
2.5.2 error
Use error
call to stop the spining animation and replace the spinning symbol with cross character to indicate error completion.
spinner = TTY::Spinner.new("[:spinner] Task name")
spinner.error('(error)')
This will produce:
[✖] Task name (error)
2.6 update
Use update
call to dynamically change label name(s).
Provide an arbitrary token name(s) in the message string, such as :title
spinner = TTY::Spinner.new("[:spinner] :title")
and then pass token name and value:
spinner.update(title: 'Downloading file1')
next start animation:
spinner.run { ... }
# => | Downloading file1
Once animation finishes you can kick start another one with a different name:
spinner.update(title: 'Downloading file2')
spinner.run { ... }
2.7 reset
In order to reset the spinner to its initial frame do:
spinner.reset
2.8 join
One way to wait while the spinning animates is to join the thread started with start
method:
spinner.join
Optionally you can provide timeout:
spinner.join(0.5)
3. Configuration
There are number of configuration options that can be provided to customise the behaviour of a spinner.
3.1 :format
Use one of the predefined spinner styles by passing the formatting token :format
spinner = TTY::Spinner.new(format: :pulse_2)
All spinner formats that TTY::Spinner accepts are defined in /lib/tty/spinner/formats.rb
If you wish to see all available formats in action run the formats.rb
file in examples folder like so:
bundle exec ruby examples/formats.rb
3.2 :frames
If you wish to use custom formatting use the :frames
option with either array
or string
of characters.
spinner = TTY::Spinner.new(frames: [".", "o", "0", "@", "*"])
3.3 :interval
The :interval
option accepts integer
representing number of Hz
units, for instance, frequency of 10 will mean that the spinning animation will be displayed 10 times per second.
spinner = TTY::Spinner.new(interval: 20) # 20 Hz (20 times per second)
3.4 :hide_cursor
Hides cursor when spinning animation performs. Defaults to false
.
spinner = TTY::Spinner.new(hide_cursor: true)
3.5 :clear
After spinner is finished clears its output. Defaults to false
.
spinner = TTY::Spinner.new(clear: true)
3.6 :success_mark
To change marker indicating successful completion use the :success_mark
option:
spinner = TTY::Spinner.new(success_mark: '+')
3.7 :error_mark
To change marker indicating error completion use the :error_mark
option:
spinner = TTY::Spinner.new(error_mark: 'x')
3.8 :output
To change where data is streamed use :output
option like so:
spinner = TTY::Spinner.new(output: $stdout)
The output stream defaults to stderr
.
4. Events
TTY::Spinner emits :done
, :success
and :error
event types when spinner is stopped.
4.1 done
This event is emitted irrespective of the completion method. In order to listen for this event you need to register callback:
spinner.on(:done) { ... }
4.2 success
This event is fired when success
call is made. In order to respond to the event, you need to register callback:
spinner.on(:success) { ... }
4.3 error
This event is fired when error
completion is called. In order to respond to the event, you need to register callback:
spinner.on(:error) { ... }
5. TTY::Spinner::Multi API
5.1 register
Create and register a TTY::Spinner
under the multispinner
new_spinner = multi_spinner.register("[:spinner] Task 1 name", options)
If no options are given it will use the options given to the multi_spinner when it was initialized to create the new spinner. If options are passed, they will override any options given to the multi spinner.
5.2 auto_spin
The multispinner has to have been given a message on initialization.
To perform automatic spinning animation use auto_spin
method like so:
multi_spinner = TTY::Spinner::Multi.new("[:spinner] Top level spinner")
multi_spinner.auto_spin
If you register spinners without any tasks then you will have to manually control when the multi_spinner
finishes by calling stop
, success
or error
. Alternatively you can register spinners with tasks (see async tasks)
The speed with which the spinning happens is determined by the :interval
parameter. All the spinner formats have their default intervals specified (see).
5.2.1 async tasks
In case when you wish to execute async tasks and update individual spinners automatically, in any order, about their task status use #register
and pass additional block parameter with the job to be executed.
For example, create a multi spinner that will track status of all registered spinners:
spinners = TTY::Spinner::Multi.new("[:spinner] top")
and then register spinners with their respective tasks:
spinners.register("[:spinner] one") { |sp| sleep(2); sp.success('yes 2') }
spinners.register("[:spinner] two") { |sp| sleep(3); sp.error('no 2') }
Finally, call #auto_spin
to kick things off:
spinners.auto_spin
5.3 stop
In order to stop the multi spinner call stop
. This will stop the top level spinner, if it exists, and any sub-spinners still spinning.
multi_spinner.stop
5.3.1 success
Use success
call to stop the spinning animation and replace the spinning symbol with checkmark character to indicate successful completion.
This will also call #success
on any sub-spinners that are still spinning.
multi_spinner.success
5.3.2 error
Use error
call to stop the spining animation and replace the spinning symbol with cross character to indicate error completion.
This will also call #error
on any sub-spinners that are still spinning.
multi_spinner.error
5.4 :style
In addition to all configuration options you can style multi spinner like so:
multi_spinner = TTY::Spinner::Multi.new("[:spinner] parent", style: {
top: '. '
middle: '|-> '
bottom: '|__ '
})
Contributing
- Fork it ( https://github.com/piotrmurach/tty-spinner/fork )
- Create your feature branch (
git checkout -b my-new-feature
) - Commit your changes (
git commit -am 'Add some feature'
) - Push to the branch (
git push origin my-new-feature
) - Create a new Pull Request
Copyright
Copyright (c) 2014-2017 Piotr Murach. See LICENSE for further details.