TCP mesh almost working.
This commit is contained in:
parent
80d2cf654b
commit
738a9035ef
4 changed files with 125 additions and 88 deletions
|
@ -56,8 +56,10 @@ func _data_recieved(type, data):
|
|||
#***TODO**** We should really be displaying things in columns.
|
||||
var root = peers_tree.create_item()
|
||||
for peer in Peers.peerArray:
|
||||
var child = peers_tree.create_item(root)
|
||||
child.set_text(0, peer["user"] + " (" + peer["ip"] + ") " + str(peer["ping"]) + "ms")
|
||||
print(peer["online"])
|
||||
if peer["online"]:
|
||||
var child = peers_tree.create_item(root)
|
||||
child.set_text(0, peer["user"] + " (" + peer["ip"] + ")")
|
||||
# Handle empty peer list.
|
||||
if data.size() == 0 and peers_tree.get_root() != null:
|
||||
peers_tree.clear()
|
||||
|
|
24
hamncheese/Scripts/network.gd
Normal file
24
hamncheese/Scripts/network.gd
Normal file
|
@ -0,0 +1,24 @@
|
|||
extends Node
|
||||
|
||||
|
||||
func _process(_delta):
|
||||
pass
|
||||
|
||||
|
||||
func _ready():
|
||||
Peers.peer_received_packet.connect(_received_packet)
|
||||
|
||||
|
||||
func _received_packet(peer, verb, payload):
|
||||
match verb:
|
||||
"online":
|
||||
if peer["online"] != payload["status"]:
|
||||
peer["online"] = payload["status"]
|
||||
peer["refresh"] = true
|
||||
|
||||
_:
|
||||
print("UNKNOWN PACKET")
|
||||
print(peer)
|
||||
print(verb)
|
||||
print(payload)
|
||||
print()
|
|
@ -1,17 +1,15 @@
|
|||
extends Node
|
||||
|
||||
|
||||
const ENET_SERVICE_EVENT_TYPE = 0
|
||||
const ENET_SERVICE_PEER = 1
|
||||
const ENET_SERVICE_EVENT_DATA = 2
|
||||
const ENET_SERVICE_EVENT_CHANNEL = 3
|
||||
signal peer_received_packet(peer, verb, payload)
|
||||
|
||||
|
||||
var _basePort: int
|
||||
var _tcp := TCPServer.new()
|
||||
var _basePort : int
|
||||
var _serverRunning: bool
|
||||
var _timer : Timer
|
||||
|
||||
# This array is of dictionary elements that contain:
|
||||
# "enet": ENet listening connnection.
|
||||
# "id": Unique ID of this peer (1-254) based on IP.
|
||||
# "ip": IP address of this peer.
|
||||
# "port": Listen port of this peer.
|
||||
|
@ -20,10 +18,10 @@ var _serverRunning: bool
|
|||
var _userInfo: Dictionary
|
||||
|
||||
# This array is of dictionary elements that contain:
|
||||
# "enet": ENet connection to this host.
|
||||
# "tcp": TCP connection to this peer.
|
||||
# "id": Unique ID of this peer (1-254) based on IP.
|
||||
# "ip": IP address of this peer.
|
||||
# "online": Will be true except when used to update the array.
|
||||
# "online": Will be true when TCP network can talk to the peer.
|
||||
# "port": Listen port of this peer.
|
||||
# "user": User name on this IP.
|
||||
# "uuid": UUID for this peer.
|
||||
|
@ -44,50 +42,30 @@ var _userInfo: Dictionary
|
|||
var peerArray: Array
|
||||
|
||||
|
||||
func _on_timer_timeout():
|
||||
if _serverRunning:
|
||||
# Tell everyone we're alive.
|
||||
for peer in peerArray:
|
||||
if peer["tcp"] != null:
|
||||
peer["tcp"].poll()
|
||||
if peer["tcp"].get_status() == StreamPeerTCP.STATUS_CONNECTED:
|
||||
send_to_peer(peer, "online", { "status": true })
|
||||
|
||||
|
||||
func _process(_delta):
|
||||
if _serverRunning:
|
||||
# Handle current connections.
|
||||
_process_enet(_userInfo["enet"], _userInfo["id"])
|
||||
# Manage peer connections.
|
||||
for peer in peerArray:
|
||||
# Do we need new connections? It looks funny that we check for both connected and
|
||||
# disconnected but there are other states the peer could be in.
|
||||
if !is_peer_valid(peer):
|
||||
print("Connecting to ", peer["ip"], ":", peer["port"])
|
||||
peer["enet"] = _userInfo["enet"].connect_to_host(peer["ip"], peer["port"], 0)
|
||||
else:
|
||||
# Do we need to remove this one?
|
||||
if is_peer_disconnected(peer):
|
||||
peer["enet"] = null
|
||||
|
||||
|
||||
func _process_enet(host: ENetConnection, id: int):
|
||||
if host == null:
|
||||
return
|
||||
var ret = host.service() # Returns an array of ENET_SERVICE_* items.
|
||||
match ret[ENET_SERVICE_EVENT_TYPE]:
|
||||
host.EVENT_CONNECT:
|
||||
print("Peer connected ", id, " (", host.get_peers().size(), " known peers)")
|
||||
#var enet_peers = host.get_peers()
|
||||
#for enet_peer in enet_peers:
|
||||
|
||||
host.EVENT_DISCONNECT:
|
||||
print("Peer disconnected ", id, " (", host.get_peers().size(), " known peers)")
|
||||
|
||||
host.EVENT_ERROR:
|
||||
print("Peer error ", id, " (", host.get_peers().size(), " known peers)")
|
||||
#***TODO*** Attempt disconnect/reconnect
|
||||
|
||||
host.EVENT_NONE:
|
||||
pass
|
||||
|
||||
host.EVENT_RECEIVE:
|
||||
print("Peer recieved data ", id, " (", host.get_peers().size(), " known peers)")
|
||||
_tcp_server()
|
||||
|
||||
|
||||
func _ready():
|
||||
_serverRunning = false
|
||||
clear()
|
||||
_timer = Timer.new()
|
||||
_timer.wait_time = 1
|
||||
_timer.one_shot = false
|
||||
_timer.timeout.connect(_on_timer_timeout)
|
||||
Engine.get_main_loop().current_scene.add_child(_timer)
|
||||
_timer.start()
|
||||
|
||||
|
||||
func _sort_by_ip(a, b):
|
||||
|
@ -97,35 +75,70 @@ func _sort_by_ip(a, b):
|
|||
return false
|
||||
|
||||
|
||||
func _tcp_server():
|
||||
if _tcp.is_listening():
|
||||
# New inbound connection.
|
||||
if _tcp.is_connection_available():
|
||||
var new_peer: StreamPeerTCP = _tcp.take_connection()
|
||||
# Do we have a connection for this peer already?
|
||||
for peer in peerArray:
|
||||
if peer["ip"] == new_peer.get_connected_host():
|
||||
if peer["tcp"] == null:
|
||||
# No - add it!
|
||||
peer["tcp"] = new_peer
|
||||
print("New peer ", peer["ip"], ":", peer["port"])
|
||||
else:
|
||||
# Yes. Close existing, use this one.
|
||||
peer["tcp"].disconnect_from_host()
|
||||
peer["tcp"] = new_peer
|
||||
print("Updated peer ", peer["ip"], ":", peer["port"])
|
||||
peer["tcp"].set_no_delay(true)
|
||||
|
||||
# Process incoming data and attempt connections.
|
||||
for peer in peerArray:
|
||||
if peer["tcp"] == null:
|
||||
# Try to connect.
|
||||
print("Connecting to ", peer["ip"], ":", peer["port"])
|
||||
peer["tcp"] = StreamPeerTCP.new()
|
||||
var error = peer["tcp"].connect_to_host(peer["ip"], peer["port"])
|
||||
if error == OK:
|
||||
peer["tcp"].set_no_delay(true)
|
||||
else:
|
||||
peer["tcp"] = null
|
||||
else:
|
||||
# Update network status.
|
||||
peer["tcp"].poll()
|
||||
# Still connected?
|
||||
if peer["tcp"].get_status() == StreamPeerTCP.STATUS_ERROR:
|
||||
peer["tcp"].disconnect_from_host()
|
||||
peer["tcp"] = null
|
||||
print("Lost peer ", peer["ip"], ":", peer["port"])
|
||||
else:
|
||||
# Data waiting?
|
||||
if peer["tcp"].get_status() == StreamPeerTCP.STATUS_CONNECTED:
|
||||
if peer["tcp"].get_available_bytes() > 0:
|
||||
var data = peer["tcp"].get_var()
|
||||
peer_received_packet.emit(peer, data["verb"], data["payload"])
|
||||
|
||||
|
||||
func clear():
|
||||
peerArray.clear()
|
||||
|
||||
|
||||
func is_peer_connected(peer):
|
||||
if is_peer_valid(peer):
|
||||
if peer["enet"].get_state() == ENetPacketPeer.STATE_CONNECTED:
|
||||
return true
|
||||
return false
|
||||
|
||||
|
||||
func is_peer_disconnected(peer):
|
||||
if is_peer_valid(peer):
|
||||
if peer["enet"].get_state() == ENetPacketPeer.STATE_DISCONNECTED:
|
||||
return true
|
||||
return false
|
||||
|
||||
|
||||
func is_peer_valid(peer):
|
||||
if typeof(peer["enet"]) == TYPE_OBJECT:
|
||||
if peer["enet"] != null:
|
||||
return true
|
||||
return false
|
||||
|
||||
|
||||
func is_running():
|
||||
return _serverRunning
|
||||
|
||||
|
||||
func send_to_peer(peer, verb: String, payload: Dictionary):
|
||||
if peer["tcp"] != null:
|
||||
if peer["tcp"].get_status() == StreamPeerTCP.STATUS_CONNECTED:
|
||||
var message = {}
|
||||
message["verb"] = verb
|
||||
message["payload"] = payload
|
||||
peer["tcp"].put_var(message)
|
||||
peer["tcp"].poll()
|
||||
|
||||
|
||||
func start_server(address, portStart, user, uuid):
|
||||
if !_serverRunning:
|
||||
clear()
|
||||
|
@ -136,8 +149,7 @@ func start_server(address, portStart, user, uuid):
|
|||
_userInfo["id"] = _userInfo["ip"].get_slice(".", 3).to_int() # Use last octet for our ID.
|
||||
_userInfo["port"] = _basePort + _userInfo["id"]
|
||||
# Set up our listening port.
|
||||
_userInfo["enet"] = ENetConnection.new()
|
||||
_userInfo["enet"].create_host_bound(_userInfo["ip"], _userInfo["port"], 256, 0)
|
||||
_tcp.listen(_userInfo["port"], _userInfo["ip"])
|
||||
_serverRunning = true
|
||||
|
||||
|
||||
|
@ -145,8 +157,13 @@ func stop_server():
|
|||
if _serverRunning:
|
||||
# Tear down network.
|
||||
_serverRunning = false
|
||||
_userInfo["enet"].flush()
|
||||
_userInfo["enet"].destroy()
|
||||
for peer in peerArray:
|
||||
if peer["tcp"] != null:
|
||||
send_to_peer(peer, "online", { "status": false })
|
||||
peer["tcp"].disconnect_from_host()
|
||||
peer["tcp"] = null
|
||||
print("Disconnected peer ", peer["ip"], ":", peer["port"])
|
||||
_tcp.stop()
|
||||
|
||||
|
||||
func update(peersFromCPP: Array):
|
||||
|
@ -178,34 +195,27 @@ func update(peersFromCPP: Array):
|
|||
if oldPeer["ip"] == peerCPP["ip"]:
|
||||
found = true
|
||||
peerCPP = oldPeer
|
||||
# Update peer statistics. ***TODO*** These do not set 'changed' and are not refreshed.
|
||||
if is_peer_connected(peerCPP):
|
||||
peerCPP["ping"] = peerCPP["enet"].get_statistic(ENetPacketPeer.PEER_ROUND_TRIP_TIME)
|
||||
if !found:
|
||||
# We didn't have them. Add needed records.
|
||||
peerCPP["user"] = ""
|
||||
peerCPP["uuid"] = ""
|
||||
peerCPP["online"] = true
|
||||
peerCPP["online"] = false
|
||||
peerCPP["refresh"] = false
|
||||
peerCPP["ping"] = 0.0
|
||||
changed = true
|
||||
# Also create the ENet connection data.
|
||||
# Also create the TCP connection data.
|
||||
peerCPP["id"] = peerCPP["ip"].get_slice(".", 3).to_int() # Use last octet for our ID.
|
||||
peerCPP["port"] = _basePort + peerCPP["ip"].get_slice(".", 3).to_int()
|
||||
peerCPP["enet"] = null
|
||||
# Sometimes the CPP code will return duplicates. Check.
|
||||
# Also check if we need to redraw anyone.
|
||||
found = false
|
||||
for peer in peerArray:
|
||||
if peer["ip"] == peerCPP["ip"]:
|
||||
found = true
|
||||
if peer["refresh"] == true:
|
||||
peer["refresh"] = false
|
||||
changed = true
|
||||
peerCPP["tcp"] = null
|
||||
|
||||
# Add them to the new list.
|
||||
peerArray.append(peerCPP)
|
||||
|
||||
# Check if we need to redraw anyone.
|
||||
for peer in peerArray:
|
||||
if peer["refresh"] == true:
|
||||
peer["refresh"] = false
|
||||
changed = true
|
||||
|
||||
# Sort new array.
|
||||
peerArray.sort_custom(_sort_by_ip)
|
||||
|
||||
|
|
|
@ -26,6 +26,7 @@ Process="*res://Scripts/process.gd"
|
|||
Dialog="*res://Scripts/dialog.gd"
|
||||
Edge="*res://Scripts/edge.gd"
|
||||
Peers="*res://Scripts/peers.gd"
|
||||
Network="*res://Scripts/network.gd"
|
||||
Settings="*res://Scenes/settings.tscn"
|
||||
About="*res://Scenes/about.tscn"
|
||||
Manual="*res://Scenes/manual.tscn"
|
||||
|
|
Loading…
Add table
Reference in a new issue