mirror of https://github.com/containers/podman.git
194 lines
5.0 KiB
Go
194 lines
5.0 KiB
Go
package mpb
|
|
|
|
import (
|
|
"io"
|
|
|
|
"github.com/vbauerster/mpb/decor"
|
|
)
|
|
|
|
// BarOption is a function option which changes the default behavior of a bar.
|
|
type BarOption func(*bState)
|
|
|
|
// AppendDecorators let you inject decorators to the bar's right side.
|
|
func AppendDecorators(appenders ...decor.Decorator) BarOption {
|
|
return func(s *bState) {
|
|
for _, decorator := range appenders {
|
|
if ar, ok := decorator.(decor.AmountReceiver); ok {
|
|
s.amountReceivers = append(s.amountReceivers, ar)
|
|
}
|
|
if sl, ok := decorator.(decor.ShutdownListener); ok {
|
|
s.shutdownListeners = append(s.shutdownListeners, sl)
|
|
}
|
|
s.aDecorators = append(s.aDecorators, decorator)
|
|
}
|
|
}
|
|
}
|
|
|
|
// PrependDecorators let you inject decorators to the bar's left side.
|
|
func PrependDecorators(prependers ...decor.Decorator) BarOption {
|
|
return func(s *bState) {
|
|
for _, decorator := range prependers {
|
|
if ar, ok := decorator.(decor.AmountReceiver); ok {
|
|
s.amountReceivers = append(s.amountReceivers, ar)
|
|
}
|
|
if sl, ok := decorator.(decor.ShutdownListener); ok {
|
|
s.shutdownListeners = append(s.shutdownListeners, sl)
|
|
}
|
|
s.pDecorators = append(s.pDecorators, decorator)
|
|
}
|
|
}
|
|
}
|
|
|
|
// BarID sets bar id.
|
|
func BarID(id int) BarOption {
|
|
return func(s *bState) {
|
|
s.id = id
|
|
}
|
|
}
|
|
|
|
// BarWidth sets bar width independent of the container.
|
|
func BarWidth(width int) BarOption {
|
|
return func(s *bState) {
|
|
s.width = width
|
|
}
|
|
}
|
|
|
|
// BarRemoveOnComplete is a flag, if set whole bar line will be removed
|
|
// on complete event. If both BarRemoveOnComplete and BarClearOnComplete
|
|
// are set, first bar section gets cleared and then whole bar line
|
|
// gets removed completely.
|
|
func BarRemoveOnComplete() BarOption {
|
|
return func(s *bState) {
|
|
s.removeOnComplete = true
|
|
}
|
|
}
|
|
|
|
// BarReplaceOnComplete is indicator for delayed bar start, after the
|
|
// `runningBar` is complete. To achieve bar replacement effect,
|
|
// `runningBar` should has its `BarRemoveOnComplete` option set.
|
|
func BarReplaceOnComplete(runningBar *Bar) BarOption {
|
|
return BarParkTo(runningBar)
|
|
}
|
|
|
|
// BarParkTo same as BarReplaceOnComplete
|
|
func BarParkTo(runningBar *Bar) BarOption {
|
|
return func(s *bState) {
|
|
s.runningBar = runningBar
|
|
}
|
|
}
|
|
|
|
// BarClearOnComplete is a flag, if set will clear bar section on
|
|
// complete event. If you need to remove a whole bar line, refer to
|
|
// BarRemoveOnComplete.
|
|
func BarClearOnComplete() BarOption {
|
|
return func(s *bState) {
|
|
s.barClearOnComplete = true
|
|
}
|
|
}
|
|
|
|
// BarPriority sets bar's priority. Zero is highest priority, i.e. bar
|
|
// will be on top. If `BarReplaceOnComplete` option is supplied, this
|
|
// option is ignored.
|
|
func BarPriority(priority int) BarOption {
|
|
return func(s *bState) {
|
|
s.priority = priority
|
|
}
|
|
}
|
|
|
|
// BarNewLineExtend takes user defined efn, which gets called each
|
|
// render cycle. Any write to provided writer of efn, will appear on
|
|
// new line of respective bar.
|
|
func BarNewLineExtend(efn func(io.Writer, *decor.Statistics)) BarOption {
|
|
return func(s *bState) {
|
|
s.newLineExtendFn = efn
|
|
}
|
|
}
|
|
|
|
// TrimSpace trims bar's edge spaces.
|
|
func TrimSpace() BarOption {
|
|
return func(s *bState) {
|
|
s.trimSpace = true
|
|
}
|
|
}
|
|
|
|
// BarStyle sets custom bar style, default one is "[=>-]<+".
|
|
//
|
|
// '[' left bracket rune
|
|
//
|
|
// '=' fill rune
|
|
//
|
|
// '>' tip rune
|
|
//
|
|
// '-' empty rune
|
|
//
|
|
// ']' right bracket rune
|
|
//
|
|
// '<' reverse tip rune, used when BarReverse option is set
|
|
//
|
|
// '+' refill rune, used when *Bar.SetRefill(int64) is called
|
|
//
|
|
// It's ok to provide first five runes only, for example mpb.BarStyle("╢▌▌░╟")
|
|
func BarStyle(style string) BarOption {
|
|
chk := func(filler Filler) (interface{}, bool) {
|
|
if style == "" {
|
|
return nil, false
|
|
}
|
|
t, ok := filler.(*barFiller)
|
|
return t, ok
|
|
}
|
|
cb := func(t interface{}) {
|
|
t.(*barFiller).setStyle(style)
|
|
}
|
|
return MakeFillerTypeSpecificBarOption(chk, cb)
|
|
}
|
|
|
|
// BarReverse reverse mode, bar will progress from right to left.
|
|
func BarReverse() BarOption {
|
|
chk := func(filler Filler) (interface{}, bool) {
|
|
t, ok := filler.(*barFiller)
|
|
return t, ok
|
|
}
|
|
cb := func(t interface{}) {
|
|
t.(*barFiller).setReverse()
|
|
}
|
|
return MakeFillerTypeSpecificBarOption(chk, cb)
|
|
}
|
|
|
|
// SpinnerStyle sets custom spinner style.
|
|
// Effective when Filler type is spinner.
|
|
func SpinnerStyle(frames []string) BarOption {
|
|
chk := func(filler Filler) (interface{}, bool) {
|
|
if len(frames) == 0 {
|
|
return nil, false
|
|
}
|
|
t, ok := filler.(*spinnerFiller)
|
|
return t, ok
|
|
}
|
|
cb := func(t interface{}) {
|
|
t.(*spinnerFiller).frames = frames
|
|
}
|
|
return MakeFillerTypeSpecificBarOption(chk, cb)
|
|
}
|
|
|
|
// MakeFillerTypeSpecificBarOption makes BarOption specific to Filler's
|
|
// actual type. If you implement your own Filler, so most probably
|
|
// you'll need this. See BarStyle or SpinnerStyle for example.
|
|
func MakeFillerTypeSpecificBarOption(
|
|
typeChecker func(Filler) (interface{}, bool),
|
|
cb func(interface{}),
|
|
) BarOption {
|
|
return func(s *bState) {
|
|
if t, ok := typeChecker(s.filler); ok {
|
|
cb(t)
|
|
}
|
|
}
|
|
}
|
|
|
|
// OptionOnCondition returns option when condition evaluates to true.
|
|
func OptionOnCondition(option BarOption, condition func() bool) BarOption {
|
|
if condition() {
|
|
return option
|
|
}
|
|
return nil
|
|
}
|