private void OnSceneUnloadClient(Guid switchSceneGuid, Stream objectStream) { var networkObjects = UnityEngine.Object.FindObjectsOfType <NetworkObject>(); m_NetworkManager.SpawnManager.ClientCollectSoftSyncSceneObjectSweep(networkObjects); using (var reader = PooledNetworkReader.Get(objectStream)) { var newObjectsCount = reader.ReadUInt32Packed(); for (int i = 0; i < newObjectsCount; i++) { NetworkObject.DeserializeSceneObject(objectStream as Serialization.NetworkBuffer, reader, m_NetworkManager); } } using (var buffer = PooledNetworkBuffer.Get()) using (var writer = PooledNetworkWriter.Get(buffer)) { writer.WriteByteArray(switchSceneGuid.ToByteArray()); m_NetworkManager.MessageSender.Send(m_NetworkManager.ServerClientId, NetworkConstants.CLIENT_SWITCH_SCENE_COMPLETED, NetworkChannel.Internal, buffer); } s_IsSwitching = false; OnSceneSwitched?.Invoke(); }
private static void OnSceneUnloadClient(Guid switchSceneGuid, Stream objectStream) { if (!NetworkManager.Singleton.NetworkConfig.EnableSceneManagement || NetworkManager.Singleton.NetworkConfig.UsePrefabSync) { NetworkSpawnManager.DestroySceneObjects(); using (var reader = PooledNetworkReader.Get(objectStream)) { uint newObjectsCount = reader.ReadUInt32Packed(); for (int i = 0; i < newObjectsCount; i++) { bool isPlayerObject = reader.ReadBool(); ulong networkId = reader.ReadUInt64Packed(); ulong owner = reader.ReadUInt64Packed(); bool hasParent = reader.ReadBool(); ulong?parentNetworkId = null; if (hasParent) { parentNetworkId = reader.ReadUInt64Packed(); } ulong prefabHash = reader.ReadUInt64Packed(); Vector3? position = null; Quaternion?rotation = null; if (reader.ReadBool()) { position = new Vector3(reader.ReadSinglePacked(), reader.ReadSinglePacked(), reader.ReadSinglePacked()); rotation = Quaternion.Euler(reader.ReadSinglePacked(), reader.ReadSinglePacked(), reader.ReadSinglePacked()); } var networkObject = NetworkSpawnManager.CreateLocalNetworkObject(false, 0, prefabHash, parentNetworkId, position, rotation); NetworkSpawnManager.SpawnNetworkObjectLocally(networkObject, networkId, true, isPlayerObject, owner, objectStream, false, 0, true, false); var bufferQueue = BufferManager.ConsumeBuffersForNetworkId(networkId); // Apply buffered messages if (bufferQueue != null) { while (bufferQueue.Count > 0) { BufferManager.BufferedMessage message = bufferQueue.Dequeue(); NetworkManager.Singleton.HandleIncomingData(message.SenderClientId, message.NetworkChannel, new ArraySegment <byte>(message.NetworkBuffer.GetBuffer(), (int)message.NetworkBuffer.Position, (int)message.NetworkBuffer.Length), message.ReceiveTime, false); BufferManager.RecycleConsumedBufferedMessage(message); } } } } } else { var networkObjects = MonoBehaviour.FindObjectsOfType <NetworkObject>(); NetworkSpawnManager.ClientCollectSoftSyncSceneObjectSweep(networkObjects); using (var reader = PooledNetworkReader.Get(objectStream)) { uint newObjectsCount = reader.ReadUInt32Packed(); for (int i = 0; i < newObjectsCount; i++) { bool isPlayerObject = reader.ReadBool(); ulong networkId = reader.ReadUInt64Packed(); ulong owner = reader.ReadUInt64Packed(); bool hasParent = reader.ReadBool(); ulong?parentNetworkId = null; if (hasParent) { parentNetworkId = reader.ReadUInt64Packed(); } ulong instanceId = reader.ReadUInt64Packed(); var networkObject = NetworkSpawnManager.CreateLocalNetworkObject(true, instanceId, 0, parentNetworkId, null, null); NetworkSpawnManager.SpawnNetworkObjectLocally(networkObject, networkId, true, isPlayerObject, owner, objectStream, false, 0, true, false); var bufferQueue = BufferManager.ConsumeBuffersForNetworkId(networkId); // Apply buffered messages if (bufferQueue != null) { while (bufferQueue.Count > 0) { BufferManager.BufferedMessage message = bufferQueue.Dequeue(); NetworkManager.Singleton.HandleIncomingData(message.SenderClientId, message.NetworkChannel, new ArraySegment <byte>(message.NetworkBuffer.GetBuffer(), (int)message.NetworkBuffer.Position, (int)message.NetworkBuffer.Length), message.ReceiveTime, false); BufferManager.RecycleConsumedBufferedMessage(message); } } } } } using (var buffer = PooledNetworkBuffer.Get()) using (var writer = PooledNetworkWriter.Get(buffer)) { writer.WriteByteArray(switchSceneGuid.ToByteArray()); InternalMessageSender.Send(NetworkManager.Singleton.ServerClientId, NetworkConstants.CLIENT_SWITCH_SCENE_COMPLETED, NetworkChannel.Internal, buffer); } s_IsSwitching = false; OnSceneSwitched?.Invoke(); }
private static void OnSceneUnloadServer(Guid switchSceneGuid) { // Justification: Rare alloc, could(should?) reuse var newSceneObjects = new List <NetworkObject>(); { var networkObjects = MonoBehaviour.FindObjectsOfType <NetworkObject>(); for (int i = 0; i < networkObjects.Length; i++) { if (networkObjects[i].IsSceneObject == null) { NetworkSpawnManager.SpawnNetworkObjectLocally(networkObjects[i], NetworkSpawnManager.GetNetworkObjectId(), true, false, null, null, false, 0, false, true); newSceneObjects.Add(networkObjects[i]); } } } for (int j = 0; j < NetworkManager.Singleton.ConnectedClientsList.Count; j++) { if (NetworkManager.Singleton.ConnectedClientsList[j].ClientId != NetworkManager.Singleton.ServerClientId) { using (var buffer = PooledNetworkBuffer.Get()) using (var writer = PooledNetworkWriter.Get(buffer)) { writer.WriteUInt32Packed(CurrentActiveSceneIndex); writer.WriteByteArray(switchSceneGuid.ToByteArray()); uint sceneObjectsToSpawn = 0; for (int i = 0; i < newSceneObjects.Count; i++) { if (newSceneObjects[i].m_Observers.Contains(NetworkManager.Singleton.ConnectedClientsList[j].ClientId)) { sceneObjectsToSpawn++; } } writer.WriteUInt32Packed(sceneObjectsToSpawn); for (int i = 0; i < newSceneObjects.Count; i++) { if (newSceneObjects[i].m_Observers.Contains(NetworkManager.Singleton.ConnectedClientsList[j].ClientId)) { writer.WriteBool(newSceneObjects[i].IsPlayerObject); writer.WriteUInt64Packed(newSceneObjects[i].NetworkObjectId); writer.WriteUInt64Packed(newSceneObjects[i].OwnerClientId); NetworkObject parentNetworkObject = null; if (!newSceneObjects[i].AlwaysReplicateAsRoot && newSceneObjects[i].transform.parent != null) { parentNetworkObject = newSceneObjects[i].transform.parent.GetComponent <NetworkObject>(); } if (parentNetworkObject == null) { writer.WriteBool(false); } else { writer.WriteBool(true); writer.WriteUInt64Packed(parentNetworkObject.NetworkObjectId); } if (!NetworkManager.Singleton.NetworkConfig.EnableSceneManagement || NetworkManager.Singleton.NetworkConfig.UsePrefabSync) { writer.WriteUInt64Packed(newSceneObjects[i].PrefabHash); writer.WriteSinglePacked(newSceneObjects[i].transform.position.x); writer.WriteSinglePacked(newSceneObjects[i].transform.position.y); writer.WriteSinglePacked(newSceneObjects[i].transform.position.z); writer.WriteSinglePacked(newSceneObjects[i].transform.rotation.eulerAngles.x); writer.WriteSinglePacked(newSceneObjects[i].transform.rotation.eulerAngles.y); writer.WriteSinglePacked(newSceneObjects[i].transform.rotation.eulerAngles.z); } else { writer.WriteUInt64Packed(newSceneObjects[i].NetworkInstanceId); } if (NetworkManager.Singleton.NetworkConfig.EnableNetworkVariable) { newSceneObjects[i].WriteNetworkVariableData(buffer, NetworkManager.Singleton.ConnectedClientsList[j].ClientId); } } } InternalMessageSender.Send(NetworkManager.Singleton.ConnectedClientsList[j].ClientId, NetworkConstants.SWITCH_SCENE, NetworkChannel.Internal, buffer); } } } //Tell server that scene load is completed if (NetworkManager.Singleton.IsHost) { OnClientSwitchSceneCompleted(NetworkManager.Singleton.LocalClientId, switchSceneGuid); } s_IsSwitching = false; OnSceneSwitched?.Invoke(); }
protected virtual void RaiseEvent(JObject message) { switch (message["update-type"].ToObject <string>()) { case "SwitchScenes": List <SceneItem> sources = new List <SceneItem>(); foreach (JObject source in message["sources"]) { sources.Add(new SceneItem() { alignment = source["alignment"].ToObject <int>(), cx = source["cx"].ToObject <double>(), x = source["x"].ToObject <double>(), cy = source["cy"].ToObject <double>(), y = source["y"].ToObject <double>(), volume = source["volume"].ToObject <double>(), locked = source["locked"].ToObject <bool>(), name = source["name"].ToObject <string>(), type = source["type"].ToObject <string>(), id = source["id"].ToObject <int>(), render = source["render"].ToObject <bool>(), muted = source["muted"].ToObject <bool>(), source_cx = source["source_cx"].ToObject <int>(), source_cy = source["source_cy"].ToObject <int>() }); } OnSceneSwitched?.Invoke(this, new SceneSwitchedEventArgs() { newSceneName = message["scene-name"].ToObject <string>(), sources = sources.ToArray() }); break; case "ScenesChanged": OnScenesChanged?.Invoke(this, new OBSEventArgs()); break; case "SceneCollectionChanged": OnSceneCollectionChanged?.Invoke(this, new OBSEventArgs()); break; case "SceneCollectionListChanged": OnSceneCollectionListChanged?.Invoke(this, new OBSEventArgs()); break; case "SwitchTransition": OnSwitchTransition?.Invoke(this, new SwitchTransitionEventArgs() { transitionName = message["transition-name"].ToObject <string>() }); break; case "TransitionListChanged": OnTransitionListChanged?.Invoke(this, new OBSEventArgs()); break; case "TransitionDurationChanged": OnTransitionDurationChanged?.Invoke(this, new TransitionDurationChangedEventArgs() { newDuration = message["new-duration"].ToObject <int>() }); break; case "TransitionBegin": OnTransitionBegin?.Invoke(this, new TransitionBeginEventArgs() { duration = message["duration"].ToObject <int>(), fromScene = message["from-scene"].ToObject <string>(), toScene = message["to-scene"].ToObject <string>(), name = message["name"].ToObject <string>(), type = message["type"].ToObject <string>() }); break; case "TransitionEnd": OnTransitionEnd?.Invoke(this, new TransitionEndEventArgs() { duration = message["duration"].ToObject <int>(), toScene = message["to-scene"].ToObject <string>(), name = message["name"].ToObject <string>(), type = message["type"].ToObject <string>() }); break; case "TransitionVideoEnd": OnTransitionVideoEnd?.Invoke(this, new TransitionVideoEndEventArgs() { duration = message["duration"].ToObject <int>(), fromScene = message["from-scene"].ToObject <string>(), toScene = message["to-scene"].ToObject <string>(), name = message["name"].ToObject <string>(), type = message["type"].ToObject <string>() }); break; case "ProfileChanged": OnProfileChanged?.Invoke(this, new OBSEventArgs()); break; case "ProfileListChanged": OnProfileListChanged?.Invoke(this, new OBSEventArgs()); break; case "StreamStarting": OnStreamStarting?.Invoke(this, new OBSEventArgs()); break; case "StreamStarted": OnStreamStarted?.Invoke(this, new OBSEventArgs()); break; case "StreamStopping": OnStreamStopping?.Invoke(this, new OBSEventArgs()); break; case "StreamStopped": OnStreamStopped?.Invoke(this, new OBSEventArgs()); break; case "StreamStatus": OnStreamStatusUpdate?.Invoke(this, new StreamStatusUpdateEventArgs() { recording = message["recording"].ToObject <bool>(), recordingPaused = message["recording-paused"].ToObject <bool>(), replayBufferActive = message["replay-buffer-active"].ToObject <bool>(), streaming = message["streaming"].ToObject <bool>(), bytesPerSec = message["bytes-per-sec"].ToObject <int>(), kbitsPerSec = message["kbits-per-sec"].ToObject <int>(), totalStreamTime = message["total-stream-time"].ToObject <int>(), numTotalFrames = message["num-total-frames"].ToObject <int>(), numDroppedFrames = message["num-dropped-frames"].ToObject <int>(), renderTotalFrames = message["render-total-frames"].ToObject <int>(), renderMissedFrames = message["render-missed-frames"].ToObject <int>(), outputTotalFrames = message["output-total-frames"].ToObject <int>(), outputSkippedFrames = message["output-skipped-frames"].ToObject <int>(), strain = message["strain"].ToObject <double>(), fps = message["fps"].ToObject <double>(), averageFrameTime = message["average-frame-time"].ToObject <double>(), cpuUsage = message["cpu-usage"].ToObject <double>(), memoryUsage = message["memory-usage"].ToObject <double>(), freeDiskSpace = message["free-disk-space"].ToObject <double>() }); break; case "RecordingStarting": OnRecordingStarting?.Invoke(this, new OBSEventArgs()); break; case "RecordingStarted": OnRecordingStarted?.Invoke(this, new OBSEventArgs()); break; case "RecordingStopping": OnRecordingStopping?.Invoke(this, new OBSEventArgs()); break; case "RecordingStopped": OnRecordingStopped?.Invoke(this, new OBSEventArgs()); break; case "RecordingPaused": OnRecordingPaused?.Invoke(this, new OBSEventArgs()); break; case "RecordingResumed": OnRecordingResumed?.Invoke(this, new OBSEventArgs()); break; case "ReplayStarting": OnReplayStarting?.Invoke(this, new OBSEventArgs()); break; case "ReplayStarted": OnReplayStarted?.Invoke(this, new OBSEventArgs()); break; case "ReplayStopping": OnReplayStopping?.Invoke(this, new OBSEventArgs()); break; case "ReplayStopped": OnReplayStopped?.Invoke(this, new OBSEventArgs()); break; case "Exiting": OnExiting?.Invoke(this, new OBSEventArgs()); break; case "Heartbeat": OnHeartbeat?.Invoke(this, new HeartbeatEventArgs() { pulse = message["pulse"].ToObject <bool>(), streaming = message.ContainsKey("streaming") ? message["streaming"].ToObject <bool>() : false, recording = message.ContainsKey("recording") ? message["recording"].ToObject <bool>() : false, currentProfile = message.ContainsKey("current-profile") ? message["current-profile"].ToObject <string>() : string.Empty, currentScene = message.ContainsKey("current-scene") ? message["current-scene"].ToObject <string>() : string.Empty, totalStreamTime = message.ContainsKey("total-stream-time") ? message["total-stream-time"].ToObject <int>() : 0, totalStreamBytes = message.ContainsKey("total-stream-bytes") ? message["total-stream-bytes"].ToObject <int>() : 0, totalStreamFrames = message.ContainsKey("total-stream-frames") ? message["total-stream-frames"].ToObject <int>() : 0, totalRecordTime = message.ContainsKey("total-record-time") ? message["total-record-time"].ToObject <int>() : 0, totalRecordBytes = message.ContainsKey("total-record-bytes") ? message["total-record-bytes"].ToObject <int>() : 0, totalRecordFrames = message.ContainsKey("total-record-frames") ? message["total-record-frames"].ToObject <int>() : 0, stats = message.ContainsKey("stats") ? (new OBSStats() { fps = message["stats"]["fps"].ToObject <double>(), averageframetime = message["stats"]["average-frame-time"].ToObject <double>(), cpuusage = message["stats"]["cpu-usage"].ToObject <double>(), memoryusage = message["stats"]["memory-usage"].ToObject <double>(), freediskspace = message["stats"]["free-disk-space"].ToObject <double>(), rendertotalframes = message["stats"]["render-total-frames"].ToObject <int>(), rendermissedframes = message["stats"]["render-missed-frames"].ToObject <int>(), outputtotalframes = message["stats"]["output-total-frames"].ToObject <int>(), outputskippedframes = message["stats"]["output-skipped-frames"].ToObject <int>() }) : new OBSStats() }); break; case "SourceCreated": OnSourceCreated?.Invoke(this, new SourceEventArgs() { sourceName = message["sourceName"].ToObject <string>(), sourceType = message["sourceType"].ToObject <string>(), sourceKind = message["sourceKind"].ToObject <string>() }); break; case "SourceDestroyed": OnSourceDestroyed?.Invoke(this, new SourceEventArgs() { sourceName = message["sourceName"].ToObject <string>(), sourceType = message["sourceType"].ToObject <string>(), sourceKind = message["sourceKind"].ToObject <string>() }); break; case "SourceVolumeChanged": OnSourceVolumeChanged?.Invoke(this, new SourceVolumeChangedEventArgs() { sourcename = message["sourceName"].ToObject <string>(), sourcevolume = Convert.ToSingle(message["volume"].ToObject <string>()) }); break; case "SourceMuteStateChanged": OnSourceMuteChanged?.Invoke(this, new SourceMuteChangedEventArgs() { sourceName = message["sourceName"].ToObject <string>(), muted = message["muted"].ToObject <bool>() }); break; case "SourceAudioSyncOffsetChanged": OnSourceAudioSyncOffsetChanged?.Invoke(this, new SourceAudioSyncOffsetChangedArgs() { sourceName = message["sourceName"].ToObject <string>(), syncOffset = message["syncOffset"].ToObject <int>() }); break; case "SourceAudioMixersChanged": List <Mixer> mixerlist = new List <Mixer>(); foreach (JObject mixer in message["mixers"]) { mixerlist.Add(new Mixer() { id = mixer["id"].ToObject <int>(), enabled = mixer["enabled"].ToObject <bool>() }); } OnSourceAudioMixersChanged?.Invoke(this, new SourceAudioMixersChangedArgs() { sourceName = message["sourceName"].ToObject <string>(), hexMixersValue = message["hexMixersValue"].ToObject <string>(), mixers = mixerlist.ToArray() }); break; case "SourceRenamed": OnSourceRenamed?.Invoke(this, new SourceRenamedEventArgs() { previousName = message["previousName"].ToObject <string>(), newName = message["newName"].ToObject <string>() }); break; case "SourceFilterAdded": OnSourceFilterAdded?.Invoke(this, new SourceFilterEventArgs() { filterName = message["filterName"].ToObject <string>(), sourceName = message["sourceName"].ToObject <string>(), filterType = message["filterType"].ToObject <string>() }); break; case "SourceFilterRemoved": OnSourceFilterAdded?.Invoke(this, new SourceFilterEventArgs() { filterName = message["filterName"].ToObject <string>(), sourceName = message["sourceName"].ToObject <string>(), filterType = message["filterType"].ToObject <string>() }); break; case "SourceFilterVisibilityChanged": OnSourceFilterVisibilityChanged?.Invoke(this, new SourceFilterVisibilityChangedEventArgs() { filterName = message["filterName"].ToObject <string>(), sourceName = message["sourceName"].ToObject <string>(), filterEnabled = message["filterEnabled"].ToObject <bool>() }); break; case "SourceFiltersReordered": List <Filter> filterlist = new List <Filter>(); foreach (JObject filter in message["filters"]) { filterlist.Add(new Filter() { name = filter["name"].ToObject <string>(), type = filter["type"].ToObject <string>() }); } OnSourceFiltersReordered?.Invoke(this, new SourceFiltersReorderedEventArgs() { sourceName = message["sourceName"].ToObject <string>(), filters = filterlist.ToArray() }); break; case "SceneItemAdded": OnSceneItemAdded?.Invoke(this, new SceneItemEventArgs() { sceneName = message["scene-name"].ToObject <string>(), itemName = message["item-name"].ToObject <string>(), itemId = message["item-id"].ToObject <int>() }); break; case "SceneItemRemoved": OnSceneItemRemoved?.Invoke(this, new SceneItemEventArgs() { sceneName = message["scene-name"].ToObject <string>(), itemName = message["item-name"].ToObject <string>(), itemId = message["item-id"].ToObject <int>() }); break; case "SceneItemVisibilityChanged": OnSceneItemVisibilityChanged?.Invoke(this, new SceneItemVisibilityChangedEventArgs() { sceneName = message["scene-name"].ToObject <string>(), itemName = message["item-name"].ToObject <string>(), itemId = message["item-id"].ToObject <int>(), itemVisible = message["item-visible"].ToObject <bool>() }); break; case "SceneItemLockChanged": OnSceneItemLockChanged?.Invoke(this, new SceneItemLockChangedEventArgs() { sceneName = message["scene-name"].ToObject <string>(), itemName = message["item-name"].ToObject <string>(), itemId = message["item-id"].ToObject <int>(), itemLocked = message["item-locked"].ToObject <bool>() }); break; case "StudioModeSwitched": OnStudioModeSwitched?.Invoke(this, new StudioModeSwitchedEventArgs() { newState = message["new-state"].ToObject <bool>() }); break; default: this.OnOBSWebsocketInfo?.Invoke(this, new OBSWebsocketEventArgs() { text = string.Format("Event not implemented: {0}", (string)message["update-type"]) }); break; } }
private void OnSceneUnloadServer(Guid switchSceneGuid) { // Justification: Rare alloc, could(should?) reuse var newSceneObjects = new List <NetworkObject>(); { var networkObjects = UnityEngine.Object.FindObjectsOfType <NetworkObject>(); for (int i = 0; i < networkObjects.Length; i++) { if (networkObjects[i].NetworkManager == m_NetworkManager) { if (networkObjects[i].IsSceneObject == null) { m_NetworkManager.SpawnManager.SpawnNetworkObjectLocally(networkObjects[i], m_NetworkManager.SpawnManager.GetNetworkObjectId(), true, false, null, null, false, 0, false, true); newSceneObjects.Add(networkObjects[i]); } } } } for (int j = 0; j < m_NetworkManager.ConnectedClientsList.Count; j++) { if (m_NetworkManager.ConnectedClientsList[j].ClientId != m_NetworkManager.ServerClientId) { using (var buffer = PooledNetworkBuffer.Get()) using (var writer = PooledNetworkWriter.Get(buffer)) { writer.WriteUInt32Packed(CurrentActiveSceneIndex); writer.WriteByteArray(switchSceneGuid.ToByteArray()); uint sceneObjectsToSpawn = 0; for (int i = 0; i < newSceneObjects.Count; i++) { if (newSceneObjects[i].Observers.Contains(m_NetworkManager.ConnectedClientsList[j].ClientId)) { sceneObjectsToSpawn++; } } // Write number of scene objects to spawn writer.WriteUInt32Packed(sceneObjectsToSpawn); for (int i = 0; i < newSceneObjects.Count; i++) { if (newSceneObjects[i].Observers.Contains(m_NetworkManager.ConnectedClientsList[j].ClientId)) { newSceneObjects[i].SerializeSceneObject(writer, m_NetworkManager.ConnectedClientsList[j].ClientId); } } m_NetworkManager.MessageSender.Send(m_NetworkManager.ConnectedClientsList[j].ClientId, NetworkConstants.SWITCH_SCENE, NetworkChannel.Internal, buffer); } } } // Tell server that scene load is completed if (m_NetworkManager.IsHost) { OnClientSwitchSceneCompleted(m_NetworkManager.LocalClientId, switchSceneGuid); } s_IsSwitching = false; OnSceneSwitched?.Invoke(); }
public static void FireSceneSwitchDone() { OnSceneSwitched?.Invoke(); }