Adding hand, adding complete pc interface, adding selected pokemon logic.
This commit is contained in:
parent
a43b07c5fc
commit
acfdd06660
1
Build.PL
1
Build.PL
@ -18,6 +18,7 @@ my $build = Module::Build->new(
|
||||
'namespace::clean' => 0,
|
||||
'Cairo::GObject' => 0,
|
||||
'UUID::URandom' => 0,
|
||||
'Glib' => 0,
|
||||
},
|
||||
);
|
||||
$build->create_build_script;
|
||||
|
@ -27,6 +27,8 @@ has _initial_rematches => ( is => 'rw' );
|
||||
|
||||
has _initial_flags => ( is => 'rw' );
|
||||
|
||||
has _pc => ( is => 'rw' );
|
||||
|
||||
sub instance {
|
||||
my $class = shift;
|
||||
my $input_file = shift;
|
||||
@ -221,10 +223,15 @@ sub _get_flags_hash_by_id {
|
||||
|
||||
sub get_pc_system {
|
||||
my $self = shift;
|
||||
if (defined $self->_pc) {
|
||||
return $self->_pc;
|
||||
}
|
||||
my $pc = Rsaves::read_pc_storage($self->_get_current_save);
|
||||
return GEmeTool::Save::PokemonPC->new(_pc => $pc, _save => sub {
|
||||
my $return = GEmeTool::Save::PokemonPC->new(_pc => $pc, _save => sub {
|
||||
my $pc = shift;
|
||||
Rsaves::save_pc_changes($self->_get_current_save, $pc)
|
||||
});
|
||||
$self->_pc($return);
|
||||
return $return;
|
||||
}
|
||||
1;
|
||||
|
@ -24,6 +24,10 @@ has _box => (
|
||||
required => 1,
|
||||
);
|
||||
|
||||
has _pokemons => (
|
||||
is => 'rw',
|
||||
);
|
||||
|
||||
sub wallpaper {
|
||||
my $self = shift;
|
||||
my $arg = shift;
|
||||
@ -45,9 +49,19 @@ sub name {
|
||||
sub get_pokemon {
|
||||
my $self = shift;
|
||||
my $number = shift;
|
||||
my $pokemons = $self->_pokemons;
|
||||
if (!defined $pokemons) {
|
||||
$pokemons = [];
|
||||
$self->_pokemons($pokemons);
|
||||
}
|
||||
if ($number < 0 || $number > 29) {
|
||||
die "Pokemon boxes can only hold pokemon from 0 to 29, index $number invalid.";
|
||||
}
|
||||
return GEmeTool::Save::Pokemon->new( _pokemon => $self->_box->[$number] );
|
||||
if (defined $pokemons->[$number]) {
|
||||
return $pokemons->[$number];
|
||||
}
|
||||
my $return = GEmeTool::Save::Pokemon->new( _pokemon => $self->_box->[$number] );
|
||||
$pokemons->[$number] = $return;
|
||||
return $return;
|
||||
}
|
||||
1;
|
||||
|
@ -20,6 +20,10 @@ has _save => (
|
||||
required => 1,
|
||||
);
|
||||
|
||||
has _boxes => (
|
||||
is => 'rw',
|
||||
);
|
||||
|
||||
sub boxes {
|
||||
my $self = shift;
|
||||
my $pc = $self->_pc;
|
||||
@ -30,12 +34,21 @@ sub boxes {
|
||||
return \@boxes;
|
||||
}
|
||||
|
||||
|
||||
sub get_box {
|
||||
my $self = shift;
|
||||
my $number = shift;
|
||||
my $boxes = $self->_boxes;
|
||||
if (!defined $boxes) {
|
||||
$self->_boxes([]);
|
||||
$boxes = $self->_boxes;
|
||||
}
|
||||
if ($number < 0 || $number > 13) {
|
||||
die "Bad box number $number.";
|
||||
}
|
||||
if (defined $boxes->[$number]) {
|
||||
return $boxes->[$number];
|
||||
}
|
||||
my $pc = $self->_pc;
|
||||
my $wallpaper = \$pc->{wallpapers}[$number];
|
||||
my $name = \$pc->{boxes_names}[$number];
|
||||
@ -45,6 +58,7 @@ sub get_box {
|
||||
_name => $name,
|
||||
_box => $box
|
||||
);
|
||||
$boxes->[$number] = $return;
|
||||
return $return;
|
||||
}
|
||||
|
||||
|
@ -11,10 +11,11 @@ use Glib::IO;
|
||||
use Glib::Object::Introspection;
|
||||
use Data::Dumper;
|
||||
use Path::Tiny;
|
||||
|
||||
use GEmeTool::Options;
|
||||
use GEmeTool::Save;
|
||||
use GEmeTool::View::LogWindow;
|
||||
use Cairo::GObject;
|
||||
use GEmeTool::View::PokemonPCWindow;
|
||||
|
||||
use Moo;
|
||||
|
||||
@ -219,11 +220,11 @@ sub open_file {
|
||||
}
|
||||
|
||||
sub start_editing_file {
|
||||
my $self = shift;
|
||||
my $file = $self->_file;
|
||||
my $save_as_action = $self->_save_as_action;
|
||||
my $pc_action = $self->_pc_action;
|
||||
my $box_app = Gtk4::Box->new( 'vertical', 0 );
|
||||
my $self = shift;
|
||||
my $file = $self->_file;
|
||||
my $save_as_action = $self->_save_as_action;
|
||||
my $pc_action = $self->_pc_action;
|
||||
my $box_app = Gtk4::Box->new( 'vertical', 0 );
|
||||
$self->_save( GEmeTool::Save->instance($file) );
|
||||
my $save_obj = $self->_save;
|
||||
|
||||
@ -324,82 +325,7 @@ sub activate_about {
|
||||
my $root = path(__FILE__)->parent->parent->parent->parent;
|
||||
|
||||
sub activate_view_pc {
|
||||
my $self = shift;
|
||||
my $gtk_window = Gtk4::Window->new;
|
||||
my $canvas = Gtk4::DrawingArea->new;
|
||||
$gtk_window->set_default_size( 312, 340 );
|
||||
$gtk_window->set_resizable(0);
|
||||
$canvas->set_draw_func(
|
||||
sub {
|
||||
my $canvas = shift;
|
||||
my $cairo = shift;
|
||||
my $width = shift;
|
||||
my $height = shift;
|
||||
|
||||
$self->draw_box($cairo);
|
||||
$self->draw_pokemon($cairo);
|
||||
$self->draw_box_name($cairo);
|
||||
}
|
||||
);
|
||||
$gtk_window->set_child($canvas);
|
||||
$gtk_window->present;
|
||||
}
|
||||
|
||||
sub draw_box_name {
|
||||
my $self = shift;
|
||||
my $cairo = shift;
|
||||
my $save = $self->_save;
|
||||
my $pc = $save->get_pc_system;
|
||||
my $box = $pc->get_box(0);
|
||||
my $name = Rsaves::translate_3rd_encoding($box->name);
|
||||
$cairo->scale( 1, 1 );
|
||||
$cairo->set_source_rgb(0, 0, 0);
|
||||
$cairo->select_font_face('monospace', 'normal', 'normal');
|
||||
$cairo->set_font_size(20);
|
||||
$cairo->move_to(75 - (length($name) * 5), 19);
|
||||
$cairo->show_text($name);
|
||||
}
|
||||
|
||||
sub draw_pokemon {
|
||||
my $self = shift;
|
||||
my $cairo = shift;
|
||||
my $save = $self->_save;
|
||||
my $pc = $save->get_pc_system;
|
||||
my $box = $pc->get_box(0);
|
||||
$cairo->scale(0.95, 0.95);
|
||||
for ( my $i = 0 ; $i < 5 ; $i++ ) {
|
||||
# ROW
|
||||
for ( my $j = 0 ; $j < 6 ; $j++ ) {
|
||||
# COLUMN
|
||||
my $pokemon = $box->get_pokemon($i*6 + $j);
|
||||
my $pokemon_image =
|
||||
$root->child($pokemon->get_image);
|
||||
my $surface = Cairo::ImageSurface->create_from_png($pokemon_image);
|
||||
my $output_image = Cairo::ImageSurface->create( 'argb32', 32, 32 );
|
||||
my $image_context = Cairo::Context->create($output_image);
|
||||
$image_context->set_source_surface( $surface, 0, 0 );
|
||||
$image_context->get_source()->set_filter('nearest');
|
||||
$image_context->paint;
|
||||
my $p = 25;
|
||||
$cairo->set_source_surface( $output_image, $j * ($p + 1),
|
||||
20 + ( ( $p - 3 ) * $i ) );
|
||||
$cairo->get_source()->set_filter('nearest');
|
||||
$cairo->paint;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
sub draw_box {
|
||||
my $self = shift;
|
||||
my $cairo = shift;
|
||||
my $surface = Cairo::ImageSurface->create_from_png(
|
||||
$root->child('resources/forest.png') );
|
||||
|
||||
$cairo->scale( 2, 2 );
|
||||
$cairo->set_source_surface( $surface, 0, 0 );
|
||||
$cairo->get_source()->set_filter('nearest');
|
||||
|
||||
$cairo->paint;
|
||||
|
||||
my $self = shift;
|
||||
GEmeTool::View::PokemonPCWindow->new( _save => $self->_save )->start;
|
||||
}
|
||||
1;
|
||||
|
234
lib/GEmeTool/View/PokemonPCWindow.pm
Normal file
234
lib/GEmeTool/View/PokemonPCWindow.pm
Normal file
@ -0,0 +1,234 @@
|
||||
package GEmeTool::View::PokemonPCWindow;
|
||||
|
||||
use v5.16.3;
|
||||
|
||||
use strict;
|
||||
use warnings;
|
||||
|
||||
use Cairo::GObject;
|
||||
use Glib;
|
||||
use Glib::IO;
|
||||
use Path::Tiny;
|
||||
use Math::Trig;
|
||||
|
||||
use Moo;
|
||||
|
||||
Glib::Object::Introspection->setup(
|
||||
basename => 'Gtk',
|
||||
version => '4.0',
|
||||
package => 'Gtk4',
|
||||
);
|
||||
|
||||
Glib::Object::Introspection->setup(
|
||||
basename => 'Gdk',
|
||||
version => '4.0',
|
||||
package => 'Gdk',
|
||||
);
|
||||
|
||||
has _save => (
|
||||
is => 'ro',
|
||||
required => 1,
|
||||
);
|
||||
|
||||
|
||||
my $BOX_X = 275;
|
||||
my $BOX_Y = 50;
|
||||
my $BOX_WIDTH = 312;
|
||||
my $BOX_HEIGHT = 340;
|
||||
|
||||
has _cursor_position => ( is => 'rw' );
|
||||
|
||||
my $root = path(__FILE__)->parent->parent->parent->parent;
|
||||
|
||||
sub start {
|
||||
my $self = shift;
|
||||
my $gtk_window = Gtk4::Window->new;
|
||||
my $controller_motion = Gtk4::EventControllerMotion->new;
|
||||
$controller_motion->signal_connect(
|
||||
motion => sub {
|
||||
my ( $x, $y ) = @_[ 1, 2 ];
|
||||
$self->_cursor_position( [ $x, $y ] );
|
||||
}
|
||||
);
|
||||
my $canvas = Gtk4::DrawingArea->new;
|
||||
$canvas->add_controller($controller_motion);
|
||||
my $scale_factor_pc = 2.5;
|
||||
my ($width, $height) = map { $_ * $scale_factor_pc } (256, 158);
|
||||
$gtk_window->set_default_size( $width, $height );
|
||||
$gtk_window->set_resizable(0);
|
||||
$canvas->set_draw_func(
|
||||
sub {
|
||||
my $canvas = shift;
|
||||
my $cairo = shift;
|
||||
my $width = shift;
|
||||
my $height = shift;
|
||||
|
||||
$self->draw_pc($cairo, $scale_factor_pc);
|
||||
{
|
||||
my $output_box = Cairo::ImageSurface->create( 'argb32', $BOX_WIDTH, $BOX_HEIGHT );
|
||||
my $box_context = Cairo::Context->create($output_box);
|
||||
$self->draw_box($box_context);
|
||||
my $selected_pokemon = $self->get_selected_pokemon;
|
||||
$self->draw_pokemon( $box_context, $selected_pokemon );
|
||||
$self->draw_box_name($box_context);
|
||||
$cairo->set_source_surface( $output_box, $BOX_X, $BOX_Y );
|
||||
$cairo->paint;
|
||||
}
|
||||
$self->draw_cursor($cairo);
|
||||
}
|
||||
);
|
||||
$gtk_window->set_child($canvas);
|
||||
$gtk_window->present;
|
||||
Glib::Timeout->add(
|
||||
1000 / 15,
|
||||
sub {
|
||||
$canvas->queue_draw;
|
||||
return 1;
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
sub draw_pc {
|
||||
my $self = shift;
|
||||
my $cairo = shift;
|
||||
my $scale_factor = shift;
|
||||
$cairo->scale( ($scale_factor) x 2 );
|
||||
my $surface = Cairo::ImageSurface->create_from_png($root->child('resources/pc_background.png'));
|
||||
$cairo->set_source_surface( $surface, 0, 0 );
|
||||
$cairo->get_source()->set_filter('nearest');
|
||||
$cairo->paint;
|
||||
$cairo->scale( ( 1 / $scale_factor ) x 2 );
|
||||
}
|
||||
|
||||
sub draw_cursor {
|
||||
my $self = shift;
|
||||
my $cairo = shift;
|
||||
my $cursor_png = $root->child('resources/hand_cursor.png');
|
||||
my $surface = Cairo::ImageSurface->create_from_png($cursor_png);
|
||||
my $output_image = Cairo::ImageSurface->create( 'argb32', 32, 32 );
|
||||
my $image_context = Cairo::Context->create($output_image);
|
||||
my $cursor_position = $self->_cursor_position;
|
||||
return if !defined $cursor_position;
|
||||
my $scale_factor = 0.95 * 2;
|
||||
$cairo->scale( ($scale_factor) x 2 );
|
||||
my ( $x, $y ) = map { $_ / $scale_factor } @$cursor_position;
|
||||
$x -= 10;
|
||||
$y -= 20;
|
||||
$image_context->set_source_surface( $surface, 0, 0 );
|
||||
$image_context->get_source()->set_filter('nearest');
|
||||
$image_context->paint;
|
||||
my $p = 25;
|
||||
$cairo->set_source_surface( $output_image, $x, $y, );
|
||||
$cairo->get_source()->set_filter('nearest');
|
||||
$cairo->paint;
|
||||
$cairo->scale( ( 1 / $scale_factor ) x 2 );
|
||||
}
|
||||
|
||||
sub draw_box_name {
|
||||
my $self = shift;
|
||||
my $cairo = shift;
|
||||
my $save = $self->_save;
|
||||
my $pc = $save->get_pc_system;
|
||||
my $box = $pc->get_box(0);
|
||||
my $name = Rsaves::translate_3rd_encoding( $box->name );
|
||||
my $scale_factor = 0.95 * 2;
|
||||
$cairo->scale( $scale_factor, $scale_factor );
|
||||
$cairo->set_source_rgb( 0, 0, 0 );
|
||||
$cairo->select_font_face( 'monospace', 'normal', 'normal' );
|
||||
$cairo->set_font_size(20);
|
||||
$cairo->move_to( 75 - ( length($name) * 5 ), 19 );
|
||||
$cairo->show_text($name);
|
||||
$cairo->scale( ( 1 / $scale_factor ) x 2 );
|
||||
}
|
||||
|
||||
sub draw_pokemon {
|
||||
my $self = shift;
|
||||
my $cairo = shift;
|
||||
my $selected_pokemon = shift;
|
||||
my $save = $self->_save;
|
||||
my $pc = $save->get_pc_system;
|
||||
my $box = $pc->get_box(0);
|
||||
my $scale_factor = 0.95 * 2;
|
||||
$cairo->scale( $scale_factor, $scale_factor );
|
||||
|
||||
for ( my $i = 0 ; $i < 5 ; $i++ ) {
|
||||
|
||||
# ROW
|
||||
for ( my $j = 0 ; $j < 6 ; $j++ ) {
|
||||
|
||||
# COLUMN
|
||||
my $pokemon = $box->get_pokemon( $i * 6 + $j );
|
||||
my $is_selected =
|
||||
defined $selected_pokemon && $pokemon eq $selected_pokemon;
|
||||
my $pokemon_image = $root->child( $pokemon->get_image );
|
||||
my $p = 25;
|
||||
my $x = $j * ( $p + 1 );
|
||||
my $y = 20 + ( ( $p - 3 ) * $i );
|
||||
|
||||
if ($is_selected) {
|
||||
$cairo->set_source_rgb( 1, 1, 0 );
|
||||
$cairo->arc( $x + 5 + 11, $y + 10 + 11, 22/2, 0, pi*2 );
|
||||
$cairo->fill;
|
||||
}
|
||||
|
||||
my $surface = Cairo::ImageSurface->create_from_png($pokemon_image);
|
||||
my $output_image = Cairo::ImageSurface->create( 'argb32', 32, 32 );
|
||||
my $image_context = Cairo::Context->create($output_image);
|
||||
$image_context->set_source_surface( $surface, 0, 0 );
|
||||
$image_context->get_source()->set_filter('nearest');
|
||||
$image_context->paint;
|
||||
$cairo->set_source_surface( $output_image, $x, $y );
|
||||
$cairo->get_source()->set_filter('nearest');
|
||||
$cairo->paint;
|
||||
}
|
||||
}
|
||||
$cairo->scale( ( 1 / $scale_factor ) x 2 );
|
||||
}
|
||||
|
||||
sub get_selected_pokemon {
|
||||
my $self = shift;
|
||||
my $cursor_position = $self->_cursor_position;
|
||||
return if !defined $cursor_position;
|
||||
my ($x, $y) = @$cursor_position;
|
||||
|
||||
return if $x < $BOX_X;
|
||||
return if $y < $BOX_Y;
|
||||
|
||||
$x -= $BOX_X;
|
||||
$y -= $BOX_Y;
|
||||
|
||||
return if $x >= $BOX_WIDTH - 13;
|
||||
return if $y >= $BOX_HEIGHT;
|
||||
|
||||
my $scale_factor = 0.95 * 2;
|
||||
( $x, $y ) = map { $_ / $scale_factor } ($x, $y);
|
||||
return if $y <= 20;
|
||||
$y -= 20;
|
||||
|
||||
my $p = 25;
|
||||
my $i = int( $y / ( $p - 3 ) );
|
||||
my $j = int( $x / ( $p + 1 ) );
|
||||
my $save = $self->_save;
|
||||
my $pc = $save->get_pc_system;
|
||||
my $box = $pc->get_box(0);
|
||||
my $number = $i * 6 + $j;
|
||||
return if $number > 29;
|
||||
my $pokemon = $box->get_pokemon($number);
|
||||
return $pokemon;
|
||||
}
|
||||
|
||||
sub draw_box {
|
||||
my $self = shift;
|
||||
my $cairo = shift;
|
||||
my $surface = Cairo::ImageSurface->create_from_png(
|
||||
$root->child('resources/forest.png') );
|
||||
|
||||
$cairo->scale( 2, 2 );
|
||||
$cairo->set_source_surface( $surface, 0, 0 );
|
||||
$cairo->get_source()->set_filter('nearest');
|
||||
|
||||
$cairo->paint;
|
||||
$cairo->scale( 1 / 2, 1 / 2 );
|
||||
|
||||
}
|
||||
1;
|
BIN
resources/hand_cursor.png
Normal file
BIN
resources/hand_cursor.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 24 KiB |
BIN
resources/pc_background.png
Normal file
BIN
resources/pc_background.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 167 KiB |
Loading…
Reference in New Issue
Block a user