Ejemplo n.º 1
0
void newsroom_set_names(newsroom_local *local,
                        const char *pilot1, const char *pilot2,
                        const char *har1, const char *har2,
                        int sex1, int sex2) {

    str_create_from_cstr(&local->pilot1, pilot1);
    str_create_from_cstr(&local->pilot2, pilot2);
    str_create_from_cstr(&local->har1, har1);
    str_create_from_cstr(&local->har2, har2);
    local->sex1 = sex1;
    local->sex2 = sex2;

    // Remove the whitespace at the end of pilots name
    if(isspace(str_at(&local->pilot1, str_size(&local->pilot1)-1))) {
        str_remove_at(&local->pilot1, str_size(&local->pilot1)-1);
    }
    if(isspace(str_at(&local->pilot2, str_size(&local->pilot2)-1))) {
        str_remove_at(&local->pilot2, str_size(&local->pilot2)-1);
    }
}
Ejemplo n.º 2
0
int is_valid_move(af_move *move, har *h) {
    // If category is any of these, and bot is not close, then
    // do not try to execute any of them. This attempts
    // to make the HARs close up instead of standing in place
    // wawing their hands towards each other. Not a perfect solution.
    switch(move->category) {
        case CAT_CLOSE:
        case CAT_LOW:
        case CAT_MEDIUM:
        case CAT_HIGH:
            // Only allow handwaving if close or jumping
            if(!h->close && h->state != STATE_JUMPING) {
                return 0;
            }
    }
    if(move->category == CAT_JUMPING && h->state != STATE_JUMPING) {
        // not jumping but trying to execute a jumping move
        return 0;
    }
    if(move->category != CAT_JUMPING && h->state == STATE_JUMPING) {
        // jumping but this move is not a jumping move
        return 0;
    }
    if(move->category == CAT_SCRAP && h->state != STATE_VICTORY) {
        return 0;
    }

    if(move->category == CAT_DESTRUCTION && h->state != STATE_SCRAP) {
        return 0;
    }
    // XXX check for chaining?

    int move_str_len = str_size(&move->move_string);
    char tmp;
    for(int i = 0; i < move_str_len; i++) {
        tmp = str_at(&move->move_string, i);
        if(!((tmp >= '1' && tmp <= '9') || tmp == 'K' || tmp == 'P')) {
            return 0;
        }
    }

    if((move->damage > 0
        || move->category == CAT_PROJECTILE
        || move->category == CAT_SCRAP
        || move->category == CAT_DESTRUCTION) && move_str_len > 0) 
    {
        return 1;
    }

    return 0;
}
Ejemplo n.º 3
0
void newsroom_fixup_str(newsroom_local *local) {

    /*
     * Substitution table

       1= Player1 - Crystal
       2= Player2 - Steffan
       3= HAR1 - jaguar
       4= HAR2 - shadow
       5= Arena - power plant
       6= His/Her P1 - Her
       7= Him/Her P1 - Her
       8= He/She P1 - She
       10= Him/Her P2 - Him
       11= He/She P2 - He
    */

    const char *text = NULL;

    if(local->screen == 0) {
        text = lang_get(NEWSROOM_TEXT+local->news_id);
    } else {
        text = lang_get(NEWSROOM_TEXT+local->news_id+1);
    }

    str textstr;
    size_t prevpos=0, pos = 0;

    str_create_from_cstr(&textstr, text);
    str_free(&local->news_str);
    while(str_next_of(&textstr, '~', &pos)) {
        str tmp;
        str_create(&tmp);
        str_substr(&tmp, &textstr, prevpos, pos);
        str_append(&local->news_str, &tmp);
        str_free(&tmp);

        // replace ~n tokens
        char n = str_at(&textstr, pos+1);
        char nn = str_at(&textstr, pos+2);
        switch(n) {
            case '1':
                if(nn == '0') {
                    // ~10
                    str_append_c(&local->news_str, object_pronoun(local->sex2));
                    pos++;
                } else if(nn == '1') {
                    // ~11
                    str_append_c(&local->news_str, subject_pronoun(local->sex2));
                    pos++;
                } else {
                    // ~1
                    str_append(&local->news_str, &local->pilot1);
                }
                break;
            case '2':
                str_append(&local->news_str, &local->pilot2);
                break;
            case '3':
                str_append(&local->news_str, &local->har1);
                break;
            case '4':
                str_append(&local->news_str, &local->har2);
                break;
            case '5':
                str_append_c(&local->news_str, "Stadium");
                break;
            case '6':
                str_append_c(&local->news_str, "The");
                break;
            case '7':
                str_append_c(&local->news_str, object_pronoun(local->sex1));
                break;
            case '8':
                str_append_c(&local->news_str, subject_pronoun(local->sex1));
                break;
            case '9':
                str_append_c(&local->news_str, "WTF");
                break;
        }
        pos+=2;
        prevpos = pos;
    }
    str tmp;
    str_create(&tmp);
    str_substr(&tmp, &textstr, pos, str_size(&textstr));
    str_append(&local->news_str, &tmp);
    str_free(&tmp);
    str_free(&textstr);
}
Ejemplo n.º 4
0
static char _scr_str_next(string_script * scr) {
  char c;
  return (0 != (c = str_at(scr->s, scr->pos++))) ? c : EOF;
}
Ejemplo n.º 5
0
int ai_controller_poll(controller *ctrl, ctrl_event **ev) {
    ai *a = ctrl->data;
    object *o = ctrl->har;
    if (!o) {
        return 1;
    }
    har *h = object_get_userdata(o);
    object *o_enemy = game_state_get_player(o->gs, h->player_id == 1 ? 0 : 1)->har;

    // Do not run AI while the game is paused
    if(game_state_is_paused(o->gs)) { return 0; }

    // Do not run AI while match is starting or ending
    // XXX this prevents the AI from doing scrap/destruction moves
    // XXX this could be fixed by providing a "scene changed" event
    if(is_arena(game_state_get_scene(o->gs)->id) &&
       arena_get_state(game_state_get_scene(o->gs)) != ARENA_STATE_FIGHTING) {

        // null out selected move to fix the "AI not moving problem"
        a->selected_move = NULL;
        return 0;
    }

    // Grab all projectiles on screen
    vector_clear(&a->active_projectiles);
    game_state_get_projectiles(o->gs, &a->active_projectiles);

    // Try to block har
    if(ai_block_har(ctrl, ev)) {
        return 0;
    }

    // Try to block projectiles
    if(ai_block_projectile(ctrl, ev)) {
        return 0;
    }

    if(a->selected_move) {
        // finish doing the selected move first
        if(a->input_lag_timer > 0) {
            a->input_lag_timer--;
        } else {
            a->move_str_pos--;
            if(a->move_str_pos <= 0) {
                a->move_str_pos = 0;
            }
            a->input_lag_timer = a->input_lag;
        }
        int ch = str_at(&a->selected_move->move_string, a->move_str_pos);
        controller_cmd(ctrl, char_to_act(ch, o->direction), ev);

    } else if(rand_int(100) < a->difficulty) {
        af_move *selected_move = NULL;
        int top_value = 0;

        // Attack
        for(int i = 0; i < 70; i++) {
            af_move *move = NULL;
            if((move = af_get_move(h->af_data, i))) {
                move_stat *ms = &a->move_stats[i];
                if(is_valid_move(move, h)) {
                    int value = ms->value + rand_int(10);
                    if (ms->min_hit_dist != -1){
                        if (ms->last_dist < ms->max_hit_dist+5 && ms->last_dist > ms->min_hit_dist+5){
                            value += 2;
                        } else if (ms->last_dist > ms->max_hit_dist+10){
                            value -= 3;
                        }
                    }

                    value -= ms->attempts/2;
                    value -= ms->consecutive*2;

                    if (is_special_move(move) && !maybe(a->difficulty)) {
                        DEBUG("skipping special move %s because of difficulty", str_c(&move->move_string));
                        continue;
                    }

                    if (selected_move == NULL){
                        selected_move = move;
                        top_value = value;
                    } else if (value > top_value) {
                        selected_move = move;
                        top_value = value;
                    }
                }
            }
        }
        for(int i = 0; i < 70; i++) {
            a->move_stats[i].consecutive /= 2;
        }
        if(selected_move) {
            a->move_stats[selected_move->id].attempts++;
            a->move_stats[selected_move->id].consecutive++;

            // do the move
            a->selected_move = selected_move;
            a->move_str_pos = str_size(&selected_move->move_string)-1;
            a->move_stats[a->selected_move->id].last_dist = fabsf(o->pos.x - o_enemy->pos.x);
            a->blocked = 0;
            DEBUG("AI selected move %s", str_c(&selected_move->move_string));
        }
    } else {
        // Change action after 30 ticks
        if(a->act_timer <= 0 && rand_int(100) > 88){
            int p = rand_int(100);
            if(p > 40){
                // walk forward
                a->cur_act = (o->direction == OBJECT_FACE_RIGHT ? ACT_RIGHT : ACT_LEFT);
            } else if(p > 20){
                // walk backward
                a->cur_act = (o->direction == OBJECT_FACE_RIGHT ? ACT_LEFT : ACT_RIGHT);
            } else if(p > 10){
                // do nothing
                a->cur_act = ACT_STOP;
            } else {
                // crouch and block
                a->cur_act = (o->direction == OBJECT_FACE_RIGHT ? ACT_DOWN|ACT_LEFT : ACT_DOWN|ACT_RIGHT);
            }

            a->act_timer = 30;
            controller_cmd(ctrl, a->cur_act, ev);
        } else {
            a->act_timer--;
        }

        // Jump once in a while
        if(rand_int(100) == 88){
            if(o->vel.x < 0) {
                controller_cmd(ctrl, ACT_UP|ACT_LEFT, ev);
            } else if(o->vel.x > 0) {
                controller_cmd(ctrl, ACT_UP|ACT_RIGHT, ev);
            } else {
                controller_cmd(ctrl, ACT_UP, ev);
            }
        }
    }
    return 0;
}