tty-table 0.9.0 → 0.10.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.travis.yml +4 -3
- data/CHANGELOG.md +16 -0
- data/Gemfile +4 -4
- data/README.md +3 -3
- data/appveyor.yml +2 -0
- data/benchmarks/speed.rb +3 -5
- data/examples/alignment.rb +3 -3
- data/examples/basic.rb +2 -2
- data/examples/orientation.rb +13 -0
- data/examples/padding.rb +15 -0
- data/examples/resize.rb +15 -0
- data/lib/tty/table.rb +2 -1
- data/lib/tty/table/border.rb +4 -12
- data/lib/tty/table/column_constraint.rb +15 -7
- data/lib/tty/table/columns.rb +42 -68
- data/lib/tty/table/field.rb +3 -13
- data/lib/tty/table/indentation.rb +9 -20
- data/lib/tty/table/operation/alignment.rb +2 -2
- data/lib/tty/table/operation/padding.rb +3 -3
- data/lib/tty/table/operation/truncation.rb +3 -3
- data/lib/tty/table/operation/wrapped.rb +3 -3
- data/lib/tty/table/operations.rb +3 -14
- data/lib/tty/table/renderer.rb +28 -24
- data/lib/tty/table/renderer/ascii.rb +1 -1
- data/lib/tty/table/renderer/basic.rb +42 -41
- data/lib/tty/table/renderer/unicode.rb +1 -1
- data/lib/tty/table/version.rb +1 -3
- data/spec/unit/border/ascii/rendering_spec.rb +1 -1
- data/spec/unit/border/null/rendering_spec.rb +1 -1
- data/spec/unit/border/unicode/rendering_spec.rb +1 -1
- data/spec/unit/column_constraint/enforce_spec.rb +2 -2
- data/spec/unit/columns/extract_widths_spec.rb +7 -12
- data/spec/unit/columns/total_width_spec.rb +3 -4
- data/spec/unit/indentation/indent_spec.rb +2 -6
- data/spec/unit/operations/new_spec.rb +3 -5
- data/spec/unit/renderer/ascii/padding_spec.rb +29 -0
- data/tty-table.gemspec +3 -4
- metadata +12 -24
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: c5a7d889fe3c0a30613340ff98741bdf6fe60e59
|
4
|
+
data.tar.gz: 41477fe8e7edddf80275eb253c5505efcde49b1b
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 28d1f65541cd25ba4dab63f85cdc66294a67e485ca88424ddf0386824b2a28744d2b5143c0880a7eb6d7ba51597a85d4df3c5bf824285f782961c6964d39c6fc
|
7
|
+
data.tar.gz: 30e29bacb151c98f5cb41f0b09a53ac3cb53e1cbb030493362713522d7ffc7f2fce6a8cca00edde189e940626cf6848614394365f55af3dd34c5b5b1ff88f651
|
data/.travis.yml
CHANGED
data/CHANGELOG.md
CHANGED
@@ -1,5 +1,20 @@
|
|
1
1
|
# Change log
|
2
2
|
|
3
|
+
## [v0.10.0] - 2018-02-18
|
4
|
+
|
5
|
+
### Changed
|
6
|
+
* Change to limit Ruby version to 2.0
|
7
|
+
* Change to use strings instead of verse
|
8
|
+
* Change Field to rely on Strings#display_width
|
9
|
+
* Change Operations to stop accepting table at initialization
|
10
|
+
* Change Operations#run_operations to #apply_to
|
11
|
+
* Change Border to remove padding configuration
|
12
|
+
* Change ColumnSet class to Columns stateless module
|
13
|
+
* Change Indentation class to stateless module
|
14
|
+
|
15
|
+
### Fixed
|
16
|
+
* Fix :resize option to honour :padding values
|
17
|
+
|
3
18
|
## [v0.9.0] - 2017-11-04
|
4
19
|
|
5
20
|
### Changed
|
@@ -76,6 +91,7 @@
|
|
76
91
|
|
77
92
|
* Initial implementation and release
|
78
93
|
|
94
|
+
[v0.10.0]: https://github.com/piotrmurach/tty-table/compare/v0.9.0...v0.10.0
|
79
95
|
[v0.9.0]: https://github.com/piotrmurach/tty-table/compare/v0.8.0...v0.9.0
|
80
96
|
[v0.8.0]: https://github.com/piotrmurach/tty-table/compare/v0.7.0...v0.8.0
|
81
97
|
[v0.7.0]: https://github.com/piotrmurach/tty-table/compare/v0.6.0...v0.7.0
|
data/Gemfile
CHANGED
@@ -3,15 +3,15 @@ source 'https://rubygems.org'
|
|
3
3
|
gemspec
|
4
4
|
|
5
5
|
group :tools do
|
6
|
-
gem 'yard',
|
6
|
+
gem 'yard', '~> 0.9.12'
|
7
7
|
end
|
8
8
|
|
9
9
|
group :metrics do
|
10
|
-
gem 'coveralls', '~> 0.8.
|
11
|
-
gem 'simplecov', '~> 0.
|
10
|
+
gem 'coveralls', '~> 0.8.21'
|
11
|
+
gem 'simplecov', '~> 0.14.1'
|
12
12
|
gem 'yardstick', '~> 0.9.9'
|
13
13
|
end
|
14
14
|
|
15
15
|
group :benchmarks do
|
16
|
-
gem '
|
16
|
+
gem 'benchmark-ips', '~> 2.7.2'
|
17
17
|
end
|
data/README.md
CHANGED
@@ -432,7 +432,7 @@ table.render(:ascii)
|
|
432
432
|
To print border around data table you need to specify `renderer` type out of `basic`, `ascii`, `unicode`. By default `basic` is used. For instance, to output unicode border:
|
433
433
|
|
434
434
|
```ruby
|
435
|
-
table = TTY::Table.new ['header1', 'header2'], [['a1', 'a2'], ['b1', 'b2']
|
435
|
+
table = TTY::Table.new ['header1', 'header2'], [['a1', 'a2'], ['b1', 'b2']]
|
436
436
|
table.render :unicode
|
437
437
|
# =>
|
438
438
|
# ┌───────┬───────┐
|
@@ -554,7 +554,7 @@ All [supported colors](https://github.com/piotrmurach/pastel#3-supported-colors)
|
|
554
554
|
You can define filters that will modify individual table fields value before they are rendered. A filter can be a callable such as proc. Here's an example that formats
|
555
555
|
|
556
556
|
```ruby
|
557
|
-
table = TTY::Table.new ['header1', 'header2'], [['a1', 'a2'], ['b1', 'b2']
|
557
|
+
table = TTY::Table.new ['header1', 'header2'], [['a1', 'a2'], ['b1', 'b2']]
|
558
558
|
table.render do |renderer|
|
559
559
|
renderer.filter = Proc.new do |val, row_index, col_index|
|
560
560
|
if col_index == 1 and !(row_index == 0)
|
@@ -710,4 +710,4 @@ This project is intended to be a safe, welcoming space for collaboration, and co
|
|
710
710
|
|
711
711
|
## Copyright
|
712
712
|
|
713
|
-
Copyright (c) 2015-
|
713
|
+
Copyright (c) 2015-2018 Piotr Murach. See LICENSE for further details.
|
data/appveyor.yml
CHANGED
data/benchmarks/speed.rb
CHANGED
@@ -1,17 +1,15 @@
|
|
1
1
|
# coding: utf-8
|
2
2
|
|
3
|
-
# Benchmark speed of table operations
|
4
|
-
|
5
|
-
$LOAD_PATH.unshift File.expand_path('../../lib', __FILE__)
|
6
|
-
|
7
|
-
require 'tty-table'
|
8
3
|
require 'benchmark'
|
9
4
|
require 'benchmark/ips'
|
10
5
|
|
6
|
+
require_relative '../lib/tty-table'
|
7
|
+
|
11
8
|
header = [:name, :color]
|
12
9
|
rows = (1..100).map { |n| ["row#{n}", "red"] }
|
13
10
|
table = TTY::Table.new(header, rows)
|
14
11
|
|
12
|
+
# Benchmark speed of table operations
|
15
13
|
Benchmark.ips do |r|
|
16
14
|
r.report("Ruby #to_s") do
|
17
15
|
rows.to_s
|
data/examples/alignment.rb
CHANGED
@@ -1,8 +1,8 @@
|
|
1
|
-
#
|
1
|
+
# frozen_string_literal: true
|
2
2
|
|
3
|
-
|
3
|
+
require_relative '../lib/tty-table'
|
4
4
|
|
5
|
-
table = TTY::Table.new header: ['
|
5
|
+
table = TTY::Table.new header: ['right align', 'center align', 'left align']
|
6
6
|
table << ['a1', 'a2', 'a3']
|
7
7
|
table << ['b1','b2', 'b3']
|
8
8
|
table << ['c1', 'c2', 'c3']
|
data/examples/basic.rb
CHANGED
@@ -0,0 +1,13 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require_relative "../lib/tty-table"
|
4
|
+
|
5
|
+
table = TTY::Table.new(header: ["Column 1", "Column 2", "Column 3"]) do |t|
|
6
|
+
t << [ "r1 c1", "r1 c2", "r1 c3" ]
|
7
|
+
t << [ "r2 c1", "r2 c2", "r2 c3" ]
|
8
|
+
t << [ "r3 c1", "r3 c2", "r3 c3" ]
|
9
|
+
end
|
10
|
+
|
11
|
+
table.orientation = :vertical
|
12
|
+
|
13
|
+
puts table.render(:ascii)
|
data/examples/padding.rb
ADDED
@@ -0,0 +1,15 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'pastel'
|
4
|
+
require_relative "../lib/tty-table"
|
5
|
+
|
6
|
+
pastel = Pastel.new
|
7
|
+
yellow = pastel.yellow.detach
|
8
|
+
|
9
|
+
table = TTY::Table.new(header: [ yellow.("Column 1"), yellow.("Column 2"), yellow.("Column 3")]) do |t|
|
10
|
+
t << [ "11", "12", "13" ]
|
11
|
+
t << [ "21", "22", "23" ]
|
12
|
+
t << [ "31", "32", "33" ]
|
13
|
+
end
|
14
|
+
|
15
|
+
puts table.render(:ascii, padding: [1, 2, 1, 2])
|
data/examples/resize.rb
ADDED
@@ -0,0 +1,15 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'pastel'
|
4
|
+
require_relative "../lib/tty-table"
|
5
|
+
|
6
|
+
pastel = Pastel.new
|
7
|
+
yellow = pastel.yellow.detach
|
8
|
+
|
9
|
+
table = TTY::Table.new(header: [ yellow.("Column 1"), yellow.("Column 2"), yellow.("Column 3")]) do |t|
|
10
|
+
t << [ "11", "12", "13" ]
|
11
|
+
t << [ "21", "22", "23" ]
|
12
|
+
t << [ "31", "32", "33" ]
|
13
|
+
end
|
14
|
+
|
15
|
+
puts table.render(:ascii, resize: true, padding: [1, 2, 1, 2])
|
data/lib/tty/table.rb
CHANGED
@@ -339,6 +339,7 @@ module TTY
|
|
339
339
|
def columns_size
|
340
340
|
rows.size > 0 ? rows[0].size : 0
|
341
341
|
end
|
342
|
+
alias columns_count columns_size
|
342
343
|
|
343
344
|
# Return the number of rows
|
344
345
|
#
|
@@ -370,7 +371,7 @@ module TTY
|
|
370
371
|
#
|
371
372
|
# @api public
|
372
373
|
def width
|
373
|
-
Columns.
|
374
|
+
Columns.total_width(data)
|
374
375
|
end
|
375
376
|
|
376
377
|
# Return true if this is an empty table, i.e. if the number of
|
data/lib/tty/table/border.rb
CHANGED
@@ -2,7 +2,7 @@
|
|
2
2
|
|
3
3
|
require 'equatable'
|
4
4
|
require 'pastel'
|
5
|
-
require '
|
5
|
+
require 'strings'
|
6
6
|
|
7
7
|
require_relative 'border_options'
|
8
8
|
require_relative 'border_dsl'
|
@@ -39,12 +39,11 @@ module TTY
|
|
39
39
|
# @return [Object]
|
40
40
|
#
|
41
41
|
# @api private
|
42
|
-
def initialize(column_widths,
|
42
|
+
def initialize(column_widths, options = nil)
|
43
43
|
if self.class == Border
|
44
44
|
fail NotImplementedError, "#{self} is an abstract class"
|
45
45
|
else
|
46
46
|
@widths = column_widths
|
47
|
-
@padding = Verse::Padder.parse(padding)
|
48
47
|
@border_options = TTY::Table::BorderOptions.from options
|
49
48
|
@color = Pastel.new
|
50
49
|
end
|
@@ -166,11 +165,6 @@ module TTY
|
|
166
165
|
# @api private
|
167
166
|
attr_reader :border_options
|
168
167
|
|
169
|
-
# The padding to apply to each field
|
170
|
-
#
|
171
|
-
# @api private
|
172
|
-
attr_reader :padding
|
173
|
-
|
174
168
|
# Separate multiline string into individual rows with border.
|
175
169
|
#
|
176
170
|
# @param [TTY::Table::Row] row
|
@@ -206,7 +200,7 @@ module TTY
|
|
206
200
|
line.left + row.fields.each_with_index.map do |field, index|
|
207
201
|
direction = field.alignment || :left
|
208
202
|
field_content = field.lines[line_index] || SPACE_CHAR * field.length
|
209
|
-
|
203
|
+
Strings.align(field_content, widths[index], direction: direction)
|
210
204
|
end.join(line.center) + line.right
|
211
205
|
end
|
212
206
|
|
@@ -237,9 +231,7 @@ module TTY
|
|
237
231
|
#
|
238
232
|
# @api private
|
239
233
|
def render_line(line, left, right, intersection)
|
240
|
-
left + widths.map
|
241
|
-
line * (padding.left + width + padding.right)
|
242
|
-
end.join(intersection) + right
|
234
|
+
left + widths.map { |width| line * width }.join(intersection) + right
|
243
235
|
end
|
244
236
|
end # Border
|
245
237
|
end # Table
|
@@ -57,7 +57,7 @@ module TTY
|
|
57
57
|
# @api public
|
58
58
|
def padding_size
|
59
59
|
padding = renderer.padding
|
60
|
-
(padding.left + padding.right) *
|
60
|
+
(padding.left + padding.right) * table.columns_count
|
61
61
|
end
|
62
62
|
|
63
63
|
# Estimate minimum table width to be able to display content
|
@@ -86,9 +86,16 @@ module TTY
|
|
86
86
|
# @api public
|
87
87
|
def enforce
|
88
88
|
assert_minimum_width
|
89
|
+
padding = renderer.padding
|
89
90
|
|
90
91
|
if natural_width <= renderer.width
|
91
|
-
renderer.resize
|
92
|
+
if renderer.resize
|
93
|
+
expand_column_widths
|
94
|
+
else
|
95
|
+
renderer.column_widths.map do |width|
|
96
|
+
padding.left + width + padding.right
|
97
|
+
end
|
98
|
+
end
|
92
99
|
else
|
93
100
|
if renderer.resize
|
94
101
|
shrink
|
@@ -115,12 +122,13 @@ module TTY
|
|
115
122
|
# Expand column widths to match the requested width
|
116
123
|
#
|
117
124
|
# @api private
|
118
|
-
def
|
119
|
-
|
120
|
-
|
125
|
+
def expand_column_widths
|
126
|
+
columns_count = table.columns_count
|
127
|
+
max_width = renderer.width
|
128
|
+
extra_column_width = ((max_width - natural_width) / columns_count.to_f).floor
|
121
129
|
|
122
|
-
widths = (0...
|
123
|
-
lengths
|
130
|
+
widths = (0...columns_count).reduce([]) do |lengths, col|
|
131
|
+
lengths << renderer.column_widths[col] + extra_column_width
|
124
132
|
end
|
125
133
|
distribute_extra_width(widths)
|
126
134
|
end
|
data/lib/tty/table/columns.rb
CHANGED
@@ -1,66 +1,55 @@
|
|
1
1
|
# encoding: utf-8
|
2
|
-
|
3
|
-
require 'equatable'
|
2
|
+
# frozen_string_literal: true
|
4
3
|
|
5
4
|
require_relative 'error'
|
6
5
|
|
7
6
|
module TTY
|
8
7
|
class Table
|
9
|
-
# A
|
8
|
+
# A module for calculating table data column widths
|
10
9
|
#
|
11
10
|
# Used by {Table} to manage column sizing.
|
12
11
|
#
|
13
12
|
# @api private
|
14
|
-
|
15
|
-
include Equatable
|
16
|
-
|
17
|
-
# Initialize Columns
|
18
|
-
#
|
19
|
-
# @param [Array[Array[Object]]] data
|
20
|
-
#
|
21
|
-
# @api public
|
22
|
-
def initialize(table)
|
23
|
-
@data = table.data
|
24
|
-
end
|
25
|
-
|
13
|
+
module Columns
|
26
14
|
# Calculate total table width
|
27
15
|
#
|
28
16
|
# @return [Integer]
|
29
17
|
#
|
30
18
|
# @api public
|
31
|
-
def total_width
|
32
|
-
extract_widths.reduce(:+)
|
19
|
+
def total_width(data)
|
20
|
+
extract_widths(data).reduce(:+)
|
33
21
|
end
|
22
|
+
module_function :total_width
|
34
23
|
|
35
24
|
# Calcualte maximum column widths
|
36
25
|
#
|
37
26
|
# @return [Array] column widths
|
38
27
|
#
|
39
28
|
# @api private
|
40
|
-
def extract_widths
|
29
|
+
def extract_widths(data)
|
41
30
|
colcount = data.max { |row_a, row_b| row_a.size <=> row_b.size }.size
|
42
|
-
|
31
|
+
(0...colcount).reduce([]) do |maximas, col_index|
|
32
|
+
maximas << find_maximum(data, col_index)
|
33
|
+
maximas
|
34
|
+
end
|
43
35
|
end
|
36
|
+
module_function :extract_widths
|
44
37
|
|
45
|
-
#
|
46
|
-
#
|
47
|
-
# @param [Array] column_widths
|
38
|
+
# Find a maximum column width. The calculation takes into account
|
39
|
+
# wether the content is escaped or not.
|
48
40
|
#
|
49
|
-
# @param [Integer]
|
41
|
+
# @param [Integer] index
|
42
|
+
# the column index
|
50
43
|
#
|
51
|
-
# @
|
44
|
+
# @return [Integer]
|
52
45
|
#
|
53
|
-
# @api
|
54
|
-
def
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
end
|
59
|
-
if column_widths.size != table_widths
|
60
|
-
fail InvalidArgument, 'Value for :column_widths must match ' \
|
61
|
-
'table column count'
|
62
|
-
end
|
46
|
+
# @api private
|
47
|
+
def find_maximum(data, index)
|
48
|
+
data.map do |row|
|
49
|
+
(field = row.call(index)) ? field.length : 0
|
50
|
+
end.max
|
63
51
|
end
|
52
|
+
module_function :find_maximum
|
64
53
|
|
65
54
|
# Converts column widths to array format or infers default widths
|
66
55
|
#
|
@@ -71,7 +60,7 @@ module TTY
|
|
71
60
|
# @return [Array[Integer]]
|
72
61
|
#
|
73
62
|
# @api public
|
74
|
-
def
|
63
|
+
def widths_from(table, column_widths = nil)
|
75
64
|
case column_widths
|
76
65
|
when Array
|
77
66
|
assert_widths(column_widths, table.columns_size)
|
@@ -79,48 +68,33 @@ module TTY
|
|
79
68
|
when Numeric
|
80
69
|
Array.new(table.columns_size, column_widths)
|
81
70
|
when NilClass
|
82
|
-
|
71
|
+
extract_widths(table.data)
|
83
72
|
else
|
84
73
|
fail TypeError, 'Invalid type for column widths'
|
85
74
|
end
|
86
75
|
end
|
76
|
+
module_function :widths_from
|
87
77
|
|
88
|
-
|
89
|
-
|
90
|
-
attr_reader :data
|
91
|
-
|
92
|
-
# Find maximum widths for each row and header if present.
|
93
|
-
#
|
94
|
-
# @param [Integer] colcount
|
95
|
-
# number of columns
|
96
|
-
#
|
97
|
-
# @return [Array[Integer]]
|
78
|
+
# Assert data integrity for column widths
|
98
79
|
#
|
99
|
-
# @
|
100
|
-
def find_maximas(colcount)
|
101
|
-
maximas = []
|
102
|
-
start = 0
|
103
|
-
|
104
|
-
start.upto(colcount - 1) do |col_index|
|
105
|
-
maximas << find_maximum(col_index)
|
106
|
-
end
|
107
|
-
maximas
|
108
|
-
end
|
109
|
-
|
110
|
-
# Find a maximum column width. The calculation takes into account
|
111
|
-
# wether the content is escaped or not.
|
80
|
+
# @param [Array] column_widths
|
112
81
|
#
|
113
|
-
# @param [Integer]
|
114
|
-
# the column index
|
82
|
+
# @param [Integer] table_widths
|
115
83
|
#
|
116
|
-
# @
|
84
|
+
# @raise [TTY::InvalidArgument]
|
117
85
|
#
|
118
|
-
# @api
|
119
|
-
def
|
120
|
-
|
121
|
-
|
122
|
-
|
86
|
+
# @api public
|
87
|
+
def assert_widths(column_widths, table_widths)
|
88
|
+
if column_widths.empty?
|
89
|
+
fail InvalidArgument, 'Value for :column_widths must be ' \
|
90
|
+
'a non-empty array'
|
91
|
+
end
|
92
|
+
if column_widths.size != table_widths
|
93
|
+
fail InvalidArgument, 'Value for :column_widths must match ' \
|
94
|
+
'table column count'
|
95
|
+
end
|
123
96
|
end
|
124
|
-
|
97
|
+
module_function :assert_widths
|
98
|
+
end # Columns
|
125
99
|
end # Table
|
126
100
|
end # TTY
|