Пример #1
0
        // invoked by unity runtime immediately after the regular "Update()" function.
        internal void UNetUpdate()
        {
            // check if any behaviours are ready to send
            uint dirtyChannelBits = 0;

            for (int i = 0; i < m_NetworkBehaviours.Length; i++)
            {
                NetworkBehaviour comp = m_NetworkBehaviours[i];
                int channelId         = comp.GetDirtyChannel();
                if (channelId != -1)
                {
                    dirtyChannelBits |= (uint)(1 << channelId);
                }
            }
            if (dirtyChannelBits == 0)
            {
                return;
            }

            for (int channelId = 0; channelId < NetworkServer.numChannels; channelId++)
            {
                if ((dirtyChannelBits & (uint)(1 << channelId)) != 0)
                {
                    s_UpdateWriter.StartMessage(MsgType.UpdateVars);
                    s_UpdateWriter.Write(netId);

                    bool wroteData = false;
                    int  oldPos;
                    for (int i = 0; i < m_NetworkBehaviours.Length; i++)
                    {
                        oldPos = s_UpdateWriter.Position;
                        NetworkBehaviour comp = m_NetworkBehaviours[i];
                        if (comp.GetDirtyChannel() != channelId)
                        {
                            // component could write more than one dirty-bits, so call the serialize func
                            OnSerializeSafely(comp, s_UpdateWriter, false);
                            continue;
                        }

                        if (OnSerializeSafely(comp, s_UpdateWriter, false))
                        {
                            comp.ClearAllDirtyBits();

#if UNITY_EDITOR
                            //UnityEditor.NetworkDetailStats.IncrementStat(
                            //    UnityEditor.NetworkDetailStats.NetworkDirection.Outgoing,
                            //    MsgType.UpdateVars, comp.GetType().Name, 1);
#endif

                            wroteData = true;
                        }
                        if (s_UpdateWriter.Position - oldPos > NetworkServer.maxPacketSize)
                        {
                            if (LogFilter.logWarn)
                            {
                                Debug.LogWarning("Large state update of " + (s_UpdateWriter.Position - oldPos) + " bytes for netId:" + netId + " from script:" + comp);
                            }
                        }
                    }

                    if (!wroteData)
                    {
                        // nothing to send.. this could be a script with no OnSerialize function setting dirty bits
                        continue;
                    }

                    s_UpdateWriter.FinishMessage();
                    NetworkServer.SendWriterToReady(gameObject, s_UpdateWriter, channelId);
                }
            }
        }
Пример #2
0
        public void RebuildObservers(bool initialize)
        {
            if (m_Observers == null)
            {
                return;
            }

            bool changed = false;
            bool result  = false;
            HashSet <NetworkConnection> newObservers = new HashSet <NetworkConnection>();
            HashSet <NetworkConnection> oldObservers = new HashSet <NetworkConnection>(m_Observers);

            for (int i = 0; i < m_NetworkBehaviours.Length; i++)
            {
                NetworkBehaviour comp = m_NetworkBehaviours[i];
                result |= comp.OnRebuildObservers(newObservers, initialize);
            }
            if (!result)
            {
                // none of the behaviours rebuilt our observers, use built-in rebuild method
                if (initialize)
                {
                    for (int i = 0; i < NetworkServer.connections.Count; i++)
                    {
                        var conn = NetworkServer.connections[i];
                        if (conn == null)
                        {
                            continue;
                        }
                        if (conn.isReady)
                        {
                            AddObserver(conn);
                        }
                    }

                    for (int i = 0; i < NetworkServer.localConnections.Count; i++)
                    {
                        var conn = NetworkServer.localConnections[i];
                        if (conn == null)
                        {
                            continue;
                        }
                        if (conn.isReady)
                        {
                            AddObserver(conn);
                        }
                    }
                }
                return;
            }

            // apply changes from rebuild
            foreach (var conn in newObservers)
            {
                if (conn == null)
                {
                    continue;
                }

                if (!conn.isReady)
                {
                    if (LogFilter.logWarn)
                    {
                        Debug.LogWarning("Observer is not ready for " + gameObject + " " + conn);
                    }
                    continue;
                }

                if (initialize || !oldObservers.Contains(conn))
                {
                    // new observer
                    conn.AddToVisList(this);
                    if (LogFilter.logDebug)
                    {
                        Debug.Log("New Observer for " + gameObject + " " + conn);
                    }
                    changed = true;
                }
            }

            foreach (var conn in oldObservers)
            {
                if (!newObservers.Contains(conn))
                {
                    // removed observer
                    conn.RemoveFromVisList(this, false);
                    if (LogFilter.logDebug)
                    {
                        Debug.Log("Removed Observer for " + gameObject + " " + conn);
                    }
                    changed = true;
                }
            }

            // special case for local client.
            if (initialize)
            {
                for (int i = 0; i < NetworkServer.localConnections.Count; i++)
                {
                    if (!newObservers.Contains(NetworkServer.localConnections[i]))
                    {
                        OnSetLocalVisibility(false);
                    }
                }
            }

            if (!changed)
            {
                return;
            }

            m_Observers = new List <NetworkConnection>(newObservers);

            // rebuild hashset once we have the final set of new observers
            m_ObserverConnections.Clear();
            for (int i = 0; i < m_Observers.Count; i++)
            {
                m_ObserverConnections.Add(m_Observers[i].connectionId);
            }
        }
Пример #3
0
        internal void OnStartServer(bool allowNonZeroNetId)
        {
            if (m_IsServer)
            {
                return;
            }
            m_IsServer = true;

            if (m_LocalPlayerAuthority)
            {
                // local player on server has NO authority
                m_HasAuthority = false;
            }
            else
            {
                // enemy on server has authority
                m_HasAuthority = true;
            }

            m_Observers           = new List <NetworkConnection>();
            m_ObserverConnections = new HashSet <int>();
            CacheBehaviours();

            // If the instance/net ID is invalid here then this is an object instantiated from a prefab and the server should assign a valid ID
            if (netId.IsEmpty())
            {
                m_NetId = GetNextNetworkId();
            }
            else
            {
                if (allowNonZeroNetId)
                {
                    //allowed
                }
                else
                {
                    if (LogFilter.logError)
                    {
                        Debug.LogError("Object has non-zero netId " + netId + " for " + gameObject);
                    }
                    return;
                }
            }

            if (LogFilter.logDev)
            {
                Debug.Log("OnStartServer " + gameObject + " GUID:" + netId);
            }
            NetworkServer.instance.SetLocalObjectOnServer(netId, gameObject);

            for (int i = 0; i < m_NetworkBehaviours.Length; i++)
            {
                NetworkBehaviour comp = m_NetworkBehaviours[i];
                try
                {
                    comp.OnStartServer();
                }
                catch (Exception e)
                {
                    Debug.LogError("Exception in OnStartServer:" + e.Message + " " + e.StackTrace);
                }
            }

            if (NetworkClient.active && NetworkServer.localClientActive)
            {
                // there will be no spawn message, so start the client here too
                ClientScene.SetLocalObject(netId, gameObject);
                OnStartClient();
            }

            if (m_HasAuthority)
            {
                OnStartAuthority();
            }
        }
Пример #4
0
 public void InitializeBehaviour(NetworkBehaviour beh, int cmdHash)
 {
     m_Behaviour = beh;
     m_CmdHash   = cmdHash;
 }