NAME
HTML::Make - A flexible HTML generator
SYNOPSIS
# Make a table.
use HTML::Make;
my $table = HTML::Make->new ('table');
# Can add elements as text
$table->add_text ('<tr><th>Item<th>Cost');
my %items = (
compressor => 12800,
heater => 'free',
camera => 1080,
);
for my $k (sort keys %items) {
# Add an element using "push". The return value is the new element.
my $tr = $table->push ('tr');
# Can add element to $tr using "push"
$tr->push ('td', text => $k);
# Can also make a new element then "push" it.
my $td = HTML::Make->new ('td', text => $items{$k},
attr => {style => 'padding:1em'});
$tr->push ($td);
}
# Get the output
print $table->text ();
produces output
<table>
<tr><th>Item<th>Cost<tr>
<td>camera</td>
<td style="padding:1em">1080</td>
</tr>
<tr>
<td>compressor</td>
<td style="padding:1em">12800</td>
</tr>
<tr>
<td>heater</td>
<td style="padding:1em">free</td>
</tr>
</table>
As HTML this looks like this:
Item | Cost |
---|---|
camera | 1080 |
compressor | 12800 |
heater | free |
(This example is included as synopsis.pl in the distribution.)
VERSION
This documents HTML::Make version 0.17 corresponding to git commit d3936ea8324960958db788a27aa75d1c5acc0ade released on Tue Jul 25 14:00:27 2023 +0900.
DESCRIPTION
HTML::Make is an HTML generator. It generates HTML fragments, such as HTML lists or tables, rather than complete HTML pages.
METHODS
add_attr
$obj->add_attr (class => 'buggles');
Add attributes to $obj
. The following adds a class "beano" to the "li" element:
use HTML::Make;
my $obj = HTML::Make->new ('li');
$obj->add_attr (class => 'beano');
print $obj->text ();
produces output
<li class="beano"></li>
(This example is included as li-class-beano.pl in the distribution.)
This issues a warning of the form "Overwriting attribute 'class' for 'p'" if the object already contains an attribute of the specified type.
use HTML::Make;
my $p = HTML::Make->new ('p', attr => {class => 'big'});
$p->add_attr (class => 'small');
produces output
Overwriting attribute 'class' for 'p' tag at /usr/home/ben/projects/html-make/examples/p-double-class.pl line 6.
(This example is included as p-double-class.pl in the distribution.)
This also issues a warning if the attribute is not valid for the tag, according to "tag_attr_ok" in HTML::Valid::Tagset. This is restricted to what is valid in HTML5.
add_class
$element->add_class ('help');
As a special case of "add_attr", HTML::Make allows you to add to the class of the item with add_class
. This is added to the existing classes of the element rather than overwriting them.
use HTML::Make;
my $p = HTML::Make->new ('p', class => 'top');
$p->add_class ('help');
print $p->text ();
produces output
<p class="top help">
</p>
(This example is included as add-class.pl in the distribution.)
🎲 This method was added in version 0.13.
add_comment
$element->add_comment ('This should be fixed!');
Add an HTML comment to the element's children.
use HTML::Make;
my $p = HTML::Make->new ('p', text => 'Help! I need somebody! Help!');
$p->add_comment ('This should be fixed');
print $p->text ();
produces output
<p>
Help! I need somebody! Help!<!-- This should be fixed --></p>
(This example is included as add-comment.pl in the distribution.)
🎲 This method was added in version 0.12.
add_text
$element->add_text ('buggles');
Add text to $element
. For example,
use HTML::Make;
my $element = HTML::Make->new ('p');
$element->add_text ('peanuts');
print $element->text ();
produces output
<p>
peanuts</p>
(This example is included as add-text.pl in the distribution.)
The text may contain HTML elements:
use HTML::Make;
my $element = HTML::Make->new ('p');
$element->add_text ('peanuts <i>eggs</i>');
print $element->text ();
produces output
<p>
peanuts <i>eggs</i></p>
(This example is included as add-text-html.pl in the distribution.)
The return value is the added text object.
HTML::Make does not do any escaping or other alteration of the user's text whatsoever.
attr
my $attr = $element->attr ();
This returns a hash reference, possibly empty, containing the attributes of $element
. This is a copy of the attributes of $element
so it can be altered without altering the attributes of $element
.
use HTML::Make;
my $p = HTML::Make->new ('p', attr => {style => 'color:blue;'});
my $attr = $p->attr;
$attr->{style} = 'color:purple;';
print $p->text ();
produces output
<p style="color:blue;">
</p>
(This example is included as attr.pl in the distribution.)
children
my $children = $obj->children ();
This returns an array reference, possibly empty, containing the child elements of $obj
, in the order they were added to $obj.
multiply
my @elements = $obj->multiply ('li', \@contents);
Given an HTML tag type as the first argument, and an array reference as the second argument, this adds multiple child elements to $obj
of type given by the first argument, with text contents given by \@contents
.
use HTML::Make;
my $ol = HTML::Make->new ('ol');
$ol->multiply ('li', ['one', 'two', 'three']);
print $ol->text ();
produces output
<ol>
<li>one</li>
<li>two</li>
<li>three</li>
</ol>
As HTML this looks like this:
- one
- two
- three
(This example is included as multiply.pl in the distribution.)
new
my $element = HTML::Make->new ('li');
Make a new HTML element of the specified type.
To add attributes to the element, use
my $element = HTML::Make->new ('li', attr => {class => 'biglist'});
To add text,
my $element = HTML::Make->new ('li', text => "White punks on dope");
Both attributes and text may be added:
my $element = HTML::Make->new ('li', attr => {id => 'ok'}, text => 'OK');
HTML::Make checks the element against a list of known HTML tags from "HTML::Valid::Tagset", and warns if the first argument is not on this list. To switch off this behaviour and allow arbitrary tags, use the nocheck
option:
use HTML::Make;
my $freaky = HTML::Make->new ('freaky', nocheck => 1);
$freaky->push ('franky', nocheck => 1, text => 'Visible man');
print $freaky->text ();
produces output
<freaky><franky>Visible man</franky>
</freaky>
(This example is included as nocheck.pl in the distribution.)
Allowed options
The following options are allowed in new
and in "push":
- attr
-
my $item = HTML::Make->new ('li', attr => {style => "color: #FFD"});
Any HTML tag attributes can be added as a hash reference.
- class
-
my $item = HTML::Make->new ('li', class => 'entry');
This is equivalent to
attr => {class => $class}
. It is allowed for any HTML element. See also "add_class".🎲 This option was added in version 0.13.
- href
-
my $link = HTML::Make->new ('a', href => 'http://www.example.com');
This is equivalent to
attr => {href => $url}
. It is allowed only fora
elements.🎲 This option was added in version 0.13.
- id
-
my $item = HTML::Make->new ('li', id => 'entry');
This is equivalent to
attr => {id => $id}
. It is allowed for any HTML element.🎲 This option was added in version 0.13.
- text
-
my $link = HTML::Make->new ('a', href => $url, text => "My cool website");
The text, the part between <a> and </a>.
See also "add_text".
opening_tag
my $tag = $obj->opening_tag ();
Returns the text value of the HTML tag opening, complete with attributes. There is no "closing_tag" method, the module just prints "</$tag>" within the "text" method.
push
my $child = $element->push ('tag');
Add child element of type <tag> to $element
and return the result as a new HTML::Make
object. For example,
use utf8;
use HTML::Make;
my $table = HTML::Make->new ('table');
my $row = $table->push ('tr');
my $cell = $row->push ('td', text => 'Cell');
print $table->text ();
produces output
<table>
<tr>
<td>Cell</td>
</tr>
</table>
(This example is included as table.pl in the distribution.)
It is also possible to push one HTML::Make object into another one.
my $td = HTML::Make->new ('td');
$tr->push ($td);
In this case, the return value is the initial element itself.
push
takes all of the same arguments as "new", for example:
use HTML::Make;
my $element = HTML::Make->new ('p', text => 'Here is a ');
$element->push ('a', attr => {href => 'http://www.example.org/'}, text => 'link to example');
print $element->text ();
produces output
<p>
Here is a <a href="http://www.example.org/">
link to example</a>
</p>
As HTML this looks like this:
Here is a link to example
(This example is included as link-example.pl in the distribution.)
Making a colourful list
An object created with HTML::Make may also be pushed:
use utf8;
use HTML::Make;
my @colours = (
daidai => 0xEE7800,
murasaki => 0x884898,
kimidori => 0xB9C42F,
kogecha => 0x6A4D32,
uguisuiro => 0x838B0D,
);
my $ul = HTML::Make->new ('ul');
while (@colours) {
my $colour = shift @colours;
my $rgb = shift @colours;
# Here we make a new element and then push it into $ul, rather
# than using the return value of $ul->push ().
my $li = HTML::Make->new (
'li', text => $colour,
attr => {
style => sprintf ("background: #%06X", $rgb),
});
$ul->push ($li);
}
print $ul->text ();
produces output
<ul>
<li style="background: #EE7800">daidai</li>
<li style="background: #884898">murasaki</li>
<li style="background: #B9C42F">kimidori</li>
<li style="background: #6A4D32">kogecha</li>
<li style="background: #838B0D">uguisuiro</li>
</ul>
As HTML this looks like this:
- daidai
- murasaki
- kimidori
- kogecha
- uguisuiro
(This example is included as push-new.pl in the distribution.)
See also Make a list of colours with HTML::Make.
JSON to HTML
This script converts arbitrary JSON to HTML:
use utf8;
use JSON::Parse 'parse_json';
use HTML::Make;
my $json =<<EOF;
{"words":[{"j_pron_only":"パイプ","word":"pipe"},{"word":"cutting","j_pron_only":"カティング"},{"word":"implement","j_pron_only":"インプリムント"}]}
EOF
my $p = parse_json ($json);
my $html = json_to_html ($p);
print $html->text ();
exit;
sub json_to_html
{
my ($input) = @_;
my $element;
if (ref $input eq 'ARRAY') {
$element = HTML::Make->new ('ol');
for my $k (@$input) {
my $li = $element->push ('li');
$li->push (json_to_html ($k));
}
}
elsif (ref $input eq 'HASH') {
$element = HTML::Make->new ('table');
for my $k (sort keys %$input) {
my $tr = $element->push ('tr');
$tr->push ('th', text => $k);
my $td = $tr->push ('td');
$td->push (json_to_html ($input->{$k}));
}
}
else {
$element = HTML::Make->new ('span', text => $input);
}
return $element;
}
produces output
<table>
<tr>
<th>words</th>
<td><ol>
<li><table>
<tr>
<th>j_pron_only</th>
<td><span>パイプ</span>
</td>
</tr>
<tr>
<th>word</th>
<td><span>pipe</span>
</td>
</tr>
</table>
</li>
<li><table>
<tr>
<th>j_pron_only</th>
<td><span>カティング</span>
</td>
</tr>
<tr>
<th>word</th>
<td><span>cutting</span>
</td>
</tr>
</table>
</li>
<li><table>
<tr>
<th>j_pron_only</th>
<td><span>インプリムント</span>
</td>
</tr>
<tr>
<th>word</th>
<td><span>implement</span>
</td>
</tr>
</table>
</li>
</ol>
</td>
</tr>
</table>
As HTML this looks like this:
words |
|
---|
(This example is included as json-to-html.pl in the distribution.)
See also Convert JSON to HTML with JSON::Parse and HTML::Make.
There are some ad-hoc guardrails
This warns if you add some types of elements to possibly inappropriate parent elements. For example if you add an <li> tag to a <tr> it reacts like this:
use HTML::Make;
my $tr = HTML::Make->new ('tr');
$tr->push ('li');
produces output
Pushing non-table element <li> to a table row at /usr/home/ben/projects/html-make/examples/push-li-to-tr.pl line 6.
(This example is included as push-li-to-tr.pl in the distribution.)
We've never received a single bug report for this module, and so these warnings are mostly added in an ad-hoc fashion as we've found ourselves making various mistakes. If you find yourself tripping over some kind of error repeatedly, then feel free to ask us to add that to this module.
text
$element->text ();
This returns the element and its child elements as text, so usually this is called at the final stage.
If $element
's type is html
, a doctype declaration of the form <!DOCTYPE html>
is added before the opening tag.
OUTPUT FORMAT
This section discusses the way that HTML is output by the module.
Whitespace
- Indentation
-
The output HTML is not indented.
- New lines
-
New lines are added after block-level elements, according to "%isBlock" in HTML::Valid::Tagset, and after <tr> elements.
BUGS
This module assumes you want to make HTML5.
There is no way to control the whitespace in the output HTML such as indentation.
This module assumes lower case HTML tags (HTML tags are actually completely case insensitive, so <LI> or <A HREF='http://www.example.com'> and so on are all valid.)
DEPENDENCIES
This module depends on the following Perl modules.
- Carp
-
Carp is used to report errors.
- HTML::Valid::Tagset
-
HTML::Valid::Tagset is used to validate tags and tag/attribute pairs.
- JSON::Parse
-
JSON::Parse is used to read an information file about HTML tags and attributes.
SEE ALSO
HTML::Make family
These are modules based on HTML::Make.
- HTML::Make::Calendar
-
Make a calendar in HTML format.
- HTML::Make::Page
-
Make the HTML
<head>
element using Perl.
CPAN modules
These are the other modules we've found on CPAN (one is only on sourceforge) which generate HTML programmatically, rather than by template substitution.
- CGI
-
[⭐⭐ Author: LEEJO; Date:
2020-10-05
; Version:4.51
]The CGI module contains HTML generation. See also CGI::HTML::Functions.
- HTML::Builder
-
[⭐ Author: RSRCHBOY; Date:
2012-12-02
; Version:0.008
] - HTML::DataTable
-
[Author: NICWOLFF; Date:
2012-01-08
; Version:0.54
]"Print HTML tables from Perl data"
- HTML::Declare
-
[Author: BINGOS; Date:
2017-03-28
; Version:2.6
]An HTML mini-language.
- HTML::FromArrayref
-
[⭐ Author: NICWOLFF; Date:
2013-10-30
; Version:1.06
]Output HTML described by a Perl data structure
This project is on the SourceForge site, not CPAN.
- HTML::HTML5::Builder
-
[Author: TOBYINK; Date:
2011-10-20
; Version:0.004
]"erect some scaffolding for your documents"
- HTML::Native
-
[Author: MCB; Date:
2014-01-15
; Version:1.1
]"Generate and manipulate HTML as native Perl data structures"
You give this list references containing your HTML structures, and it converts them into HTML text.
- HTML::TagTree
-
[Author: DDEBRITO; Date:
2014-09-05
; Version:v1.03
]An HTML generator via a tree of 'tag' objects
- HTML::Template
-
[⭐⭐ Author: SAMTREGAR; Date:
2017-05-18
; Version:2.97
]An HTML-like templating language.
- HTML::Tiny
-
[⭐ Author: ANDYA; Date:
2009-03-08
; Version:1.05
]This is similar to the HTML generation which is in CGI. Its last update, version 1.05, was in 2009, and so it doesn't include HTML5 tags.
- HTML::Tree
-
[⭐⭐ Author: KENTNL; Date:
2017-08-31
; Version:5.07
]This doesn't have any proper documentation so we're not sure what it does, but it is linked from "HTML::Native" as an alternative to that.
- HTML::Untidy
-
[⭐ Author: JEFFOBER; Date:
2017-10-27
; Version:0.02
]
HTML validator
My HTML validator is on github. This is in the Go language, not in Perl.
AUTHOR
Ben Bullock, <bkb@cpan.org>
COPYRIGHT & LICENCE
This package and associated files are copyright (C) 2012-2023 Ben Bullock.
You can use, copy, modify and redistribute this package and associated files under the Perl Artistic Licence or the GNU General Public Licence.