Text::Table::Tiny is a simple module for generating ASCII tables from array data. I use it in lots of places, which is why I adopted it, and have evolved it. This post describes changes I'm working on, to give people a chance to comment, before the changes are locked in.
Note: I plan to keep this module conceptually simple: you pass an array which is then put into a simple 2D grid, with no cells spanning columns or rows. There are plenty of other table modules if you want something more complex.
The module provides a single function, which takes an arrayref of rows, and a few optional parameters:
use Text::Table::Tiny qw/ generate_table /;
my @rows = (
['Country', 'Capital', 'Population'],
['UK', 'London', 59.67],
['Switzerland', 'Bern', 7.25],
['China', 'Beijing', 1315.84],
);
print generate_table(rows => \@rows, header_row => 1);
This results in the following table:
+-------------+---------+------------+
| Country | Capital | Population |
+-------------+---------+------------+
| UK | London | 59.67 |
| Switzerland | Bern | 7.25 |
| China | Beijing | 1315.84 |
+-------------+---------+------------+
You can ask for divider lines between all rows,
by setting separate_rows
to a true value,
which results in a funky line between the header and the body,
if you had a header:
+-------------+---------+------------+
| Country | Capital | Population |
O=============O=========O============O
| UK | London | 59.67 |
+-------------+---------+------------+
| Switzerland | Bern | 7.25 |
+-------------+---------+------------+
| China | Beijing | 1315.84 |
+-------------+---------+------------+
I have never used this, and imagine that very few people do. It's too visually noisy, and generally vertical space is at a premium.
And finally, you can ask for the top and bottom borders to be left off,
by setting top_and_tail
to a true value:
| Country | Capital | Population |
+-------------+---------+------------+
| UK | London | 59.67 |
| Switzerland | Bern | 7.25 |
| China | Beijing | 1315.84 |
The rest of this post describes the changes I've implemented so far.
A few times I've wanted right-aligned columns, and Andy Lester recently requested this capability as well, which is what nudged me into action.
So now you can pass an align
parameter,
which takes an arrayref of alignment indicators:
align => [qw/ l c r /],
Which results in:
+-------------+---------+------------+
| Country | Capital | Population |
+-------------+---------+------------+
| UK | London | 59.67 |
| Switzerland | Bern | 7.25 |
| China | Beijing | 1315.84 |
+-------------+---------+------------+
For the next release, I'll probably just support left-, centre-, and right-alignment, but in the future might support right-alignment at decimal point (and other characters, like comma or colon).
The new style
parameter defaults to "classic"
,
but "boxrule"
switches to using the box rule characters:
style => "boxrule",
This results in:
┌─────────────┬─────────┬────────────┐
│ Country │ Capital │ Population │
├─────────────┼─────────┼────────────┤
│ UK │ London │ 59.67 │
│ Switzerland │ Bern │ 7.25 │
│ China │ Beijing │ 1315.84 │
└─────────────┴─────────┴────────────┘
At first that table wasn't coming out right in my blog. Looks like Google's Inconsolata typeface doesn't get the box rule characters right, so watch out if you use Inconsolata. I switched my blog to use Source Code Pro (from Google Fonts), and now the tables look right.
Here's what boxrule looks like if you set separate_rows
as well:
┌─────────────┬─────────┬────────────┐
│ Country │ Capital │ Population │
╞═════════════╪═════════╪════════════╡
│ UK │ London │ 59.67 │
├─────────────┼─────────┼────────────┤
│ Switzerland │ Bern │ 7.25 │
├─────────────┼─────────┼────────────┤
│ China │ Beijing │ 1315.84 │
└─────────────┴─────────┴────────────┘
This takes up too much vertical space, but I guess if you have wide data but not too many rows, then you might use this?
I've got some tools that display a lot of columns, so I wanted the option to remove the padding around the text in each column:
compact => 1
Combined with boxrule, we get:
┌───────────┬───────┬──────────┐
│Country │Capital│Population│
├───────────┼───────┼──────────┤
│UK │London │ 59.67│
│Switzerland│ Bern │ 7.25│
│China │Beijing│ 1315.84│
└───────────┴───────┴──────────┘
The "norule"
style results in a columnar display:
Country Capital Population
UK London 59.67
Switzerland Bern 7.25
China Beijing 1315.84
You can combine this with compact
to get columns that are closer together:
Country Capital Population
UK London 59.67
Switzerland Bern 7.25
China Beijing 1315.84
I suspect that in most situations this wouldn't work, but it illustrates that I've got to make sure that all of these options work sensibly together.
I've had a PR on this to add support for generating markdown tables. I need to look into markdown tables, and see how best to fit that in. Should it be a separate function, or a style? If it's a style, then the other options all need to make sense when combined with it.
If you use this module, or now think you might,
do you have any opinions on the above,
or other features you'd like to see?
You can either add comments below, or email me
at neil at bowers dot com
.