Added ReadyForEntityUpdates message allowing the server to send entity updates

main
pereslav 5 years ago
parent 34f4ba7821
commit 008c653524

@ -92,6 +92,10 @@ namespace Multiplayer
//! @return the stats object bound to this multiplayer instance
MultiplayerStats& GetStats() { return m_stats; }
//! Sends a packet telling if entity update messages can be sent
//! @param readyForEntityUpdates Ready for entity updates or not
virtual void SendReadyForEntityUpdates(bool readyForEntityUpdates) = 0;
private:
MultiplayerStats m_stats;
};

@ -14,6 +14,10 @@
<Member Type="Multiplayer::HostId" Name="hostId" Init="Multiplayer::InvalidHostId" />
<Member Type="Multiplayer::LongNetworkString" Name="map" />
</Packet>
<Packet Name="ReadyForEntityUpdates" Desc="Client confirming it is ready to receive entity updates">
<Member Type="bool" Name="readyForEntityUpdates" />
</Packet>
<Packet Name="SyncConsole" Desc="Packet for synchornizing cvars between hosts">
<Member Type="Multiplayer::LongNetworkString" Name="commandSet" Container="Vector" Count="32" />

@ -36,7 +36,8 @@ namespace Multiplayer
void Update(AZ::TimeMs serverGameTimeMs) override;
//! @}
bool CanSendUpdates();
bool CanSendUpdates() const;
void SetCanSendUpdates(bool canSendUpdates);
NetworkEntityHandle GetPrimaryPlayerEntity();
const NetworkEntityHandle& GetPrimaryPlayerEntity() const;
@ -51,7 +52,7 @@ namespace Multiplayer
EntityStopEvent::Handler m_controlledEntityRemovedHandler;
EntityMigrationEvent::Handler m_controlledEntityMigrationHandler;
AzNetworking::IConnection* m_connection = nullptr;
bool m_canSendUpdates = true;
bool m_canSendUpdates = false;
};
}

@ -12,11 +12,17 @@
namespace Multiplayer
{
inline bool ServerToClientConnectionData::CanSendUpdates()
inline bool ServerToClientConnectionData::CanSendUpdates() const
{
return m_canSendUpdates;
}
inline void ServerToClientConnectionData::SetCanSendUpdates(bool canSendUpdates)
{
m_canSendUpdates = canSendUpdates;
}
inline NetworkEntityHandle ServerToClientConnectionData::GetPrimaryPlayerEntity()
{
return m_controlledEntity;

@ -381,6 +381,19 @@ namespace Multiplayer
return false;
}
bool MultiplayerSystemComponent::HandleRequest( AzNetworking::IConnection* connection,
[[maybe_unused]] const AzNetworking::IPacketHeader& packetHeader, MultiplayerPackets::ReadyForEntityUpdates& packet)
{
auto* connectionData = reinterpret_cast<ServerToClientConnectionData*>(connection->GetUserData());
if (connectionData)
{
connectionData->SetCanSendUpdates(packet.GetReadyForEntityUpdates());
return true;
}
return false;
}
ConnectResult MultiplayerSystemComponent::ValidateConnect
(
[[maybe_unused]] const IpAddress& remoteAddress,
@ -503,6 +516,15 @@ namespace Multiplayer
handler.Connect(m_shutdownEvent);
}
void MultiplayerSystemComponent::SendReadyForEntityUpdates(bool readyForEntityUpdates)
{
IConnectionSet& connectionSet = m_networkInterface->GetConnectionSet();
connectionSet.VisitConnections([readyForEntityUpdates](IConnection& connection)
{
connection.SendReliablePacket(MultiplayerPackets::ReadyForEntityUpdates(readyForEntityUpdates));
});
}
void MultiplayerSystemComponent::DumpStats([[maybe_unused]] const AZ::ConsoleCommandContainer& arguments)
{
const MultiplayerStats& stats = GetStats();

@ -71,6 +71,7 @@ namespace Multiplayer
bool HandleRequest(AzNetworking::IConnection* connection, const AzNetworking::IPacketHeader& packetHeader, MultiplayerPackets::ClientMigration& packet);
bool HandleRequest(AzNetworking::IConnection* connection, const AzNetworking::IPacketHeader& packetHeader, MultiplayerPackets::NotifyClientMigration& packet);
bool HandleRequest(AzNetworking::IConnection* connection, const AzNetworking::IPacketHeader& packetHeader, MultiplayerPackets::EntityMigration& packet);
bool HandleRequest(AzNetworking::IConnection* connection, const AzNetworking::IPacketHeader& packetHeader, MultiplayerPackets::ReadyForEntityUpdates& packet);
//! IConnectionListener interface
//! @{
@ -88,6 +89,7 @@ namespace Multiplayer
void AddConnectionAcquiredHandler(ConnectionAcquiredEvent::Handler& handler) override;
void AddSessionInitHandler(SessionInitEvent::Handler& handler) override;
void AddSessionShutdownHandler(SessionShutdownEvent::Handler& handler) override;
void SendReadyForEntityUpdates(bool readyForEntityUpdates) override;
//! @}
//! Console commands.

@ -11,19 +11,19 @@
*/
#include <Source/NetworkEntity/NetworkEntityManager.h>
#include <Source/Components/NetBindComponent.h>
#include <Include/IMultiplayer.h>
#include <AzCore/Interface/Interface.h>
#include <AzCore/Asset/AssetManager.h>
#include <AzCore/Console/IConsole.h>
#include <AzCore/Console/ILogger.h>
#include <AzCore/Interface/Interface.h>
#include <AzCore/Serialization/SerializeContext.h>
#include <AzCore/Slice/SliceMetadataInfoComponent.h>
#include <AzFramework/Components/TransformComponent.h>
#include <AzFramework/Entity/EntityContextBus.h>
#include <AzFramework/Entity/GameEntityContextBus.h>
#include <AzFramework/Components/TransformComponent.h>
#include <Include/IMultiplayer.h>
#include <Pipeline/NetworkSpawnableHolderComponent.h>
#include <AzCore/Asset/AssetManager.h>
#include <Source/Components/NetBindComponent.h>
namespace Multiplayer
{
@ -462,7 +462,9 @@ namespace Multiplayer
m_rootSpawnableAsset = netSpawnableAsset;
const auto agentType = AZ::Interface<IMultiplayer>::Get()->GetAgentType();
auto* iMultiplayer = AZ::Interface<IMultiplayer>::Get();
const auto agentType = iMultiplayer->GetAgentType();
const bool spawnImmediately =
(agentType == MultiplayerAgentType::ClientServer || agentType == MultiplayerAgentType::DedicatedServer);
@ -470,6 +472,12 @@ namespace Multiplayer
{
CreateEntitiesImmediate(*netSpawnable, NetEntityRole::Authority);
}
else
{
// If we don't spawn net entities immediately (i.e. it is a client),
// tell the server/host it can start sending updates that will instantiate entities.
iMultiplayer->SendReadyForEntityUpdates(true);
}
}
void NetworkEntityManager::OnRootSpawnableReleased([[maybe_unused]] uint32_t generation)

Loading…
Cancel
Save