Layer-based rendering

main
Daniel Asher Resnick 4 months ago
parent ae1987022e
commit 8c2d5fc6c2
  1. 16
      HexGrid.pm
  2. 1
      HexGrid/Path.pm
  3. 8
      HexGrid/Pin.pm
  4. 7
      HexGrid/Region.pm
  5. 12
      HexGrid/Tile.pm

@ -211,25 +211,21 @@ sub render($this)
# Continuations to be performed after other renders have finished # Continuations to be performed after other renders have finished
# Registered by subcomponents' render methods # Registered by subcomponents' render methods
my $laters = []; my $layers = {};
foreach my $region (keys %{$this->{regions}}) foreach my $region (keys %{$this->{regions}})
{ {
# $m contains the min/max extents of the region # $m contains the min/max extents of the region
my $m = $this->{regions}{$region}->render($svg, $laters, $this); my $m = $this->{regions}{$region}->render($svg, $this, $layers);
$min_x = $m->{min_x} if $m->{min_x} < $min_x; $min_x = $m->{min_x} if $m->{min_x} < $min_x;
$min_y = $m->{min_y} if $m->{min_y} < $min_y; $min_y = $m->{min_y} if $m->{min_y} < $min_y;
$max_x = $m->{max_x} if $m->{max_x} > $max_x; $max_x = $m->{max_x} if $m->{max_x} > $max_x;
$max_y = $m->{max_y} if $m->{max_y} > $max_y; $max_y = $m->{max_y} if $m->{max_y} > $max_y;
} }
foreach my $path (keys %{$this->paths}) foreach my $tile_callback (@{$layers->{tiles}}) { $tile_callback->(); }
{ foreach my $path (keys %{$this->paths}) { $this->{paths}{$path}->render($this, $svg); }
$this->{paths}{$path}->render($this, $svg); foreach my $pin_callback (@{$layers->{pins}}) { $pin_callback->(); }
} foreach my $popup_callback (@{$layers->{popups}}) { $popup_callback->($svg); }
foreach my $later (@$laters)
{
$later->($svg);
}
# Max and min coordinates are all at the top-left corner of tiles, add one width/height to get full extent # Max and min coordinates are all at the top-left corner of tiles, add one width/height to get full extent
my $width = $max_x - $min_x + $this->tile_width; my $width = $max_x - $min_x + $this->tile_width;
my $height = $max_y - $min_y + $this->tile_height; my $height = $max_y - $min_y + $this->tile_height;

@ -4,6 +4,7 @@ use v5.30;
use Moo; use Moo;
use MooX::Aliases; use MooX::Aliases;
use Carp;
use Data::Dumper; use Data::Dumper;
use feature "signatures"; use feature "signatures";

@ -15,7 +15,7 @@ has popup => (is => 'rw', default => 1, alias => 'use_popup');
has popup_class => (is => 'rw', default => 'pin-popup'); has popup_class => (is => 'rw', default => 'pin-popup');
sub render($this, $pin_container, $x, $y, $w, $h, $laters = undef) sub render($this, $pin_container, $x, $y, $w, $h, $clip_path, $layers)
{ {
my $group = $pin_container->g(); my $group = $pin_container->g();
my $element = $group->use(href => "#$this->{icon}_symbol", my $element = $group->use(href => "#$this->{icon}_symbol",
@ -26,12 +26,10 @@ sub render($this, $pin_container, $x, $y, $w, $h, $laters = undef)
my $center_x = $x + $w/2; my $center_x = $x + $w/2;
my $center_y = $y + $h/2; my $center_y = $y + $h/2;
if(defined $laters) push @{$layers->{popups}}, sub ($popup_container) { $this->render_popup($popup_container,
{
push @$laters, sub ($popup_container) { $this->render_popup($popup_container,
$pin_container->{transform}, $center_x, $center_y); } $pin_container->{transform}, $center_x, $center_y); }
if $this->popup; if $this->popup;
} $group->{"clip-path"} = "url(#$clip_path->{id})";
return $group; return $group;
} }

@ -46,7 +46,7 @@ sub iter_tile($this, $code)
} }
} }
sub render($this, $svg, $laters, $grid) sub render($this, $svg, $grid, $layers)
{ {
my ($min_x,$min_y,$max_x,$max_y) = qw(Inf Inf -Inf -Inf); my ($min_x,$min_y,$max_x,$max_y) = qw(Inf Inf -Inf -Inf);
my $g = $svg->g(id => HexGrid::to_id("$this->{name}$this->{id_suffix}")); my $g = $svg->g(id => HexGrid::to_id("$this->{name}$this->{id_suffix}"));
@ -55,8 +55,11 @@ sub render($this, $svg, $laters, $grid)
foreach my $sw (keys %{$this->{tiles}{$nw}}) foreach my $sw (keys %{$this->{tiles}{$nw}})
{ {
my ($x_translate, $y_translate) = $grid->translate_coords($nw, $sw); my ($x_translate, $y_translate) = $grid->translate_coords($nw, $sw);
my $tile_group = $this->{tiles}{$nw}{$sw}->render($g, $grid->tile_width, $grid->tile_height, $laters); push @{$layers->{tiles}}, sub
{
my $tile_group = $this->{tiles}{$nw}{$sw}->render($g, $grid->tile_width, $grid->tile_height, $layers);
$tile_group->{transform} = "translate($x_translate, $y_translate)"; $tile_group->{transform} = "translate($x_translate, $y_translate)";
};
$min_x = $x_translate if $x_translate < $min_x; $min_x = $x_translate if $x_translate < $min_x;
$min_y = $y_translate if $y_translate < $min_y; $min_y = $y_translate if $y_translate < $min_y;

@ -103,7 +103,7 @@ sub _do_pin($this, $pin, $dock = undef)
} }
} }
sub render($this, $container, $width, $height, $laters = undef) sub render($this, $container, $width, $height, $layers)
{ {
my $g = $container->g my $g = $container->g
( (
@ -112,8 +112,8 @@ sub render($this, $container, $width, $height, $laters = undef)
my $hex = $g->polygon(points => hex_path($width, $height), my $hex = $g->polygon(points => hex_path($width, $height),
id => "$this->{nw}_$this->{sw}_inner_hex", style => $this->style); id => "$this->{nw}_$this->{sw}_inner_hex", style => $this->style);
# Have tile contents clip to the hexagon # Have tile contents clip to the hexagon
my $clipPath = $g->clipPath(id => "$this->{nw}_$this->{sw}_clip"); my $clip_path = $g->clipPath(id => "$this->{nw}_$this->{sw}_clip");
$clipPath->use(href => "#$hex->{id}"); $clip_path->use(href => "#$hex->{id}");
if($this->{colour}) if($this->{colour})
{ {
@ -128,7 +128,7 @@ sub render($this, $container, $width, $height, $laters = undef)
# The actual image is defined at the HexGrid level, here we reference it # The actual image is defined at the HexGrid level, here we reference it
my $use_element = $g->use(id => "$this->{nw}_$this->{sw}_${image}_use", my $use_element = $g->use(id => "$this->{nw}_$this->{sw}_${image}_use",
href => "#${image}_symbol", width => $width, height => $height, href => "#${image}_symbol", width => $width, height => $height,
"clip-path" => "url(#$clipPath->{id})"); "clip-path" => "url(#$clip_path->{id})");
} }
} }
@ -152,8 +152,8 @@ sub render($this, $container, $width, $height, $laters = undef)
my $y = $height * $docks{$key}->{y}; my $y = $height * $docks{$key}->{y};
my $h = $height * $docks{$key}->{h}; my $h = $height * $docks{$key}->{h};
my $pin_element = $this->{pins}{$key}->render($g, $x, $y, $w, $h, $laters); push @{$layers->{pins}},
$pin_element->{"clip-path"} = "url(#$clipPath->{id})"; sub { $this->{pins}{$key}->render($g, $x, $y, $w, $h, $clip_path, $layers); };
} }
} }
return $g; return $g;

Loading…
Cancel
Save