X
XirmiX
Guest
I've come to understand networking a bit better, thanks to one particularly helpful user (Tsa05). Since, I'm not sure whether the previous topic concerning networking would still be relevant, I thought I'd create this to tackle this specific issue specifically. Call me impatient, but I'd rather be trying to do something and trying to get any help I can rather than sit back and wait for it to arrive. I've been able to get as far as getting the client connecting to the server, or so that's what I think. I found out that I had not been connecting to the server at all this entire time, because buffer_send_type was not a defined variable. Then I defined the variable... and I STILL got the exact same error:
The error occurs on the server side once I switch off the client. The server tries to read a string, but instead reads a number. That doesn't make sense, because if you look at my code, you can see that I'm sending a string to the server and it's storing that string, and when the server calls back that string to write it to other clients, it should be reading a string, not a number 5, or whatever it is the error's popping up. I should mention that the error used to have 0 instead of 5 in it when my server code was sending buffers through connection code. The error was still the same in other regard, however, and happened with this exact buffer_write function.
What is going on? What am I doing wrong? I thought I comprehended what I was doing, but apparently there's something wrong that creates this error every time the client disconnects, and I'm not getting any of my text messages displayed at all! And for some reason my player object is not being spawned in either.
FATAL ERROR in
action number 1
of Async Event: Networking
for object obj_connection:
buffer_write argument 1 incorrect type (5) expecting a String (YYGS)
at gml_Object_obj_connection_NetworkingEvent_1 (line 38) - buffer_write(send_buffer, buffer_string, client_id); //only sending ID, because deleting ID key will subsequently delete player username
action number 1
of Async Event: Networking
for object obj_connection:
buffer_write argument 1 incorrect type (5) expecting a String (YYGS)
at gml_Object_obj_connection_NetworkingEvent_1 (line 38) - buffer_write(send_buffer, buffer_string, client_id); //only sending ID, because deleting ID key will subsequently delete player username
The error occurs on the server side once I switch off the client. The server tries to read a string, but instead reads a number. That doesn't make sense, because if you look at my code, you can see that I'm sending a string to the server and it's storing that string, and when the server calls back that string to write it to other clients, it should be reading a string, not a number 5, or whatever it is the error's popping up. I should mention that the error used to have 0 instead of 5 in it when my server code was sending buffers through connection code. The error was still the same in other regard, however, and happened with this exact buffer_write function.
Client Create event code
Client Networking event code
Client Draw event code
Alarm 0 event code
Code:
///Initializing connection socket
{
joined = false;
playerjoined = false;
playerleft = false;
message = "";
x_previous = x+1;
y_previous = y+1;
x_current = x;
y_current = y;
send_data = 0;
port = 50000;
IP = "127.0.0.1";
socket_plug = network_create_socket(network_socket_tcp);
//send_buffer = buffer_create(256, buffer_fixed, 1);
network_connect_raw(socket_plug, IP, port);
client_amount = 0;
client_data = ds_map_create();
instance_data = ds_map_create();
myclient_id = "1234567890123456";//ini_read_string("Profile Data", "password", noone);
myplayer_username = "Scorpion";
buffer_type_send = 1;
}
Code:
type = async_load[? "type"];
switch(type)
{
//Sending data upon connection
case network_type_data:
switch(buffer_type_send)
{
//sending buffer type 1 (player enter)
case SEND_USER_ID:
//create a buffer with which to send information
var send_buffer = buffer_create(256, buffer_fixed, 1);
var buffer_type_write = SEND_USER_ID;
buffer_write(send_buffer, buffer_u8, buffer_type_write);
buffer_write(send_buffer, buffer_string, myclient_id);
buffer_write(send_buffer, buffer_string, myplayer_username);
network_send_raw(socket_plug, buffer_send, buffer_sizeof(buffer_send));
message = myplayer_username + " joined";
joined = true;
my_tank = instance_create(irandom(room_width), irandom(room_height), obj_player);
buffer_delete(send_buffer);
buffer_type_send = 0;
break;
//nothing to send when for buffer type 2 (disconnecting), that would be stupid
//sending buffer type 3 (equipment)
case SEND_EQUIPMENT_DATA:
var buffer_type_write = SEND_EQUIPMENT_DATA;
break;
//sending buffer type 4 (skins)
case SEND_SKINS_DATA:
var buffer_type_write = SEND_COORDINATE_DATA;
break;
//sending buffer type 5 (coordinates)
case SEND_COORDINATE_DATA:
var buffer_type_write = SEND_COORDINATE_DATA;
//create a buffer with which to send information
var send_buffer = buffer_create(256, buffer_fixed, 1);
buffer_write(send_buffer, buffer_u8, buffer_type_write);
buffer_write(send_buffer, buffer_f32, my_tank.x);
buffer_write(send_buffer, buffer_f32, my_tank.y);
network_send_raw(socket_plug, buffer_send, buffer_sizeof(buffer_send));
buffer_delete(send_buffer);
break;
//sending buffer type 6 (angles)
case SEND_ANGLE_DATA:
var buffer_type_write = SEND_ANGLE_DATA;
//create a buffer with which to send information
var send_buffer = buffer_create(256, buffer_fixed, 1);
buffer_write(send_buffer, buffer_u8, buffer_type_write);
buffer_write(send_buffer, buffer_f32, my_tank.direction);
network_send_raw(socket_plug, buffer_send, buffer_sizeof(buffer_send));
buffer_delete(send_buffer);
break;
}
buffer = async_load[? "buffer"];
buffer_seek(buffer, buffer_seek_start, 0);
//Identify buffer type
var buffer_type_read = buffer_read(buffer, buffer_u8);
switch(buffer_type_read)
{
//receiving buffer type 1 (player enter)
case ADD_USER_ID:
var client_id = buffer_read(buffer, buffer_string);
var player_username = buffer_read(buffer, buffer_string);
client_amount = buffer_read(buffer, buffer_u8);
client_data[? string(client_id)] = player_username;
var player_name = ds_map_find_value(client_data, client_id);
var player_joined_instance = instance_create(irandom(room_width), irandom(room_height), obj_player_other);
ds_map_add(instance_data, client_id, player_joined_instance.id);
message = player_name + " joined";
playerleft = true;
break;
//receiving buffer type 2 (player exit)
case REMOVE_USER_ID:
//reads buffers
var client_id = buffer_read(buffer, buffer_string);
client_amount= buffer_read(buffer, buffer_u8);
var player_name = ds_map_find_value(client_data, client_id);
message = player_name + " left";
playerleft = true;
//Deletes client ID from the client data list, subsequently, the client username, since client's id is its key
ds_map_delete(client_data, client_id);
break;
//receiving buffer type 4 (skins)
case 4:
break;
//receiving buffer type 5 (coordinates)
case 5:
var client_id = buffer_read(buffer, buffer_string);
var xx = buffer_read(buffer, buffer_f32);
var yy = buffer_read(buffer, buffer_f32);
var player_instance_current = ds_map_find_value(instance_data, client_id);
player_instance_current.x = xx;
player_instance_current.y = yy;
break;
//receiving buffer type 6 (angles)
case 6:
var client_id = buffer_read(buffer, buffer_string);
var rotation = buffer_read(buffer, buffer_f32);
var player_instance_current = ds_map_find_value(instance_data, client_id);
player_instance_current.direction = rotation;
break;
//unidentified case
case UNIDENTIFIED_BUFFER:
//show_error("A buffer received from the server was unidentified.", true);
break;
}
break;
}
Code:
draw_set_color(c_white);
draw_text(16, 16, client_amount);
if joined == true
{
draw_text(16, 2048, message);
alarm[0] = 200;
joined = false;
}
if playerjoined == true
{
draw_text(16, 2048, message);
alarm[0] = 200;
playerjoined = false;
}
if playerleft == true
{
draw_text(16, 2048, message);
alarm[0] = 200;
playerleft = false;
}
Code:
message = "";
Server Create event code
Server Networking event code
Server Draw event code
Code:
//declaring the type of connection (tcp)
server_type = network_socket_tcp;
//port number
port = 50000;
//max amount of clients that can connect to the server
max_players = 8;
//generating a server
server = network_create_server_raw(server_type, port, max_players);
//ds_list to hold a list of client sockets into
socket_map = ds_map_create();
//creating an integer variable, which will define how many players have joined
client_amount = ds_map_size(socket_map);
//ds_map in which to hold
client_data = ds_map_create();
joined = false;
message = "";
Code:
///Networking
type = async_load[? "type"];
//Switch statement, because needs a list of connection types... yeah
switch(type)
{
//case for the client connecting
case network_type_connect:
//Identify the connecting socket
client_socket_current = async_load[? "socket"];
//Updating the amount of players that are connected in the client amount variable
client_amount = ds_map_size(socket_map);
joined = true;
break;
//case for the client disconnecting
case network_type_disconnect:
//Identify the disconnecting socket
client_socket_current = async_load[? "socket"];
//Contained in a temporary variable, from the socket map, the ID number (a string) of the disconnecting socket
var client_id = ds_map_find_value(socket_map, client_socket_current);
//Updating the amount of players that are connected in the client amount variable
//client_amount = ds_map_size(socket_map);
//A temporary variable, which is needed to send amount of players connected, due to a disconnect, to other clients. Reason for this variable is quite complex...
var client_amount_tosend = ds_map_size(socket_map) - 1;
var buffer_type_write = 2;
//create a buffer with which to send information
var send_buffer = buffer_create(256, buffer_fixed, 1);
//writing data to send to buffer
buffer_write(send_buffer, buffer_u8, buffer_type_write);
buffer_write(send_buffer, buffer_string, client_id); //only sending ID, because deleting ID key will subsequently delete player username
buffer_write(send_buffer, buffer_u8, client_amount_tosend);
//If there are now 2 or more users connected, send data about the new client to other clients
if (ds_map_size(socket_map) >= 2)
{
for(i = 0; i < ds_map_size(socket_map); i++)
{
socket_in_use = ds_map_find_value(socket_map, i);
network_send_raw(socket_in_use, send_buffer, buffer_sizeof(send_buffer));
}
}
//In the client_data map, delete from client data the disconnecting client's ID along with their name (ID being the key and username being its string value)
ds_map_delete(client_data, client_id);
//Remove the disconnecting player socket from the socket list
ds_map_delete(socket_map, client_socket_current);
//Updating the amount of players that are connected in the client amount variable
client_amount = ds_list_size(socket_map);
buffer_delete(send_buffer);
break;
//case for receiving and sending data
case network_type_data:
//Identify the sender client
client_socket_current = async_load[? "id"];
//Identify buffer sent
buffer = async_load[? "buffer"];
//Read the buffers sent by the joining client
buffer_seek(buffer, buffer_seek_start, 0);
var buffer_type_read = buffer_read(buffer, buffer_u8); //Read's the initial integer sent, identifying the buffer type
switch(buffer_type_read)
{
//sending buffer type 1 (player enter)
case 1:
var client_id = buffer_read(buffer, buffer_string); //Client's ID number
var player_username = buffer_read(buffer, buffer_string); //Client's username
//Add new player socket to the socket list
ds_map_add(socket_map, client_socket_current, client_id);
//In the client_data map, create a new key with the ID of the player, which will hold onto the user's username
client_data[? string(client_id)] = player_username;
//Defining a temporary variable for the buffer number
var buffer_type_write = 1;
//create a buffer with which to send information
send_buffer = buffer_create(256, buffer_fixed, 1);
//writing data to send to buffer
buffer_write(send_buffer, buffer_u8, buffer_type_write);
buffer_write(send_buffer, buffer_string, client_id);
buffer_write(send_buffer, buffer_string, player_username);
buffer_write(send_buffer, buffer_u8, client_amount);
//If there are now 2 or more users connected, send data about the new client to other clients
if (ds_map_size(socket_map) >= 2)
{
for(i = 0; i < ds_map_size(socket_map); i++)
{
socket_in_use = ds_map_find_value(socket_map, i);
network_send_raw(socket_in_use, send_buffer, buffer_sizeof(send_buffer));
}
}
buffer_delete(send_buffer);
break;
//buffer type 2 already set to be sending upon disconnection
//sending buffer type 3 (equipment)
case 3:
var turret = buffer_read(buffer, buffer_u8);
var hull = buffer_read(buffer, buffer_u8);
break;
//sending buffer type 4 (skins)
case 4:
var turret = buffer_read(buffer, buffer_u8);
var hull = buffer_read(buffer, buffer_u8);
break;
//sending buffer type 5 (coordinates)
case 5:
var client_id = ds_map_find_value(socket_map, client_socket_current);
var xx = buffer_read(buffer, buffer_f32);
var yy = buffer_read(buffer, buffer_f32);
//create a buffer with which to send information
var send_buffer = buffer_create(256, buffer_fixed, 1);
buffer_write(send_buffer, buffer_string, client_id);
buffer_write(send_buffer, buffer_f32, xx);
buffer_write(send_buffer, buffer_f32, yy);
if (ds_map_size(socket_map) >= 2)
{
for(i = 0; i < ds_map_size(socket_map); i++)
{
socket_in_use = ds_map_find_value(socket_map, i);
if(i != client_socket_current)
{
network_send_raw(socket_in_use, send_buffer, buffer_sizeof(send_buffer));
}
}
}
buffer_delete(send_buffer);
break;
//sending buffer type 6 (angles)
case 6:
var client_id = ds_map_find_value(socket_map, client_socket_current);
var rotation = buffer_read(buffer, buffer_f32);
//create a buffer with which to send information
var send_buffer = buffer_create(256, buffer_fixed, 1);
buffer_write(send_buffer, buffer_string, client_id);
buffer_write(send_buffer, buffer_f32, rotation);
if (ds_map_size(socket_map) >= 2)
{
for(i = 0; i < ds_map_size(socket_map); i++)
{
socket_in_use = ds_map_find_value(socket_map, i);
if(i != client_socket_current)
{
network_send_raw(socket_in_use, send_buffer, buffer_sizeof(send_buffer));
}
}
}
buffer_delete(send_buffer);
break;
}
break;
}
Code:
draw_set_colour(c_white);
if joined == true
{
message = "player joined";
draw_text(16, 16, message);
joined = false;
}
What is going on? What am I doing wrong? I thought I comprehended what I was doing, but apparently there's something wrong that creates this error every time the client disconnects, and I'm not getting any of my text messages displayed at all! And for some reason my player object is not being spawned in either.