3 my ($page, @feat) = split m{/+}, $Request || 'image';
4 $page !~ /\W/ or Html(), Abort('Invalid codec type request', 400);
5 @feat or @feat = 'default';
6 my $title = "$page codecs";
9 title => "$title cheat sheet",
14 codec encoder encoding decode file format type mime
15 feature comparison support benchmark compression
18 stylesheet => [qw'light circus dark red'],
19 data => [qw'codec.inc.pl'],
20 raw => '<style>td,th {width:8%} tbody th {white-space:nowrap}</style>',
23 my $info = do "codec-$page.inc.pl";
24 $info and %{$info} > 1
25 or Abort("Requested codec type <q>$page</q> not available", '404 request not found', $@ // $!);
27 say "<h1>\u$title</h1>";
29 my %BOOLSCORE = (y => [5, '✔'], n => [1, '✘'], 0 => [0, 'n/a']);
33 <table class="mapped">
36 $info->{codec}->{$a}->{available} <=> $info->{codec}->{$b}->{available}
37 } keys $info->{codec}->%*;
38 my @codeccols = @{$info->{codec}}{@codecs};
43 $spans[ $_->{generation} ]++ for @codeccols;
44 print "<colgroup span=$_>" for @spans;
46 say '<thead><tr><th rowspan=2>';
47 say "\t", '<th>', $_->{name} for @codeccols;
49 print '<td>', $_->{available} for @codeccols;
52 while (defined (my $feat = shift @feat)) {
53 my $featinfo = $info->{feature}->{$feat} or next;
54 unshift @feat, @{$_} for $featinfo->{children} // ();
55 $featinfo->{score} or next;
56 print '<tbody>' if $featinfo->{children};
57 printf '<tr><th>%s', $featinfo->{name} // $feat;
59 my ($score, $data, $title) = map { ref ? @$_ : $_ } $featinfo->{score}->{$_};
60 if (not defined $data) {
61 if (my $override = $BOOLSCORE{$score}) {
62 ($score, $data) = @{$override};
65 $data = '•' x ($score - 1);
68 printf '<td class="l%d"', $score;
69 printf ' title="%s"', EscapeHTML($_) for $title // ();