powerfun-new-net/ViewModels/MainWindowViewModel.cs

987 lines
37 KiB
C#
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

using Prism.Mvvm;
using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Text;
using OnlineUserPool.Hander;
using OnlineUserPool.Model;
using OnlineUserPool.Unility;
using Serilog;
using System.Linq;
using System.Net;
using System.Net.Sockets;
using System.Threading.Tasks;
using System.Windows.Threading;
using System.Diagnostics;
using OnlineUserPool.Services;
using Newtonsoft.Json;
using System.Collections.Concurrent;
using System.IO.Compression;
using System.IO;
using System.Windows;
using OnlineUserPool.Api;
using OnlineUserPool.Api.Model;
namespace OnlineUserPool.ViewModels
{
public class MainWindowViewModel : BindableBase
{
public ObservableCollection<HostModel> Clients { get; private set; } = new ObservableCollection<HostModel>();
private static ConcurrentBag<MsgModel> receiveMes = new ConcurrentBag<MsgModel>();
private static CustomList<RoomModel> RoomList = new CustomList<RoomModel>();
private static int RoomMaxId = 0;
private static int Ticks = 0;
private static object locker = new object();
public static System.Timers.Timer timer;
private static IHandle mapRecordRankingHander;
private Dispatcher dispatcher;
public ObservableCollection<MsgModel> Customers { get; private set; } =
new ObservableCollection<MsgModel>();
private string _Title = "";
public string Title
{
get { return _Title; }
set
{
SetProperty(ref _Title, value);
}
}
private string _SendDataSize = "";
public string SendDataSize
{
get { return _SendDataSize; }
set
{
SetProperty(ref _SendDataSize, value);
}
}
private string _VirtualData = "";
public string VirtualData
{
get { return _VirtualData; }
set
{
SetProperty(ref _VirtualData, value);
}
}
private bool _closeVirtualUser = false;
public bool CloseVirtualUser
{
get { return _closeVirtualUser; }
set
{
SetProperty(ref _closeVirtualUser, value);
}
}
//private IService _udpService;
public MainWindowViewModel()
{
//初始化对战房间信息
var r = GameRoomHelper.Get();
foreach (var item in r)
{
RoomList.Add(item);
}
RoomMaxId = GameRoomHelper.GetMaxId();
//初测程序关闭事件
Application.Current.MainWindow.Closing += MainWindow_Closing;
Title = $"{ IPAddress.Any }:{ ConfigHelp.UdpPort }";
dispatcher = Dispatcher.CurrentDispatcher;
//Customers.Add("suntao");
WriteLine(DateTime.Now.ToShortDateString());
LogHelper.Init();
mapRecordRankingHander = new MapRecordRankingHander();//
//mapRecordRankingHander = new MultiUserHandle();
Log.Information($"初始化连接,当前地址:{ IPAddress.Any }:{ConfigHelp.UdpPort}");
new TcpService1().RunServer(ReceivedData, CientDisconnected);
//var tet = new System.Collections.Concurrent.ConcurrentBag<object>();
var _udpService = new UdpService();
_udpService.RunServer(ReceivedData);
Log.Information("服务启动成功");
timer = new System.Timers.Timer(500);
timer.Elapsed += Timer_Elapsed;
timer.AutoReset = true;
timer.Start();
Log.Information("等待连接");
//Console.ReadKey();
}
private void MainWindow_Closing(object sender, System.ComponentModel.CancelEventArgs e)
{
GameRoomHelper.Set(RoomList.ToList());
GameRoomHelper.SetMaxId(RoomMaxId);
}
private void ReceivedData(IPEndPoint remoteIpEndPoint, ReceiveModel msg, IService service)
{
dispatcher.Invoke(() =>
{
if (!Clients.Any(c => c.Equals(remoteIpEndPoint)))
{
Clients.Add(new HostModel
{
IPEndPoint = remoteIpEndPoint,
LastActiveTime = DateTime.Now,
//RouteId = msg.RouteId,
//MemberId = msg.MemberId,
//V = msg.V,
//Encoding = msg.Encoding,
//Client = msg.Client,
Service = service
});
}
switch (msg.CommandType)
{
//ping命令
case 0:
{
var client = Clients.FirstOrDefault(n => n.Equals(remoteIpEndPoint));
client.LastActiveTime = DateTime.Now;
if (msg.V > 0)
{
client.V = msg.V;
}
}
break;
//消息
case 1:
{
var client = Clients.FirstOrDefault(n => n.Equals(remoteIpEndPoint));
var msg1 = (msg as MsgModel);
client.Competitionid = msg1.Competitionid;
client.Model = msg1.Model;
if (client.Model == "")
{
client.RoomId = msg1.RoomId;
}
if (msg1.V > 0)
{
client.V = msg1.V;
}
receiveMes.Add(msg1);
HandleGameRoomSaved(msg1);
}
break;
//设置客户端
case 2:
{
var client = Clients.FirstOrDefault(n => n.Equals(remoteIpEndPoint));
var msg1 = (msg as SetClientCommand);
client.Encoding = msg1.Encoding;
client.Client = msg1.Client;
client.V = msg1.V;
client.MemberId = msg1.MemberId;
client.Competitionid = msg1.Competitionid;
client.IsWatch = msg1.IsWatch;
}
break;
//GameRoom
case 3:
{
HandleGameRoom(msg);
}
break;
default:
break;
}
if (msg.CommandType == 0)
{
//client.ShowVirtual = msg.ShowVirtual;
}
else if (msg.CommandType == 1)
{
}
});
}
private void Timer_Elapsed(object sender, System.Timers.ElapsedEventArgs e)
{
Ticks++;
NotifyClient();
//定时保存当前房间信息
if (Ticks % 5 == 0)
{
GameRoomHelper.SetMaxId(RoomMaxId);
GameRoomHelper.Set(RoomList.ToList());
}
}
private void HandleGameRoomSaved(MsgModel msg1)
{
//对战房间内的人保存处理
if (msg1.RoomId > 0 && msg1.Saved)
{
var current = RoomList.ToList().Where(c => c.RoomId == msg1.RoomId).FirstOrDefault();
if (current != null)
{
//更新房间内的人的保存状态
var currentPlayer = current.List.Where(c => c.UserId == msg1.MemberId).FirstOrDefault();
if (currentPlayer != null)
{
currentPlayer.Saved = true;
}
var notAllSaved = current.List.Where(c => !c.Saved).Any();
if (!notAllSaved && current.Status != 2)
{
current.Status = 2;
WebService.UpdateGameRoom(current.RoomId, current.Status);
}
if (!current.Saved)
{
notAllSaved = current.List.Where(c => !c.Saved).Any();
if (!notAllSaved && current.Status != 2)
{
current.Status = 2;
}
current.Saved = true;
WebService.AddGameRoom(current.RoomId, current.Status, current.UserId, current.Name, current.MapRouteId, current.Password, current.StartTime.Value, current.CloseTime, current.MaxMembers);
}
}
}
}
private void HandleGameRoom(ReceiveModel msg)
{
//收
switch (msg.SubType)
{
case 0: HandleCreateGameRoom(msg); break;
case 1: HandleJoinGameRoom(msg); break;
case 2: HandleGameRoomReadyStatus(msg); break;
case 3: HandleGameRoomStart(msg); break;
case 4: HandleGameRoomKick(msg); break;
case 5: HandleGameRoomProcess(msg); break;
case 6: HandleQueryGameRoomList(msg); break;//查询房间列表
default:
break;
}
switch (msg.SubType)
{
case 0:
case 1:
case 2:
case 3:
case 4: BroadCastGameRoomList(); break;
}
}
private void SendGameRoomMessage(RoomModel gameRoom)
{
if (gameRoom == null)
return;
var list = new List<MsgModel>();
list.Add(new MsgModel()
{
V = 2,
Point = new double[] { 0d, 0d },
});
string ss = "";
if (gameRoom.List != null && gameRoom.List.Count > 0)
{
ss = string.Join("|", gameRoom.List.Select(c => c.ToString()));
}
int total = 0;
var G = $"{total}l[{gameRoom},detail{{{ss}}}]";
var temp = string.Join("|", list.Select(m => m.ToString(2))) + "|";
var strV21 = $"*l{{{ temp }}};g{{{ G}}};#";
var ddd = new Data1(strV21);
var needList = Clients.Where(c => c.RoomId == gameRoom.RoomId).ToList();
foreach (var client in needList)
{
bool isZip = client.Encoding == "gzip";
client.Service.Send(ddd.GetBytes(isZip), ddd.GetBytes(isZip).Length, client.IPEndPoint);
client.Request = "";
}
}
private void BroadCastGameRoomList()
{
//广播
var needlist = Clients.Where(c => c.Model != null && c.Model.Equals("GameRoom") && !string.IsNullOrEmpty(c.Request));
var list = new List<MsgModel>();
list.Add(new MsgModel()
{
V = 2,
Point = new double[] { 0d, 0d },
});
var temp = string.Join("|", list.Select(m => m.ToString(2))) + "|";
foreach (var item in needlist)
{
var G = GameRoomMessageHandler(item);
var strV21 = $"*l{{{ temp }}};g{{{G}}};#";
var ddd = new Data1(strV21);
bool isZip = item.Encoding == "gzip";
item.Service.Send(ddd.GetBytes(isZip), ddd.GetBytes(isZip).Length, item.IPEndPoint);
}
}
//查询房间列表
private void HandleQueryGameRoomList(ReceiveModel msg)
{
var query = msg as QueryGameRoomListCommand;
var needSend = Clients.Where(c => c.MemberId == query.UserId).FirstOrDefault();
if (needSend == null)
return;
needSend.Request = $"List/{query.PageIndex}/{query.PageSize}/{query.Name}";
var list = new List<MsgModel>();
list.Add(new MsgModel()
{
V = 2,
Point = new double[] { 0d, 0d },
});
var temp = string.Join("|", list.Where(m => m.Competitionid == needSend.Competitionid).Select(m => m.ToString(2))) + "|";
List<RoomModel> rooms;
if (!string.IsNullOrEmpty(query.Name))
{
rooms = RoomList.ToList().Where(c => c.Name.Contains(query.Name) || c.RoomId.ToString() == query.Name).OrderBy(c => c.Status).ThenByDescending(c => c.CreateTime).ToList();
}
else
{
rooms = RoomList.ToList().OrderBy(c => c.Status).ThenByDescending(c => c.CreateTime).ToList();
}
//计算总页数
int total = 0;
if (query.PageSize != 0)
{
total = rooms.Count() / query.PageSize;
total = rooms.Count() % query.PageSize == 0 ? total : total + 1;
}
rooms = rooms.Skip(query.PageIndex * query.PageSize).Take(query.PageSize).ToList();
string roomInfo = $"{total}l";
foreach (var r in rooms)
{
string ss = "";
if (r.List != null && r.List.Count > 0)
{
ss = string.Join("|", r.List.Select(c => c.ToString()));
}
roomInfo += $"[{r.ToString()},detail{{{ss}}}]";
}
var strV21 = $"*l{{{ temp }}};g{{{roomInfo}}};#";
var ddd = new Data1(strV21);
bool isZip = needSend.Encoding == "gzip";
needSend.Service.Send(ddd.GetBytes(isZip), ddd.GetBytes(isZip).Length, needSend.IPEndPoint);
}
//创建房间
private void HandleCreateGameRoom(ReceiveModel msg)
{
var createMsg = msg as CreateGameRoomCommand;
RemoveOtherRoomInfo(createMsg.UserId, createMsg.Id);
var roomId = RoomMaxId + 1;
var list = new List<RoomDetailModel>();
list.Add(new RoomDetailModel()
{
RoomId = roomId,
UserId = createMsg.UserId,
JoinAt = DateTime.Now.ToUniversalTime(),
IsOwner = true,
});
var room = new RoomModel
{
RoomId = roomId,
Name = createMsg.Name,
Password = createMsg.Password,
CloseTime = createMsg.CloseTime,
CreateTime = createMsg.CreateTime,
MapRouteId = createMsg.RouteId,
MapRouteName = createMsg.MapRouteName,
AltitudeGraph = createMsg.AltitudeGraph,
MaxMembers = createMsg.MaxMembers,
UserId = createMsg.UserId,
AverageGrade = createMsg.AverageGrade,
TotalClimb = createMsg.TotalClimb,
Distance = createMsg.Distance,
EnableAR = createMsg.EnableAR,
Enable3D = createMsg.Enable3D,
FileName = createMsg.FileName,
FileUrl = createMsg.FileUrl,
IsLock = !string.IsNullOrEmpty(createMsg.Password),
List = list,
};
var mine = Clients.Where(c => c.MemberId == createMsg.UserId).FirstOrDefault();
if (mine != null)
{
mine.RoomId = room.RoomId;
}
RoomList.Add(room);
RoomMaxId = room.RoomId;
}
//先移除当前用户在其他房间的信息(考虑服务器重启的时候没有响应客户端退出命令)
private void RemoveOtherRoomInfo(int userId, int roomId)
{
var preRoom = RoomList.ToList().FirstOrDefault(c => c.Status == 0 && c.List.Any(a => a.UserId == userId) && c.RoomId != roomId);
if (preRoom != null)
{
var needRemove = preRoom.List.FirstOrDefault(c => c.UserId == userId && c.Saved == false);
preRoom.List.Remove(needRemove);
if (preRoom.List.Count == 0)
{
RoomList.Remove(preRoom);
}
//发送给这个房间的人
SendGameRoomMessage(preRoom);
}
}
//处理当前用户加入房间
private void HandleJoinGameRoom(ReceiveModel msg)
{
var msg1 = msg as JoinGameRoomCommand;
RemoveOtherRoomInfo(msg1.UserId,msg1.RoomId);
var room = RoomList.ToList().Where(c => c.RoomId == msg1.RoomId).FirstOrDefault();
var client = Clients.FirstOrDefault(n => n.MemberId.Equals(msg1.UserId));
//更新房间信息
if (room != null)
{
var list = room.List;
var member = list.Where(c => c.UserId == msg1.UserId).FirstOrDefault();
if (member != null)
{
member.JoinAt = msg1.JoinAt;
}
else
{
//如果房间人数已经满了就拒绝加入
var currentCount = room.List.Count;
if (currentCount + 1 <= room.MaxMembers)
{
list.Add(new RoomDetailModel
{
UserId = msg1.UserId,
JoinAt = msg1.JoinAt,
RoomId = msg1.RoomId
});
if (client != null)
{
client.RoomId = room.RoomId;
client.Request = "";
}
}
}
}
//发送当前房间的信息给当前房间内的人
SendGameRoomMessage(room);
}
//处理当前用户准备状态
private void HandleGameRoomReadyStatus(ReceiveModel msg)
{
var msg1 = msg as GameRoomReadyCommand;
var room = RoomList.ToList().Where(c => c.RoomId == msg1.RoomId).FirstOrDefault();
if (room != null)
{
var list = room.List;
var member = list.Where(c => c.UserId == msg1.UserId).FirstOrDefault();
if (member != null)
{
member.Status = msg1.Status;
}
}
//发送信息给当前房间内的人
SendGameRoomMessage(room);
}
//处理当前用户准备状态
private void HandleGameRoomStart(ReceiveModel msg)
{
var msg1 = msg as GameRoomStartCommand;
var client = Clients.Where(c => c.MemberId == msg1.UserId).FirstOrDefault();
if (client != null)
{
client.RoomId = msg1.RoomId;
}
var room = RoomList.ToList().Where(c => c.RoomId == msg1.RoomId).FirstOrDefault();
if (room != null)
{
room.Status = 1;
room.StatusChangedTime = DateTime.Now;
}
//发送信息给当前房间内的人
SendGameRoomMessage(room);
}
//处理房间踢人的操作
private void HandleGameRoomKick(ReceiveModel msg)
{
var msg1 = msg as GameRoomKickCommand;
var room = RoomList.ToList().FirstOrDefault(c => c.RoomId == msg1.RoomId);
if (room != null)
{
var list = room.List;
var needRemove = list.FirstOrDefault(c => c.UserId == msg1.UserId);
if (needRemove != null)
{
list.Remove(needRemove);
//如果当前是房主退出房间,房主替换成其他人, 房主客户端中断也算
if (needRemove.IsOwner && list.Any())
{
var newOwner = list.FirstOrDefault();
newOwner.IsOwner = true;
room.UserId = newOwner.UserId;
}
}
//房间没有产生记录且人数为0删除房间
if (!room.Saved && !list.Any())
{
RoomList.Remove(room);
}
var mine = Clients.FirstOrDefault(c => c.MemberId == msg1.UserId);
if (mine != null)
{
mine.RoomId = 0;
}
//发送信息给当前房间内的人
SendGameRoomMessage(room);
}
}
private const int ROOM_TIME_OUT = 60;
private const int TOTAL_PROCESS = 100;
//处理房间内人loading进度
private void HandleGameRoomProcess(ReceiveModel msg)
{
var msg1 = msg as GameRoomProcessCommand;
var room = RoomList.ToList().Where(c => c.RoomId == msg1.RoomId).FirstOrDefault();
var client = Clients.Where(c => c.MemberId == msg1.UserId).FirstOrDefault();
if (room != null)
{
var list = room.List;
var player = list.Where(c => c.UserId == msg1.UserId).FirstOrDefault();
if (player != null)
{
player.Process = msg1.Process;
}
var notReady = list.Where(c => c.Process < TOTAL_PROCESS).Any();
var now = DateTime.Now;
var timespan = now - room.StatusChangedTime;
//超时时间1分钟所有人强制开始
if ((notReady && timespan.TotalSeconds > ROOM_TIME_OUT) || !notReady)
{
room.StartTime = now.AddSeconds(10).ToUniversalTime();
}
if (client != null)
{
client.RoomId = room.RoomId;
}
SendGameRoomMessage(room);
}
}
private string GameRoomMessageHandler(HostModel item)
{
//如果当前Client有请求房间列表信息发送房间列表信息
var G = "";
if (!string.IsNullOrEmpty(item.Request))
{
var param = item.Request.Split('/');
var pageInfo = param[0];
if (pageInfo.Equals("List"))
{
var pageIndex = Convert.ToInt32(param[1]);
var pageSize = Convert.ToInt32(param[2]);
var querName = param[3].ToString();
List<RoomModel> rooms;
if (!string.IsNullOrEmpty(querName))
{
rooms = RoomList.ToList().Where(c => c.Name.Contains(querName) || c.RoomId.ToString() == querName).OrderBy(c => c.Status).ThenByDescending(c => c.CreateTime).ToList();
}
else
{
rooms = RoomList.ToList().OrderBy(c => c.Status).ThenByDescending(c => c.CreateTime).ToList();
}
//计算总页数
int total = 0;
if (pageSize != 0)
{
total = rooms.Count() / pageSize;
total = rooms.Count() % pageSize == 0 ? total : total + 1;
}
G = $"{total}l";
rooms = rooms.Skip(pageIndex * pageSize).Take(pageSize).ToList();
foreach (var r in rooms)
{
string ss = "";
if (r.List != null && r.List.Count > 0)
{
ss = string.Join("|", r.List.Select(c => c.ToString()));
}
G += $"[{r.ToString()},detail{{{ss}}}]";
}
}
}
return G;
}
private void NotifyClient()
{
try
{
if (!receiveMes.Any())
{
dispatcher.Invoke(() =>
{
//Customers.Clear();
//删除已经发送的数据
//receiveMes.Clear();
//移除5钟内连接不上的客户端
Clients.ToList().ForEach(item =>
{
if (item.Expire)
{
RemoveClient(item);
}
});
});
return;
}
lock (locker)
{
var msgs = CloneJson(receiveMes).ToList();
receiveMes.Clear();
if (!CloseVirtualUser)
{
//加入虚拟人物消息
var virtualData = mapRecordRankingHander.GetVirtualUserData();
VirtualData = $"{virtualData.Count}";
WriteLine(DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss") + "-当前在线人数:" + Clients.Count + "-当前虚拟人数:" + virtualData.Count);
#if DEBUG
WriteLine($"在线人:{Newtonsoft.Json.JsonConvert.SerializeObject(msgs)}");
//\r\n虚拟人{Newtonsoft.Json.JsonConvert.SerializeObject(virtualData)}
#endif
msgs.AddRange(virtualData);
}
//屏蔽房间模式的用户
var c = Clients.Where(c => string.IsNullOrEmpty(c.Model)).ToList();
SendMessage(c, msgs);
dispatcher.Invoke(() =>
{
Customers.Clear();
foreach (var item in msgs)
{
if (Customers.Any(c => c.MemberId == item.MemberId))
{
continue;
}
Customers.Add(item);
}
//移除下线的客户端
for (int i = 0; i < msgs.Count; i++)
{
if (msgs[i].exit && msgs[i].MemberId > 0)//客户端退出,并且不是虚拟的人物
{
//这个地方有严重的逻辑错误(虚拟的人物不能和真实的人用同一个名字)
var info = Clients.FirstOrDefault(n => n.MemberId == msgs[i].MemberId);
if (info != null)
{
RemoveClient(info);
}
}
}
//删除已经发送的数据
//receiveMes.Clear();
//移除5钟内连接不上的客户端
Clients.ToList().ForEach(item =>
{
if (item.Expire)
{
RemoveClient(item);
}
});
});
}
//更新虚拟人物信息
mapRecordRankingHander.RemoveEndAndAddNewVirtualUser(Customers.Count);
}
catch (Exception e)
{
Log.Error($"NotifyClient:{ e.Message }\r\n{ e.StackTrace }");
}
}
private void SendMessage(IList<HostModel> clients, List<MsgModel> msgModels)
{
if (!clients.Any() || !msgModels.Any())
{
return;
}
var clients1 = clients.ToList();
var list = CloneJson<List<MsgModel>>(msgModels);
foreach (var item in list)
{
item.PreDistance = Math.Round(item.PreDistance, 5);
item.EndDistance = Math.Round(item.EndDistance, 5);
item.WeightKg = Math.Round(item.WeightKg, 2);
}
string jsonString = Newtonsoft.Json.JsonConvert.SerializeObject(list.Select(m => new {
m.RouteId,
m.MemberId,
m.Point,
m.IsCompleted,
m.exit,
m.Speed,
m.PreDistance,
m.EndDistance,
//m.IsVirtual,//后面要把这个字段过滤掉
m.WeightKg,
m.Competitionid,
m.Saved,
m.FrameRate,
}));
var data = Encoding.ASCII.GetBytes(jsonString);
//SendDataSize = (data.Length/1000D).ToString() +"KB";
var strV1 = string.Join("|", list.Select(m => m.ToString(1)));
if (!string.IsNullOrWhiteSpace(strV1))
{
strV1 += "|";
}
//strV1 = "abcdefghijklmnopqrstuvwxyz";
//System.IO.File.AppendAllText(System.Environment.CurrentDirectory + "要发送的数据.txt", strV1.Trim().Replace("\0", "") + "\r\n", Encoding.UTF8);
WriteLine(strV1);
WriteLine(strV1.Length.ToString());
//var dataV1 = Encoding.UTF8.GetBytes(strV1);
//var dataV1ForUdp = strV1.Last() == '|' ? Encoding.ASCII.GetBytes(strV1.Substring(0, strV1.Length - 1)) : dataV1;
//var dataCompressV1 = Encoding.UTF8.GetBytes($"*{ Convert.ToBase64String(CommonHelper.Compress(strV1)) }#");
var data1 = new Data1(strV1);
var data1ForUdp = new Data1(strV1.Last() == '|' ? strV1.Substring(0, strV1.Length - 1) : strV1);
//var watchList = string.Join('|', clients1.Where(c => c.IsWatch).Select(c => c.MemberId));
//var strV2 = $"*l{{{ strV1 }}};w{{{ watchList }}}#";
////var dataCompressV2 = Encoding.UTF8.GetBytes($"{ Convert.ToBase64String(CommonHelper.Compress(strV2)) }");
//var data2 = new Data1(strV2);
SendDataSize = $"\t单客户端数据包V1{ data1.GetBytes().Length / 1000D }KB一共占用带宽{ data1.GetBytes().Length / 1000D * clients1.Count }KB压缩以后{ data1.GetBytes(true).Length / 1000D * clients1.Count }KB";
#region
foreach (var item in clients1)
{
try
{
if (item == null)
{
continue;
}
//if((item.Service is UdpService) ==false)
//{
// continue;
//}
if (item.V != 1 && item.V != 2)
{
item.Service.Send(data, data.Length, item.IPEndPoint);
continue;
}
if (item.V == 1 && item.Service is UdpService)
{
item.Service.Send(data1ForUdp.GetBytes(), data1ForUdp.GetBytes().Length, item.IPEndPoint);
}
else
{
Data1 ddd = null;// = item.V == 1 ? ;
if (item.V == 1)
{
ddd = data1;
}
else if (item.V == 2)
{
var temp = string.Join("|", list.Where(m => m.Competitionid == item.Competitionid).Select(m => m.ToString(2))) + "|";
var watchList1 = string.Join('|', clients1.Where(c => c.IsWatch && c.Competitionid == item.Competitionid).Select(c => c.MemberId));
var e = string.Join("|", list.Where(c => c.RoomId > 0 || c.FrameRate > 0).Select(c => $"{c.MemberId},{c.RoomId},{c.FrameRate},{c.TotalTicks}"));
var strV21 = $"*l{{{ temp }}};w{{{ watchList1 }}};e{{{ e }}};#";
ddd = new Data1(strV21);
}
else
{
continue;
}
bool isZip = item.Encoding == "gzip";
item.Service.Send(ddd.GetBytes(isZip), ddd.GetBytes(isZip).Length, item.IPEndPoint);
}
}
catch (Exception e)
{
Debug.WriteLine(e.Message);
Log.Error($"{ item.IPEndPoint.ToString() }:{ e.Message }\r\n{ e.StackTrace }");
}
}
#endregion
}
private void GameRoomDisConnectHandler(HostModel client)
{
////如果是在对战房间或者对战列表掉线执行,骑行阶段断开连接不移除房间信息
//if (client.Model != null && !client.Model.Equals("GameRoom"))
// return;
RoomList.ToList().ForEach(o => {
if (o.List != null && o.Status != 2)
{
var needRemove = o.List.FirstOrDefault(c => c.UserId == client.MemberId && c.Saved == false);
o.List.Remove(needRemove);
}
});
var needRemoveList = RoomList.ToList().Where(c => c.List.Count == 0 && c.Status != 2).ToList();
foreach (var item in needRemoveList)
{
RoomList.Remove(item);
}
BroadCastGameRoomList();
}
void WriteLine(string str)
{
//Debug.WriteLine(str);
}
T CloneJson<T>(T source)
{
// Don't serialize a null object, simply return the default for that object
if (Object.ReferenceEquals(source, null))
{
return default(T);
}
// initialize inner objects individually
// for example in default constructor some list property initialized with some values,
// but in 'source' these items are cleaned -
// without ObjectCreationHandling.Replace default constructor values will be added to result
var deserializeSettings = new JsonSerializerSettings { ObjectCreationHandling = ObjectCreationHandling.Replace };
return JsonConvert.DeserializeObject<T>(JsonConvert.SerializeObject(source), deserializeSettings);
}
private void CientDisconnected(EndPoint point)
{
dispatcher.Invoke(() =>
{
try
{
var client = Clients.FirstOrDefault(f => f.IPEndPoint.ToString() == point.ToString());
if (client != null)
{
RemoveClient(client);
GameRoomDisConnectHandler(client);
}
}
catch(Exception ex)
{
Log.Information("在CientDisconnected触发以后删除client时报错了,"+ ex.Message +", " + ex.StackTrace);
}
});
}
private void RemoveClient(HostModel client)
{
BeforeRemoved(client);
Clients.Remove(client);
}
private void BeforeRemoved(HostModel client)
{
if(client.RoomId == 0)return;
var room = RoomList.ToList().FirstOrDefault(c => c.RoomId == client.RoomId);
if(room == null)return;
var needRemove = room.List.FirstOrDefault(c => c.UserId == client.MemberId && c.Saved == false);
if(needRemove == null)return;
//从房间中移除,并考虑是否需要删除房间和移交房主
room.List.Remove(needRemove);
if (room.List.Count == 0)
{
RoomList.Remove(room);
}
else
{
var host = room.List.FirstOrDefault();
if (host != null)
{
host.IsOwner = true;
}
}
//更新房间状态
var isComplete = room.List.All(c => c.Saved != false);
if (room.Status > 0)
{
room.Status = isComplete ? 2 : 1;
}
}
}
public class Data1
{
private string _txt = "";
public Data1(string txt)
{
this._txt = txt;
}
public byte[] GetBytes(bool compress = false)
{
if (compress)
{
return GetCompressBytes();
}
return Encoding.UTF8.GetBytes(this._txt);
}
private byte[] GetCompressBytes()
{
var temp = this._txt;
if(temp[0] == '*')
{
temp = temp.Substring(1);
}
if(temp.Last() == '#')
{
temp = temp.Substring(0, temp.Length - 1);
}
return Encoding.UTF8.GetBytes($"*{ Convert.ToBase64String(CommonHelper.Compress(temp)) }#");
}
}
}