void net_write_error (int sock, int version, char *driver_info, char *cas_info, int cas_info_size, int indicator, int code, char *msg) { size_t len = NET_SIZE_INT; size_t err_msg_len = 0; char err_msg[ERR_MSG_LENGTH]; assert (code != NO_ERROR); if (version >= CAS_MAKE_VER (8, 3, 0)) { len += NET_SIZE_INT; } err_msg_len = net_error_append_shard_info (err_msg, msg, ERR_MSG_LENGTH); if (err_msg_len > 0) { len += err_msg_len + 1; } net_write_int (sock, len); if (cas_info_size > 0) { net_write_stream (sock, cas_info, cas_info_size); } if (version >= CAS_MAKE_VER (8, 3, 0)) { net_write_int (sock, indicator); } if (!DOES_CLIENT_MATCH_THE_PROTOCOL (version, PROTOCOL_V2) && !cas_di_understand_renewed_error_code (driver_info) && code != NO_ERROR) { if (indicator == CAS_ERROR_INDICATOR || code == CAS_ER_NOT_AUTHORIZED_CLIENT) { code = CAS_CONV_ERROR_TO_OLD (code); } } net_write_int (sock, code); if (err_msg_len > 0) { net_write_stream (sock, err_msg, err_msg_len + 1); } }
/* ==================== set_gamestate_GAME Start a new game ==================== */ void set_gamestate_GAME() { if (g_init()) return; // return to the editor if game init failed gamestate = GAME; if (net_is_server) { net_write_sync_square(); srv_sync_player_name(); net_write_int(STATE_CHANGE_BYTE, 1, GAME); } }
/* ==================== g_add_segment pos_x and pos_y are "-1" for local input, otherwise they are coordinate from net ==================== */ void g_add_segment(int pos_x, int pos_y, int side) { if (pos_x == -1) { if(!net_game || (local_player.turn == local_player.player_n)) { pos_x = g_min_x + (input.mouse_x - g_offset_x) / g_square_size; pos_y = g_min_y + (input.mouse_y - g_offset_y) / g_square_size; } } if (pos_x < g_min_x || pos_x >= g_max_x) return; if (pos_y < g_min_y || pos_y >= g_max_y) return; if (!squares[pos_y][pos_x].active) return; int center_x = squares[pos_y][pos_x].x1 + (squares[pos_y][pos_x].x2 - squares[pos_y][pos_x].x1) / 2; int center_y = squares[pos_y][pos_x].y1 + (squares[pos_y][pos_x].y2 - squares[pos_y][pos_x].y1) / 2; int current_dist; int shortest_dist = g_square_size * 2; // start with maximum distance if (side == -1) { // top current_dist = sqrt(ipow(input.mouse_y - squares[pos_y][pos_x].y1, 2) + ipow(input.mouse_x - center_x, 2)); if (current_dist < shortest_dist) { shortest_dist = current_dist; side = UP; } // right current_dist = sqrt(ipow(input.mouse_y - center_y, 2) + ipow(input.mouse_x - squares[pos_y][pos_x].x2, 2)); if (current_dist < shortest_dist) { shortest_dist = current_dist; side = RIGHT; } // down current_dist = sqrt(ipow(input.mouse_x - center_x, 2) + ipow(input.mouse_y - squares[pos_y][pos_x].y2, 2)); if (current_dist < shortest_dist) { shortest_dist = current_dist; side = DOWN; } // left current_dist = sqrt(ipow(input.mouse_x - squares[pos_y][pos_x].x1, 2) + ipow(input.mouse_y - center_y, 2)); if (current_dist < shortest_dist) { shortest_dist = current_dist; side = LEFT; } } if (net_is_server || (net_is_client && (local_player.turn == local_player.player_n))) net_write_int(G_ADD_SEG_BYTE, 3, pos_x, pos_y, side); switch (side) { case UP: if (squares[pos_y][pos_x].owner_up == NONE) { squares[pos_y][pos_x].owner_up = local_player.turn; *squares[pos_y][pos_x].neighbour_up = local_player.turn; } else return; break; case RIGHT: if (squares[pos_y][pos_x].owner_right == NONE) { squares[pos_y][pos_x].owner_right = local_player.turn; *squares[pos_y][pos_x].neighbour_right = local_player.turn; } else return; break; case DOWN: if (squares[pos_y][pos_x].owner_down == NONE) { squares[pos_y][pos_x].owner_down = local_player.turn; *squares[pos_y][pos_x].neighbour_down = local_player.turn; } else return; break; case LEFT: if (squares[pos_y][pos_x].owner_left == NONE) { squares[pos_y][pos_x].owner_left = local_player.turn; *squares[pos_y][pos_x].neighbour_left = local_player.turn; } else return; break; } g_check_complete_square(&squares[pos_y][pos_x]); // check neighbour squares if (pos_y != 0) g_check_complete_square(&squares[pos_y - 1][pos_x]); if (pos_x != ed_grid_w) g_check_complete_square(&squares[pos_y][pos_x + 1]); if (pos_y < ed_grid_h - 1) g_check_complete_square(&squares[pos_y + 1][pos_x]); if (pos_x != 0) g_check_complete_square(&squares[pos_y][pos_x - 1]); input.mouse_button_left = false; input.mouse_button_right = false; if (!net_game || net_is_server) { // game ended if (!squares_remaining) { if (local_player.turn == NONE) return; // no winner // move current player moving square to winning player if (local_player.turn != winning_player) { local_player.turn = winning_player; fx_new_transition(NULL, 5, FX_PLAYER_CHANGE); } return; } if (local_player.turn == PLAYER_0) { local_player.turn = PLAYER_1; } else { local_player.turn = PLAYER_0; } if (net_is_server) net_write_int(G_PLAYER_TURN_BYTE, 1, local_player.turn); fx_new_transition(NULL, 5, FX_PLAYER_CHANGE); } }