Games-Lacuna-Task

 view release on metacpan or  search on metacpan

lib/Games/Lacuna/Task/Action/Defence.pm  view on Meta::CPAN

            }
            when('Docked') {
                # do nothing
            }
            default {
                next LOCAL_SHIPS;
            }
        }
        
        $count++;
    }
    
    return $count;
}

sub get_saws {
    my ($self,$star_id,$first_attacker_arrive) = @_;
    
    my $count = 0;
    
    SYSTEM_PLANETS:
    foreach my $planet_stats ($self->my_planets) {
        next SYSTEM_PLANETS
            if $planet_stats->{star_id} != $star_id;
        my @saws = $self->find_building($planet_stats->{id},'SAW');
        SAWS:
        foreach my $saw (@saws) {
            # Check SAW level
            next SAWS
                unless ($saw->{level} * 1000 * $saw->{efficiency} / 100)  >= $self->min_defender_combat;
            
            # Check SAW availability
            if (defined $saw->{work}) {
                my $available = parse_date($saw->{work}{end});
                next SAWS
                    if $available > $first_attacker_arrive;
            }
            
            $count++;
        }
    }
    
    return $count;
}

sub dispatch_defender {
    my ($self,$to_body_id,$from_body_id,$count) = @_;
    
    my $spaceport = $self->find_building($from_body_id,'SpacePort');
    return 0
        unless $spaceport;
    my $spaceport_object = $self->build_object($spaceport);
    
    # Get all available ships
    my $ships_data = $self->request(
        object  => $spaceport_object,
        method  => 'view_all_ships',
        params  => [ { no_paging => 1 }, { tag => [ 'War' ] } ],
    );
    
    my @relocate_ship;
    my $dispatch_ship = 0;
    
    # Loop all war ships
    LOCAL_SHIPS:
    foreach my $ship (@{$ships_data->{ships}}) {
        next LOCAL_SHIPS
            unless $ship->{type} eq 'fighter'
            || $ship->{type} eq 'sweeper';
        
        next LOCAL_SHIPS
            if $ship->{name} =~ m/\!/;
        
        next LOCAL_SHIPS
            if $ship->{type} eq 'sweeper'
            && $ship->{name} !~ m/(dispatch|\$|\+)/;
        
        next LOCAL_SHIPS
            if $ship->{combat} < $self->min_defender_combat;
        
        next LOCAL_SHIPS
            unless $ship->{task} eq 'Docked';
        
        # Dispatch fighter directly
        if ($ship->{type} eq 'fighter') {
            $dispatch_ship++;
            $self->request(
                object  => $spaceport_object,
                method  => 'send_ship',
                params  => [ $ship->{id}, { body_id => $to_body_id } ],
            );
        # Add sweeper to list of dispatchable units
        } elsif ($ship->{type} eq 'sweeper') {
            push(@relocate_ship,$ship->{id});
        }
        
        # Check if we have enough defenders
        return $dispatch_ship
            if $dispatch_ship >= $count;
    }
    
    # Relocate sweepers via push
    my $relocateable_ships = min( ($count-$dispatch_ship) , scalar(@relocate_ship), $self->_planet_attack->{$to_body_id}{free_slots} );
    if ($relocateable_ships > 0) {
        my @relocate_ships_final = @relocate_ship[0..($relocateable_ships-1)];
        $dispatch_ship += $self->push_ships($from_body_id,$to_body_id,\@relocate_ships_final);
    }
    
    return $dispatch_ship;
}

sub recall_defender {
    my ($self,$body_id,$first_attacker_arrive) = @_;
    
    my $spaceport = $self->find_building($body_id,'SpacePort');
    return 0
        unless $spaceport;
    my $spaceport_object = $self->build_object($spaceport);
    
    my $count = 0;
    
    # Get all available ships
    my $ships_data = $self->request(
        object  => $spaceport_object,
        method  => 'recall_all',
    );
    
    RECALL_SHIPS:
    foreach my $ship (@{$ships_data->{ships}}) {
        # Check if ship arrives on time 
        my $arrive = parse_date($ship->{ship}{date_arrives});
        next RECALL_SHIPS
            if $arrive > $first_attacker_arrive;
        $count++;
    }
    
    return $count;
}

__PACKAGE__->meta->make_immutable;
no Moose;
1;



( run in 0.524 second using v1.01-cache-2.11-cpan-5511b514fd6 )