/// <summary> /// Handles the <see cref="LeaveRequest"/> and calls <see cref="RemovePeerFromGame"/>. /// </summary> /// <param name="peer"> /// The peer. /// </param> /// <param name="sendParameters"> /// The send Parameters. /// </param> /// <param name="leaveOperation"> /// The operation. /// </param> protected virtual void HandleLeaveOperation(HivePeer peer, SendParameters sendParameters, LeaveRequest leaveOperation) { this.LeaveOperationHandler(peer, sendParameters, leaveOperation); }
/// <summary> /// Called for each operation in the execution queue. /// Every <see cref = "Room" /> has a queue of incoming operations to execute. /// Per game <see cref = "ExecuteOperation" /> is never executed multi-threaded, thus all code executed here has thread safe access to all instance members. /// </summary> /// <param name = "peer"> /// The peer. /// </param> /// <param name = "operationRequest"> /// The operation request to execute. /// </param> /// <param name = "sendParameters"> /// The send Parameters. /// </param> protected override void ExecuteOperation(HivePeer peer, OperationRequest operationRequest, SendParameters sendParameters) { try { base.ExecuteOperation(peer, operationRequest, sendParameters); //if (log.IsDebugEnabled) //{ // log.DebugFormat("Executing operation {0}", (OperationCode)operationRequest.OperationCode); //} switch ((OperationCode)operationRequest.OperationCode) { case OperationCode.CreateGame2: { var createGameRequest = new CreateGameRequest(peer.Protocol, operationRequest); if (peer.ValidateOperation(createGameRequest, sendParameters) == false) { return; } this.LogOperation(peer, operationRequest); createGameRequest.OnStart(); this.HandleCreateGameOperation(peer, sendParameters, createGameRequest); createGameRequest.OnComplete(); } break; case OperationCode.Join: case OperationCode.JoinGame2: { var joinGameRequest = new JoinGameRequest(peer.Protocol, operationRequest); if (peer.ValidateOperation(joinGameRequest, sendParameters) == false) { return; } // Join should be default CreateIfNotexists=true //if (!joinGameRequest.CreateIfNotExists && operationRequest.OperationCode == (byte)OperationCode.Join) //{ // joinGameRequest.CreateIfNotExists = true; //} this.LogOperation(peer, operationRequest); joinGameRequest.OnStart(); this.HandleJoinGameOperation(peer, sendParameters, joinGameRequest); joinGameRequest.OnComplete(); } break; case OperationCode.DebugGame: var debugGameRequest = new DebugGameRequest(peer.Protocol, operationRequest); if (peer.ValidateOperation(debugGameRequest, sendParameters) == false) { return; } this.LogOperation(peer, operationRequest); debugGameRequest.OnStart(); this.HandleDebugGameOperation(peer, debugGameRequest, sendParameters); debugGameRequest.OnComplete(); break; case OperationCode.Leave: { var leaveOperation = new LeaveRequest(peer.Protocol, operationRequest); if (peer.ValidateOperation(leaveOperation, sendParameters) == false) { return; } this.LogOperation(peer, operationRequest); leaveOperation.OnStart(); this.HandleLeaveOperation(peer, sendParameters, leaveOperation); leaveOperation.OnComplete(); break; } case OperationCode.RaiseEvent: { var raiseEventOperation = new RaiseEventRequest(peer.Protocol, operationRequest); if (peer.ValidateOperation(raiseEventOperation, sendParameters) == false) { return; } raiseEventOperation.OnStart(); this.HandleRaiseEventOperation(peer, raiseEventOperation, sendParameters); raiseEventOperation.OnComplete(); break; } case OperationCode.GetProperties: { var getPropertiesOperation = new GetPropertiesRequest(peer.Protocol, operationRequest); if (peer.ValidateOperation(getPropertiesOperation, sendParameters) == false) { return; } getPropertiesOperation.OnStart(); this.HandleGetPropertiesOperation(peer, getPropertiesOperation, sendParameters); getPropertiesOperation.OnComplete(); break; } case OperationCode.SetProperties: { var setPropertiesOperation = new SetPropertiesRequest(peer.Protocol, operationRequest); if (peer.ValidateOperation(setPropertiesOperation, sendParameters) == false) { return; } setPropertiesOperation.OnStart(); this.HandleSetPropertiesOperation(peer, setPropertiesOperation, sendParameters); setPropertiesOperation.OnComplete(); break; } case OperationCode.Ping: { peer.SendOperationResponse(new OperationResponse (operationRequest.OperationCode) , sendParameters); break; } case OperationCode.ChangeGroups: { var changeGroupsOperation = new ChangeGroups(peer.Protocol, operationRequest); if (peer.ValidateOperation(changeGroupsOperation, sendParameters) == false) { return; } changeGroupsOperation.OnStart(); this.HandleChangeGroupsOperation(peer, changeGroupsOperation, sendParameters); changeGroupsOperation.OnComplete(); break; } default: { var message = string.Format("Unknown operation code {0}", (OperationCode)operationRequest.OperationCode); this.SendErrorResponse(peer, operationRequest.OperationCode, ErrorCode.OperationInvalid, message, sendParameters); if (Log.IsWarnEnabled) { Log.Warn(message); } } break; } } catch (Exception ex) { Log.Error(ex); } }
protected void LeaveOperationHandler(HivePeer peer, SendParameters sendParameters, LeaveRequest request) { this.RemovePeerFromGame(peer, request != null && request.IsCommingBack); if (peer != null && request != null) { // is always reliable, so it gets a response peer.SendOperationResponse(new OperationResponse { OperationCode = request.OperationRequest.OperationCode }, sendParameters); } }
protected virtual bool ProcessLeaveGame(int actorNr, LeaveRequest request, SendParameters sendParameters, HivePeer peer) { this.LeaveOperationHandler(peer, sendParameters, request); return true; }
protected override void HandleRemovePeerMessage(HivePeer peer, int reason, string details) { if ((reason == LeaveReason.PlayerTtlTimedOut) || (reason == LeaveReason.LeaveRequest)) { throw new ArgumentException("PlayerTtlTimeout and LeaveRequests are handled in their own routines."); } var actor = this.ActorsManager.ActorsGetActorByPeer(peer); var actorNr = actor != null ? actor.ActorNr : -1; var isInactive = reason != LeaveReason.PluginRequest && peer.JoinStage == HivePeer.JoinStages.Complete && this.PlayerTTL != 0; var mockRequest = new OperationRequest((byte)OperationCode.Leave) { Parameters = new Dictionary<byte, object> { {(byte) ParameterKey.ActorNr, actorNr}, {(byte) ParameterKey.IsInactive, isInactive} } }; var leaveRequest = new LeaveRequest(peer.Protocol, mockRequest); RequestHandler handler = () => { try { return this.ProcessHandleRemovePeerMessage(peer, isInactive); } catch (Exception e) { Log.ErrorFormat("Exception: {0}", e); throw; } }; var info = new LeaveGameCallInfo(this.PendingPluginContinue, this.callEnv) { ActorNr = actorNr, UserId = peer.UserId, Nickname = actor != null ? actor.Nickname : string.Empty, IsInactive = isInactive, Reason = reason, Details = details, Handler = handler, Peer = peer, OperationRequest = leaveRequest, SendParams = new SendParameters() }; try { this.Plugin.OnLeave(info); } catch (Exception e) { this.Plugin.ReportError(Photon.Hive.Plugin.ErrorCodes.UnhandledException, e); } }
/// <summary> /// Handles the <see cref="LeaveRequest"/> and calls <see cref="HiveGame.RemovePeerFromGame"/>. /// </summary> /// <param name="peer"> /// The peer. /// </param> /// <param name="sendParameters"> /// The send Parameters. /// </param> /// <param name="leaveOperation"> /// The leave Operation. /// </param> protected override void HandleLeaveOperation(HivePeer peer, SendParameters sendParameters, LeaveRequest leaveOperation) { var actor = this.GetActorByPeer(peer); if (actor != null) { RequestHandler handler = () => { try { return this.ProcessLeaveGame(actor.ActorNr, leaveOperation, sendParameters, peer); } catch (Exception e) { Log.ErrorFormat("Exception: {0}", e); throw; } }; var info = new LeaveGameCallInfo(this.PendingPluginContinue, this.callEnv) { ActorNr = actor.ActorNr, UserId = peer.UserId, Nickname = actor.Nickname, IsInactive = leaveOperation != null && leaveOperation.IsCommingBack, Reason = LeaveReason.LeaveRequest, Request = leaveOperation, Handler = handler, Peer = peer, SendParams = sendParameters, }; try { this.Plugin.OnLeave(info); } catch (Exception e) { this.Plugin.ReportError(Photon.Hive.Plugin.ErrorCodes.UnhandledException, e); } } else { this.LogQueue.Add(new LogEntry("HandleLeaveOperation", string.Format("Failed to find Actor for peer {0}", peer.ConnectionId))); } }