Merge pull request #18823 from Faless/multiplayer_raw
Allow sending raw bytes via the Multiplayer API
This commit is contained in:
commit
ca10cb6eea
5 changed files with 72 additions and 11 deletions
|
@ -76,7 +76,7 @@ Ref<NetworkedMultiplayerPeer> MultiplayerAPI::get_network_peer() const {
|
||||||
void MultiplayerAPI::_process_packet(int p_from, const uint8_t *p_packet, int p_packet_len) {
|
void MultiplayerAPI::_process_packet(int p_from, const uint8_t *p_packet, int p_packet_len) {
|
||||||
|
|
||||||
ERR_FAIL_COND(root_node == NULL);
|
ERR_FAIL_COND(root_node == NULL);
|
||||||
ERR_FAIL_COND(p_packet_len < 5);
|
ERR_FAIL_COND(p_packet_len < 1);
|
||||||
|
|
||||||
uint8_t packet_type = p_packet[0];
|
uint8_t packet_type = p_packet[0];
|
||||||
|
|
||||||
|
@ -123,6 +123,11 @@ void MultiplayerAPI::_process_packet(int p_from, const uint8_t *p_packet, int p_
|
||||||
}
|
}
|
||||||
|
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
|
case NETWORK_COMMAND_RAW: {
|
||||||
|
|
||||||
|
_process_raw(p_from, p_packet, p_packet_len);
|
||||||
|
} break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -259,6 +264,8 @@ void MultiplayerAPI::_process_simplify_path(int p_from, const uint8_t *p_packet,
|
||||||
|
|
||||||
void MultiplayerAPI::_process_confirm_path(int p_from, const uint8_t *p_packet, int p_packet_len) {
|
void MultiplayerAPI::_process_confirm_path(int p_from, const uint8_t *p_packet, int p_packet_len) {
|
||||||
|
|
||||||
|
ERR_FAIL_COND(p_packet_len < 2);
|
||||||
|
|
||||||
String paths;
|
String paths;
|
||||||
paths.parse_utf8((const char *)&p_packet[1], p_packet_len - 1);
|
paths.parse_utf8((const char *)&p_packet[1], p_packet_len - 1);
|
||||||
|
|
||||||
|
@ -648,6 +655,34 @@ void MultiplayerAPI::rsetp(Node *p_node, int p_peer_id, bool p_unreliable, const
|
||||||
_send_rpc(p_node, p_peer_id, p_unreliable, true, p_property, &vptr, 1);
|
_send_rpc(p_node, p_peer_id, p_unreliable, true, p_property, &vptr, 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Error MultiplayerAPI::send_bytes(PoolVector<uint8_t> p_data, int p_to) {
|
||||||
|
|
||||||
|
ERR_FAIL_COND_V(p_data.size() < 1, ERR_INVALID_DATA);
|
||||||
|
ERR_FAIL_COND_V(!network_peer.is_valid(), ERR_UNCONFIGURED);
|
||||||
|
ERR_FAIL_COND_V(network_peer->get_connection_status() != NetworkedMultiplayerPeer::CONNECTION_CONNECTED, ERR_UNCONFIGURED);
|
||||||
|
|
||||||
|
MAKE_ROOM(p_data.size() + 1);
|
||||||
|
PoolVector<uint8_t>::Read r = p_data.read();
|
||||||
|
packet_cache[0] = NETWORK_COMMAND_RAW;
|
||||||
|
memcpy(&packet_cache[1], &r[0], p_data.size());
|
||||||
|
network_peer->set_target_peer(p_to);
|
||||||
|
return network_peer->put_packet(packet_cache.ptr(), p_data.size() + 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
void MultiplayerAPI::_process_raw(int p_from, const uint8_t *p_packet, int p_packet_len) {
|
||||||
|
|
||||||
|
ERR_FAIL_COND(p_packet_len < 2);
|
||||||
|
|
||||||
|
PoolVector<uint8_t> out;
|
||||||
|
int len = p_packet_len - 1;
|
||||||
|
out.resize(len);
|
||||||
|
{
|
||||||
|
PoolVector<uint8_t>::Write w = out.write();
|
||||||
|
memcpy(&w[0], &p_packet[1], len);
|
||||||
|
}
|
||||||
|
emit_signal("network_peer_packet", p_from, out);
|
||||||
|
}
|
||||||
|
|
||||||
int MultiplayerAPI::get_network_unique_id() const {
|
int MultiplayerAPI::get_network_unique_id() const {
|
||||||
|
|
||||||
ERR_FAIL_COND_V(!network_peer.is_valid(), 0);
|
ERR_FAIL_COND_V(!network_peer.is_valid(), 0);
|
||||||
|
@ -686,6 +721,7 @@ Vector<int> MultiplayerAPI::get_network_connected_peers() const {
|
||||||
|
|
||||||
void MultiplayerAPI::_bind_methods() {
|
void MultiplayerAPI::_bind_methods() {
|
||||||
ClassDB::bind_method(D_METHOD("set_root_node", "node"), &MultiplayerAPI::set_root_node);
|
ClassDB::bind_method(D_METHOD("set_root_node", "node"), &MultiplayerAPI::set_root_node);
|
||||||
|
ClassDB::bind_method(D_METHOD("send_bytes", "bytes", "id"), &MultiplayerAPI::send_bytes, DEFVAL(NetworkedMultiplayerPeer::TARGET_PEER_BROADCAST));
|
||||||
ClassDB::bind_method(D_METHOD("has_network_peer"), &MultiplayerAPI::has_network_peer);
|
ClassDB::bind_method(D_METHOD("has_network_peer"), &MultiplayerAPI::has_network_peer);
|
||||||
ClassDB::bind_method(D_METHOD("get_network_peer"), &MultiplayerAPI::get_network_peer);
|
ClassDB::bind_method(D_METHOD("get_network_peer"), &MultiplayerAPI::get_network_peer);
|
||||||
ClassDB::bind_method(D_METHOD("get_network_unique_id"), &MultiplayerAPI::get_network_unique_id);
|
ClassDB::bind_method(D_METHOD("get_network_unique_id"), &MultiplayerAPI::get_network_unique_id);
|
||||||
|
@ -708,6 +744,7 @@ void MultiplayerAPI::_bind_methods() {
|
||||||
|
|
||||||
ADD_SIGNAL(MethodInfo("network_peer_connected", PropertyInfo(Variant::INT, "id")));
|
ADD_SIGNAL(MethodInfo("network_peer_connected", PropertyInfo(Variant::INT, "id")));
|
||||||
ADD_SIGNAL(MethodInfo("network_peer_disconnected", PropertyInfo(Variant::INT, "id")));
|
ADD_SIGNAL(MethodInfo("network_peer_disconnected", PropertyInfo(Variant::INT, "id")));
|
||||||
|
ADD_SIGNAL(MethodInfo("network_peer_packet", PropertyInfo(Variant::INT, "id"), PropertyInfo(Variant::POOL_BYTE_ARRAY, "packet")));
|
||||||
ADD_SIGNAL(MethodInfo("connected_to_server"));
|
ADD_SIGNAL(MethodInfo("connected_to_server"));
|
||||||
ADD_SIGNAL(MethodInfo("connection_failed"));
|
ADD_SIGNAL(MethodInfo("connection_failed"));
|
||||||
ADD_SIGNAL(MethodInfo("server_disconnected"));
|
ADD_SIGNAL(MethodInfo("server_disconnected"));
|
||||||
|
|
|
@ -43,6 +43,7 @@ protected:
|
||||||
Node *_process_get_node(int p_from, const uint8_t *p_packet, int p_packet_len);
|
Node *_process_get_node(int p_from, const uint8_t *p_packet, int p_packet_len);
|
||||||
void _process_rpc(Node *p_node, const StringName &p_name, int p_from, const uint8_t *p_packet, int p_packet_len, int p_offset);
|
void _process_rpc(Node *p_node, const StringName &p_name, int p_from, const uint8_t *p_packet, int p_packet_len, int p_offset);
|
||||||
void _process_rset(Node *p_node, const StringName &p_name, int p_from, const uint8_t *p_packet, int p_packet_len, int p_offset);
|
void _process_rset(Node *p_node, const StringName &p_name, int p_from, const uint8_t *p_packet, int p_packet_len, int p_offset);
|
||||||
|
void _process_raw(int p_from, const uint8_t *p_packet, int p_packet_len);
|
||||||
|
|
||||||
void _send_rpc(Node *p_from, int p_to, bool p_unreliable, bool p_set, const StringName &p_name, const Variant **p_arg, int p_argcount);
|
void _send_rpc(Node *p_from, int p_to, bool p_unreliable, bool p_set, const StringName &p_name, const Variant **p_arg, int p_argcount);
|
||||||
bool _send_confirm_path(NodePath p_path, PathSentCache *psc, int p_from);
|
bool _send_confirm_path(NodePath p_path, PathSentCache *psc, int p_from);
|
||||||
|
@ -53,6 +54,7 @@ public:
|
||||||
NETWORK_COMMAND_REMOTE_SET,
|
NETWORK_COMMAND_REMOTE_SET,
|
||||||
NETWORK_COMMAND_SIMPLIFY_PATH,
|
NETWORK_COMMAND_SIMPLIFY_PATH,
|
||||||
NETWORK_COMMAND_CONFIRM_PATH,
|
NETWORK_COMMAND_CONFIRM_PATH,
|
||||||
|
NETWORK_COMMAND_RAW,
|
||||||
};
|
};
|
||||||
|
|
||||||
void poll();
|
void poll();
|
||||||
|
@ -60,6 +62,7 @@ public:
|
||||||
void set_root_node(Node *p_node);
|
void set_root_node(Node *p_node);
|
||||||
void set_network_peer(const Ref<NetworkedMultiplayerPeer> &p_peer);
|
void set_network_peer(const Ref<NetworkedMultiplayerPeer> &p_peer);
|
||||||
Ref<NetworkedMultiplayerPeer> get_network_peer() const;
|
Ref<NetworkedMultiplayerPeer> get_network_peer() const;
|
||||||
|
Error send_bytes(PoolVector<uint8_t> p_data, int p_to = NetworkedMultiplayerPeer::TARGET_PEER_BROADCAST);
|
||||||
|
|
||||||
// Called by Node.rpc
|
// Called by Node.rpc
|
||||||
void rpcp(Node *p_node, int p_peer_id, bool p_unreliable, const StringName &p_method, const Variant **p_arg, int p_argcount);
|
void rpcp(Node *p_node, int p_peer_id, bool p_unreliable, const StringName &p_method, const Variant **p_arg, int p_argcount);
|
||||||
|
|
|
@ -61,10 +61,21 @@
|
||||||
</return>
|
</return>
|
||||||
<description>
|
<description>
|
||||||
Method used for polling the MultiplayerAPI.
|
Method used for polling the MultiplayerAPI.
|
||||||
You only need to worry about this if you are using [memeber Node.custom_multplayer] override.
|
You only need to worry about this if you are using [member Node.custom_multplayer] override.
|
||||||
SceneTree will poll the default MultiplayerAPI for you.
|
SceneTree will poll the default MultiplayerAPI for you.
|
||||||
</description>
|
</description>
|
||||||
</method>
|
</method>
|
||||||
|
<method name="send_bytes">
|
||||||
|
<return type="int" enum="Error">
|
||||||
|
</return>
|
||||||
|
<argument index="0" name="bytes" type="PoolByteArray">
|
||||||
|
</argument>
|
||||||
|
<argument index="1" name="id" type="int" default="0">
|
||||||
|
</argument>
|
||||||
|
<description>
|
||||||
|
Sends the given raw [code]bytes[/code] to a specific peer identified by [code]id[/code] (see [method NetworkedMultiplayerPeer.set_target_peer]). Default ID is [code]0[/code], i.e. broadcast to all peers.
|
||||||
|
</description>
|
||||||
|
</method>
|
||||||
<method name="set_root_node">
|
<method name="set_root_node">
|
||||||
<return type="void">
|
<return type="void">
|
||||||
</return>
|
</return>
|
||||||
|
@ -78,7 +89,7 @@
|
||||||
</methods>
|
</methods>
|
||||||
<members>
|
<members>
|
||||||
<member name="network_peer" type="NetworkedMultiplayerPeer" setter="set_network_peer" getter="get_network_peer">
|
<member name="network_peer" type="NetworkedMultiplayerPeer" setter="set_network_peer" getter="get_network_peer">
|
||||||
The peer object to handle the RPC system (effectively enabling networking when set). Depending on the peer itself, the MultiplayerAPI will become a network server (check with [method is_network_server()]) and will set root node's network mode to master (see NETWORK_MODE_* constants in [Node]), or it will become a regular peer with root node set to slave. All child nodes are set to inherit the network mode by default. Handling of networking-related events (connection, disconnection, new clients) is done by connecting to MultiplayerAPI's signals.
|
The peer object to handle the RPC system (effectively enabling networking when set). Depending on the peer itself, the MultiplayerAPI will become a network server (check with [method is_network_server]) and will set root node's network mode to master (see NETWORK_MODE_* constants in [Node]), or it will become a regular peer with root node set to slave. All child nodes are set to inherit the network mode by default. Handling of networking-related events (connection, disconnection, new clients) is done by connecting to MultiplayerAPI's signals.
|
||||||
</member>
|
</member>
|
||||||
<member name="refuse_new_network_connections" type="bool" setter="set_refuse_new_network_connections" getter="is_refusing_new_network_connections">
|
<member name="refuse_new_network_connections" type="bool" setter="set_refuse_new_network_connections" getter="is_refusing_new_network_connections">
|
||||||
If [code]true[/code] the MultiplayerAPI's [member network_peer] refuses new incoming connections.
|
If [code]true[/code] the MultiplayerAPI's [member network_peer] refuses new incoming connections.
|
||||||
|
@ -109,9 +120,18 @@
|
||||||
Emitted whenever this MultiplayerAPI's [member network_peer] disconnects from a peer. Clients get notified when other clients disconnect from the same server.
|
Emitted whenever this MultiplayerAPI's [member network_peer] disconnects from a peer. Clients get notified when other clients disconnect from the same server.
|
||||||
</description>
|
</description>
|
||||||
</signal>
|
</signal>
|
||||||
|
<signal name="network_peer_packet">
|
||||||
|
<argument index="0" name="id" type="int">
|
||||||
|
</argument>
|
||||||
|
<argument index="1" name="packet" type="PoolByteArray">
|
||||||
|
</argument>
|
||||||
|
<description>
|
||||||
|
Emitted whenever this MultiplayerAPI's [member network_peer] receive a [code]packet[/code] with custom data (see [method send_bytes]). ID is the peer ID of the peer that sent the packet.
|
||||||
|
</description>
|
||||||
|
</signal>
|
||||||
<signal name="server_disconnected">
|
<signal name="server_disconnected">
|
||||||
<description>
|
<description>
|
||||||
Emitted whenever this MultiplayerAPI's [member network_peer] disconnected from server. Only emitted on clients.
|
Emitted whenever this MultiplayerAPI's [member network_peer] disconnects from server. Only emitted on clients.
|
||||||
</description>
|
</description>
|
||||||
</signal>
|
</signal>
|
||||||
</signals>
|
</signals>
|
||||||
|
|
|
@ -46,7 +46,8 @@
|
||||||
<argument index="0" name="id" type="int">
|
<argument index="0" name="id" type="int">
|
||||||
</argument>
|
</argument>
|
||||||
<description>
|
<description>
|
||||||
The peer to which packets will be sent. Default value: [code]0[/code].
|
Sets the peer to which packets will be sent.
|
||||||
|
The [code]id[/code] can be one of: [code]TARGET_PEER_BROADCAST[/code] to send to all connected peers, [code]TARGET_PEER_SERVER[/code] to send to the peer acting as server, a valid peer ID to send to that specific peer, a negative peer ID to send to all peers except that one. Default: [code]TARGET_PEER_BROADCAST[/code]
|
||||||
</description>
|
</description>
|
||||||
</method>
|
</method>
|
||||||
</methods>
|
</methods>
|
||||||
|
|
|
@ -586,7 +586,7 @@
|
||||||
<argument index="1" name="method" type="String">
|
<argument index="1" name="method" type="String">
|
||||||
</argument>
|
</argument>
|
||||||
<description>
|
<description>
|
||||||
Sends a [method rpc] to a specific peer identified by [code]peer_id[/code]. Returns an empty [Variant].
|
Sends a [method rpc] to a specific peer identified by [code]peer_id[/code] (see [method NetworkedMultiplayerPeer.set_target_peer]). Returns an empty [Variant].
|
||||||
</description>
|
</description>
|
||||||
</method>
|
</method>
|
||||||
<method name="rpc_unreliable" qualifiers="vararg">
|
<method name="rpc_unreliable" qualifiers="vararg">
|
||||||
|
@ -606,7 +606,7 @@
|
||||||
<argument index="1" name="method" type="String">
|
<argument index="1" name="method" type="String">
|
||||||
</argument>
|
</argument>
|
||||||
<description>
|
<description>
|
||||||
Sends a [method rpc] to a specific peer identified by [code]peer_id[/code] using an unreliable protocol. Returns an empty [Variant].
|
Sends a [method rpc] to a specific peer identified by [code]peer_id[/code] using an unreliable protocol (see [method NetworkedMultiplayerPeer.set_target_peer]). Returns an empty [Variant].
|
||||||
</description>
|
</description>
|
||||||
</method>
|
</method>
|
||||||
<method name="rset">
|
<method name="rset">
|
||||||
|
@ -641,7 +641,7 @@
|
||||||
<argument index="2" name="value" type="Variant">
|
<argument index="2" name="value" type="Variant">
|
||||||
</argument>
|
</argument>
|
||||||
<description>
|
<description>
|
||||||
Remotely changes the property's value on a specific peer identified by [code]peer_id[/code].
|
Remotely changes the property's value on a specific peer identified by [code]peer_id[/code] (see [method NetworkedMultiplayerPeer.set_target_peer]).
|
||||||
</description>
|
</description>
|
||||||
</method>
|
</method>
|
||||||
<method name="rset_unreliable">
|
<method name="rset_unreliable">
|
||||||
|
@ -665,7 +665,7 @@
|
||||||
<argument index="2" name="value" type="Variant">
|
<argument index="2" name="value" type="Variant">
|
||||||
</argument>
|
</argument>
|
||||||
<description>
|
<description>
|
||||||
Remotely changes property's value on a specific peer identified by [code]peer_id[/code] using an unreliable protocol.
|
Remotely changes property's value on a specific peer identified by [code]peer_id[/code] using an unreliable protocol (see [method NetworkedMultiplayerPeer.set_target_peer]).
|
||||||
</description>
|
</description>
|
||||||
</method>
|
</method>
|
||||||
<method name="set_display_folded">
|
<method name="set_display_folded">
|
||||||
|
@ -703,7 +703,7 @@
|
||||||
<argument index="0" name="enable" type="bool">
|
<argument index="0" name="enable" type="bool">
|
||||||
</argument>
|
</argument>
|
||||||
<description>
|
<description>
|
||||||
Enables or disables internal physics for this node. Internal physics processing happens in isolation from the normal [method]_physics_process[/code] calls and is used by some nodes internally to guarantee proper functioning even if the node is paused or physics processing is disabled for scripting ([method set_physics_process]). Only useful for advanced uses to manipulate built-in nodes behaviour.
|
Enables or disables internal physics for this node. Internal physics processing happens in isolation from the normal [method _physics_process] calls and is used by some nodes internally to guarantee proper functioning even if the node is paused or physics processing is disabled for scripting ([method set_physics_process]). Only useful for advanced uses to manipulate built-in nodes behaviour.
|
||||||
</description>
|
</description>
|
||||||
</method>
|
</method>
|
||||||
<method name="set_process">
|
<method name="set_process">
|
||||||
|
@ -730,7 +730,7 @@
|
||||||
<argument index="0" name="enable" type="bool">
|
<argument index="0" name="enable" type="bool">
|
||||||
</argument>
|
</argument>
|
||||||
<description>
|
<description>
|
||||||
Enables or disabled internal processing for this node. Internal processing happens in isolation from the normal [method]_process[/code] calls and is used by some nodes internally to guarantee proper functioning even if the node is paused or processing is disabled for scripting ([method set_process]). Only useful for advanced uses to manipulate built-in nodes behaviour.
|
Enables or disabled internal processing for this node. Internal processing happens in isolation from the normal [method _process] calls and is used by some nodes internally to guarantee proper functioning even if the node is paused or processing is disabled for scripting ([method set_process]). Only useful for advanced uses to manipulate built-in nodes behaviour.
|
||||||
</description>
|
</description>
|
||||||
</method>
|
</method>
|
||||||
<method name="set_process_unhandled_input">
|
<method name="set_process_unhandled_input">
|
||||||
|
|
Loading…
Reference in a new issue