More pango-ization.

This commit is contained in:
Dianne Skoll
2022-01-27 15:12:24 -05:00
parent 32adce2de8
commit d973439b4f
4 changed files with 134 additions and 7 deletions

View File

@@ -33,8 +33,8 @@ my $settings = {
fill_entire_page => 0,
media => 'Letter',
width => 612,
height => 792,
width => 0,
height => 0,
title_font => 'Helvetica',
header_font => 'Helvetica',
@@ -47,7 +47,7 @@ my $settings = {
daynum_size => 14,
entry_size => 8,
border_size => 6,
border_size => 4,
line_thickness => 1,
margin_top => 36,
@@ -56,10 +56,62 @@ my $settings = {
margin_right => 36,
};
my $ret = GetOptions('landscape|l' => \$settings->{landscape},
'small-calendars|c' => \$settings->{small_calendars},
'left-numbers|x' => \$settings->{numbers_on_left},
'fill-entire-page|e' => \$settings->{fill_entire_page},
'fill-page|e' => \$settings->{fill_entire_page},
'media|m=s' => \$settings->{media},
'width|w=i' => \$settings->{width},
'height|h=i' => \$settings->{height},
'title-font=s' => \$settings->{title_font},
'header-font=s' => \$settings->{header_font},
'daynum-font=s' => \$settings->{daynum_font},
'entry-font=s' => \$settings->{entry_font},
'small-cal-font=s' => \$settings->{small_cal_font},
'title-size=f' => \$settings->{title_size},
'header-size=f' => \$settings->{header_size},
'daynum-size=f' => \$settings->{daynum_size},
'entry-size=f' => \$settings->{entry_size},
'border-size=f' => \$settings->{border_size},
'line-thickness=f' => \$settings->{line_thickness},
'margin-top=f' => \$settings->{margin_top},
'margin-bottom=f' => \$settings->{margin_bottom},
'margin-left=f' => \$settings->{margin_left},
'margin-right=f' => \$settings->{margin_right},
);
if (!$ret) {
usage();
exit(1);
}
if ($settings->{width} <= 0 ||
$settings->{height} <= 0) {
my $size = $media_to_size->{ucfirst($settings->{media})};
if (!$size) {
print STDERR "Unknown media " . $settings->{media} . "\n";
exit(1);
}
$settings->{width} = $size->[0];
$settings->{height} = $size->[1];
}
if ($settings->{landscape}) {
my $tmp = $settings->{width};
$settings->{width} = $settings->{height};
$settings->{height} = $tmp;
}
my $done_one = 0;
my $surface = Cairo::PdfSurface->create_for_stream(sub { print $_[1]; }, undef,
$settings->{width}, $settings->{height});
$surface->set_metadata('title', 'Calendar');
$surface->set_metadata('author', 'Remind (https://dianne.skoll.ca/projects/remind/)');
$surface->set_metadata('creator', 'rem2pdf (https://dianne.skoll.ca/projects/remind/)');
$surface->set_metadata('subject', 'Calendar');
my $cr = Cairo::Context->create($surface);
$cr->set_line_width($settings->{line_thickness});

View File

@@ -70,6 +70,22 @@ sub render
my ($self, $month, $cr, $settings, $so_far, $day, $col, $height) = @_;
# Do nothing in pre-render mode
return 0 unless $height;
# Render in small text at bottom-right
my ($x1, $y1, $x2, $y2) = $month->col_box_coordinates($so_far, $col, $height, $settings);
my $layout = Pango::Cairo::create_layout($cr);
$layout->set_text($self->{body});
my $desc = Pango::FontDescription->from_string($settings->{entry_font} . ' ' . int(0.75 * $settings->{entry_size}) . 'px');
$layout->set_font_description($desc);
my ($wid, $h) = $layout->get_pixel_size();
$cr->save();
$cr->move_to($x2 - $settings->{border_size}/4 - $wid, $y2 - $settings->{border_size}/4 - $h);
Pango::Cairo::show_layout($cr, $layout);
$cr->restore();
return 0;
}
package Remind::PDF::Entry::moon;
@@ -191,6 +207,16 @@ package Remind::PDF::Entry::psfile;
use base 'Remind::PDF::Entry';
package Remind::PDF::Entry::pango;
use base 'Remind::PDF::Entry';
sub adjust
{
my ($self) = @_;
if ($self->{body} =~ /^@([-0-9.]+),\s*([-0-9.]+)\s*(.*)/) {
$self->{atx} = $1;
$self->{aty} = $2;
$self->{body} = $3;
}
}
sub render
{
my ($self, $month, $cr, $settings, $so_far, $day, $col, $height) = @_;
@@ -201,13 +227,33 @@ sub render
$layout->set_width(1024 * ($x2 - $x1 - 2 * $settings->{border_size}));
$layout->set_wrap('word-char');
$layout->set_markup($self->{body});
if (($layout->get_text() // '') eq '') {
# Invalid markup
return 0;
}
my $desc = Pango::FontDescription->from_string($settings->{entry_font} . ' ' . $settings->{entry_size} . 'px');
$layout->set_font_description($desc);
my ($wid, $h) = $layout->get_pixel_size();
if ($height) {
$cr->save();
$cr->move_to($x1 + $settings->{border_size}, $so_far);
if (defined($self->{atx}) && defined($self->{aty})) {
my ($x, $y);
if ($self->{atx} < 0) {
$x = $x2 + $self->{atx} - $wid;
} else {
$x = $x1 + $self->{atx};
}
if ($self->{aty} < 0) {
$y = $y2 + $self->{aty} - $h;
} else {
$y = $y1 + $self->{aty};
}
$cr->move_to($x, $y);
} else {
$cr->move_to($x1 + $settings->{border_size}, $so_far);
}
Pango::Cairo::show_layout($cr, $layout);
$cr->restore();
}

View File

@@ -172,6 +172,7 @@ sub render
# Remaining space on page
$self->{remaining_space} = $settings->{height} - $settings->{margin_bottom} - $so_far;
$self->{minimum_row_height} = $self->{remaining_space} / 9;
# First column
my $first_col = $self->{firstwkday};
if ($self->{mondayfirst}) {
@@ -213,6 +214,9 @@ sub render
push(@{$self->{horiz_lines}}, $so_far);
}
if ($so_far > $settings->{height} - $settings->{margin_bottom}) {
print STDERR "WARNING: overfull calendar box\n";
}
# The vertical lines
my $cell = ($settings->{width} - $settings->{margin_left} - $settings->{margin_right}) / 7;
for (my $i=0; $i<=7; $i++) {
@@ -227,6 +231,9 @@ sub render
$cr->line_to($settings->{width} - $settings->{margin_right}, $y);
$cr->stroke();
}
# Done this page
$cr->show_page();
}
sub draw_row
@@ -252,6 +259,9 @@ sub draw_row
$height = $self->{row_height} - $settings->{border_size};
}
if ($height < $self->{minimum_row_height}) {
$height = $self->{minimum_row_height};
}
# Now draw for real
while ($col < 7) {
$self->draw_day($cr, $settings, $so_far, $day, $col, $height);
@@ -328,6 +338,15 @@ sub draw_day
$entry->render($self, $cr, $settings, $top, $day, $col, $height);
next;
}
# An absolutely-positioned Pango markup should not adjust height
# either
if ($entry->isa('Remind::PDF::Entry::pango') &&
defined($entry->{atx}) && defined($entry->{aty})) {
$entry->render($self, $cr, $settings, $top, $day, $col, $height);
next;
}
# Shade is done already
if ($entry->isa('Remind::PDF::Entry::shade')) {
next;
@@ -341,6 +360,12 @@ sub draw_day
$entry_height += $h2;
$so_far += $h2;
}
if ($height) {
if ($entry_height > $height) {
print STDERR "WARNING: overfull box at $day " . $self->{monthname} . ' ' . $self->{year} . "\n";
$entry_height = $height;
}
}
return $h + $entry_height + 2 * $settings->{border_size};
}
@@ -375,7 +400,7 @@ sub draw_daynames
$height = $h;
}
}
return $so_far + $height + $settings->{border_size};
return $so_far + $height + $settings->{border_size} * .75;
}
sub draw_title
@@ -383,6 +408,7 @@ sub draw_title
my ($self, $cr, $settings) = @_;
my $title = $self->{monthname} . ' ' . $self->{year};
$cr->get_target()->set_page_label($title);
my $layout = Pango::Cairo::create_layout($cr);
$layout->set_text(Encode::decode('UTF-8', $title));
my $desc = Pango::FontDescription->from_string($settings->{title_font} . ' ' . $settings->{title_size} . 'px');

View File

@@ -12,9 +12,12 @@ REM 10 SPECIAL COLOR 0 128 0 Напоминание
REM 11 SPECIAL COLOR 128 0 0 Υπενθύμιση
REM 12 SPECIAL PANGO <b>Bold</b> <small>and</small> <i>Italic</i> <big>and</big> <span bgcolor="#C0C0C0" foreground="red"><u>underline</u></span>
REM 12 MSG Hello
REM 12 SPECIAL PANGO <span face="zapf chancery">Very Fancy</span>
REM 13 SPECIAL PANGO Invalid
REM 13 SPECIAL PANGO <bad>Invalid
REM 13 MSG Hello Again
REM 15 SPECIAL PANGO @1,-1 <small><small>[hebday($U)] [hebmon($U)] Rise [sunrise($U)] Set [sunset($U)]</small></small>
REM 1 SPECIAL SHADE 128 255 128
REM [moondate(0)] SPECIAL MOON 0
@@ -22,4 +25,4 @@ REM [moondate(1)] SPECIAL MOON 1
REM [moondate(2)] SPECIAL MOON 2 -1 -1 [moontime(2)]
REM [moondate(3)] SPECIAL MOON 3 -1 -1 [moontime(3)]
REM Mon SPECIAL WEEK [weekno(today())]
REM Mon SPECIAL WEEK (W[weekno(today())])