extends Node signal connexion_updated(new_state) signal update_my_position(tick, pos, rot) signal update_player_position(id, tick, pos, rot, extra, tickjump, velocity) signal remove_player(id) @export var listen_ip:String = "127.0.0.1": set = set_ip func set_ip(value): listen_ip = value disconnect_server() @export var listen_port:int = 33333: set = set_port func set_port(value:int): listen_port = value disconnect_server() @export var username:String = "": set = set_username func set_username(value): username = value disconnect_server() @export var player_position:Node3D = null : set = set_player_position func set_player_position(value:Node3D): player_position = value enum Connexion{ NONE, ACCOUNT_REFUSED, CONNECTING, CONNECTED, } @export var state_connexion:Connexion = Connexion.NONE @export var id:int = 0: get: return id set(value): id = value var enet:ENetConnection var dataEnet:ENetPacketPeer var errorEnet:Error func get_id() -> int: return id func is_offline() -> bool: return state_connexion != Connexion.CONNECTED func update_state(value): state_connexion = value connexion_updated.emit(state_connexion) func disconnect_server(): update_state(Connexion.NONE) func create_server_enet(): print("------ create_server_enet") enet = ENetConnection.new() errorEnet = enet.create_host(10) if errorEnet != OK: print("ERROR ENET.create_host: ", errorEnet) return func connect_to_host(): print("Connect to : " + listen_ip + " : " + str(listen_port)) dataEnet = enet.connect_to_host(listen_ip, listen_port, 10) print(dataEnet) if not dataEnet: print("ERROR dataEnet == null: ") return elif not dataEnet.is_active(): print("ERROR enet.connect_to_host: ", dataEnet.is_active()) return update_state(Connexion.CONNECTING) func connect_server(): if username == "": return if player_position == null: return create_server_enet() connect_to_host() func _ready(): print("------ Multi initialized") update_state(Connexion.NONE) func bad_account(): set_username("") update_state(Connexion.ACCOUNT_REFUSED) func get_event_received(): var data:PackedFlowPull = PackedFlowPull.new(dataEnet) var command = data.get_u8() #var data = dataEnet.get_packet() #print("get: ", data) if command == 1: # Return connexion var state = data.get_u8() if state == 0: # OK id = data.get_u64() var x:float = data.get_f64() var y:float = data.get_f64() var z:float = data.get_f64() var rx:float = data.get_f64() var ry:float = data.get_f64() var rz:float = data.get_f64() var tick:int = data.get_u8() #for i in range(56,74): # var tick1:int = data.decode_u8(2+i) # print("tick ", i, " :", tick1) Global.msg_info("ME - id:%d tick:%d x:%d y:%d z:%d", [id, tick, x, y, z]) update_my_position.emit(tick, Vector3(x, y, z), Vector3(rx, ry, rz)) #self.set_player_position(Vector3(x, y, z)) update_state(Connexion.CONNECTED) else: # KO bad_account() elif command == 3: # Get position if id == 0: return var nb:int = data.get_u8() for i in nb: var mid:int = data.get_u64() var mx:float = data.get_f64() var my:float = data.get_f64() var mz:float = data.get_f64() var rx:float = data.get_f64() var ry:float = data.get_f64() var rz:float = data.get_f64() var tick:int = data.get_u8() var extra:int = data.get_u8() var vx:float var vy:float var vz:float var tickjump:int var jump:bool = (extra & 1) == 1 if jump: tickjump = data.get_u8() vx = data.get_f64() vy = data.get_f64() vz = data.get_f64() #for ii in range(56,74): # var tick1:int = data.decode_u8(pos+ii) # print("tick ", ii, " :", tick1) if mid == id: #print("Me id:", mid, " x:", mx, " y:", my, " z:", mz) continue Global.msg_info("OTHER - id:%d tick:%d mx:%d my:%d mz:%d rx:%d ry:%d rz:%d tickjump:%d vx:%d vy:%d vz:%d", [mid, tick, mx, my ,mz ,rx, ry ,rz, tickjump, vx, vy ,vz]) #print(" id:", mid, " tick:", tick, " x:", mx, " y:", my, " z:", mz, " rx:", rx, " ry:", ry, " rz:", rz, " tickjump:", tickjump, " vx:", vx, " vy:", vy, " vz:", vz) update_player_position.emit(mid, tick, Vector3(mx, my, mz), Vector3(rx, ry, rz), extra, tickjump, Vector3(vx, vy, vz)) var nbuserremove:int = data.get_u8() for i in nbuserremove: var mid = data.get_u64() if mid == id: Global.msg_info("Try to remove me : %d", [mid]) continue remove_player.emit(mid) func send_account(): var data:PackedByteArray = PackedByteArray() data.append(1) data.append(len(username)) var packed_array = username.to_ascii_buffer() data += packed_array Global.msg_debug("%s -> size:%s / %d ", [ username, data.size(), len(username)] ) errorEnet = dataEnet.send(1, data, 1) if errorEnet != OK: print("ERROR ENET: ", errorEnet) return func get_player_position(): if state_connexion != Connexion.CONNECTED: return var data:PackedFlowPush = PackedFlowPush.new() var posRaw:Vector3 = player_position.get_my_position() #get_position() var rotRaw:Vector3 = player_position.get_my_rotation() data.put_vector3(posRaw) data.put_vector3(rotRaw) if player_position.is_jump(): Global.msg_debug("Jump Jump", []) data.put_u8(1) data.put_u8(player_position.get_tickjump()) data.put_vector3(player_position.get_jump()) else: data.put_u8(0) errorEnet = data.push(dataEnet, 2, 1) if errorEnet == ERR_UNCONFIGURED: update_state(Connexion.NONE) elif errorEnet != OK: Global.msg_error("ERROR ENET: %s", [str(errorEnet)]) return func _process(_delta): if state_connexion == Connexion.ACCOUNT_REFUSED: return elif state_connexion == Connexion.NONE: connect_server() return get_player_position() if state_connexion == Connexion.CONNECTING: send_account() if dataEnet.get_state() == ENetPacketPeer.STATE_CONNECTED: var event = enet.service() if event[0] == ENetConnection.EVENT_RECEIVE: get_event_received() elif dataEnet.get_state() == ENetPacketPeer.STATE_CONNECTING: var event = enet.service() if event[0] == ENetConnection.EVENT_RECEIVE: pass elif dataEnet.get_state() == ENetPacketPeer.STATE_DISCONNECTED: var _event = enet.service() print("STATE_DISCONNECTED") elif dataEnet.get_state() == ENetPacketPeer.STATE_ACKNOWLEDGING_CONNECT: var _event = enet.service() print("STATE_ACKNOWLEDGING_CONNECT") elif dataEnet.get_state() == ENetPacketPeer.STATE_CONNECTION_PENDING: var _event = enet.service() print("STATE_CONNECTION_PENDING") elif dataEnet.get_state() == ENetPacketPeer.STATE_CONNECTION_SUCCEEDED: var _event = enet.service() print("STATE_CONNECTION_SUCCEEDED") elif dataEnet.get_state() == ENetPacketPeer.STATE_DISCONNECT_LATER: var _event = enet.service() print("STATE_DISCONNECT_LATER") elif dataEnet.get_state() == ENetPacketPeer.STATE_DISCONNECTING: var _event = enet.service() print("STATE_DISCONNECTING") elif dataEnet.get_state() == ENetPacketPeer.STATE_ACKNOWLEDGING_DISCONNECT: var _event = enet.service() print("STATE_ACKNOWLEDGING_DISCONNECT") elif dataEnet.get_state() == ENetPacketPeer.STATE_ZOMBIE: var _event = enet.service() print("STATE_ZOMBIE") else: var _event = enet.service() print("STATE_UNKNOWN")