powerfun-new-net/ViewModels/MainWindowViewModel.cs

944 lines
36 KiB
C#
Raw Normal View History

2020-10-13 08:54:24 +08:00
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;
2021-07-07 09:49:36 +08:00
using System.IO.Compression;
using System.IO;
2021-12-24 18:35:21 +08:00
using System.Windows;
2022-05-10 19:23:32 +08:00
using OnlineUserPool.Api;
using OnlineUserPool.Api.Model;
2020-10-13 08:54:24 +08:00
namespace OnlineUserPool.ViewModels
{
2022-05-10 19:23:32 +08:00
2020-10-13 08:54:24 +08:00
public class MainWindowViewModel : BindableBase
2022-05-10 19:23:32 +08:00
{
2020-10-13 08:54:24 +08:00
public ObservableCollection<HostModel> Clients { get; private set; } = new ObservableCollection<HostModel>();
private static ConcurrentBag<MsgModel> receiveMes = new ConcurrentBag<MsgModel>();
2022-05-10 19:23:32 +08:00
private static CustomList<RoomModel> RoomList = new CustomList<RoomModel>();
2022-05-18 10:39:35 +08:00
private static int RoomMaxId = 0;
private static int Ticks = 0;
2020-10-13 08:54:24 +08:00
private static object locker = new object();
public static System.Timers.Timer timer;
private static IHandle mapRecordRankingHander;
2020-10-13 08:54:24 +08:00
private Dispatcher dispatcher;
public ObservableCollection<MsgModel> Customers { get; private set; } =
new ObservableCollection<MsgModel>();
2020-10-27 10:20:47 +08:00
private string _Title = "";
public string Title
{
get { return _Title; }
set
{
SetProperty(ref _Title, value);
}
}
2020-10-13 08:54:24 +08:00
private string _SendDataSize = "";
public string SendDataSize
{
get { return _SendDataSize; }
set
{
SetProperty(ref _SendDataSize, value);
}
}
2021-12-24 18:35:21 +08:00
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;
2021-12-24 18:35:21 +08:00
2020-10-13 08:54:24 +08:00
public MainWindowViewModel()
{
2022-05-10 19:23:32 +08:00
//初始化对战房间信息
var r = GameRoomHelper.Get();
foreach (var item in r)
{
RoomList.Add(item);
}
2022-05-18 10:39:35 +08:00
RoomMaxId = GameRoomHelper.GetMaxId();
2022-05-10 19:23:32 +08:00
//初测程序关闭事件
Application.Current.MainWindow.Closing += MainWindow_Closing;
2021-06-24 09:20:01 +08:00
Title = $"{ IPAddress.Any }:{ ConfigHelp.UdpPort }";
2020-10-27 10:20:47 +08:00
2020-10-13 08:54:24 +08:00
dispatcher = Dispatcher.CurrentDispatcher;
//Customers.Add("suntao");
WriteLine(DateTime.Now.ToShortDateString());
LogHelper.Init();
2021-12-24 18:35:21 +08:00
mapRecordRankingHander = new MapRecordRankingHander();//
2021-06-24 09:20:01 +08:00
//mapRecordRankingHander = new MultiUserHandle();
Log.Information($"初始化连接,当前地址:{ IPAddress.Any }:{ConfigHelp.UdpPort}");
2021-07-07 09:49:36 +08:00
new TcpService1().RunServer(ReceivedData, CientDisconnected);
//var tet = new System.Collections.Concurrent.ConcurrentBag<object>();
2022-05-10 19:23:32 +08:00
var _udpService = new UdpService();
_udpService.RunServer(ReceivedData);
2020-10-13 08:54:24 +08:00
Log.Information("服务启动成功");
timer = new System.Timers.Timer(1000);
timer.Elapsed += Timer_Elapsed;
timer.AutoReset = true;
timer.Start();
Log.Information("等待连接");
//Console.ReadKey();
}
2022-05-10 19:23:32 +08:00
private void MainWindow_Closing(object sender, System.ComponentModel.CancelEventArgs e)
{
GameRoomHelper.Set(RoomList.ToList());
2022-05-18 10:39:35 +08:00
GameRoomHelper.SetMaxId(RoomMaxId);
2022-05-10 19:23:32 +08:00
}
2021-07-07 09:49:36 +08:00
private void ReceivedData(IPEndPoint remoteIpEndPoint, ReceiveModel msg, IService service)
2020-10-13 08:54:24 +08:00
{
dispatcher.Invoke(() =>
2020-10-13 08:54:24 +08:00
{
if (!Clients.Any(c => c.Equals(remoteIpEndPoint)))
2020-10-13 08:54:24 +08:00
{
Clients.Add(new HostModel
2020-10-13 08:54:24 +08:00
{
IPEndPoint = remoteIpEndPoint,
LastActiveTime = DateTime.Now,
2021-07-07 09:49:36 +08:00
//RouteId = msg.RouteId,
//MemberId = msg.MemberId,
//V = msg.V,
//Encoding = msg.Encoding,
//Client = msg.Client,
Service = service
});
}
2020-10-13 08:54:24 +08:00
2021-07-07 09:49:36 +08:00
switch (msg.CommandType)
{
//ping命令
case 0:
{
var client = Clients.FirstOrDefault(n => n.Equals(remoteIpEndPoint));
client.LastActiveTime = DateTime.Now;
2022-05-10 19:23:32 +08:00
if (msg.V > 0)
2021-07-07 09:49:36 +08:00
{
client.V = msg.V;
}
}
break;
//消息
case 1:
{
var client = Clients.FirstOrDefault(n => n.Equals(remoteIpEndPoint));
var msg1 = (msg as MsgModel);
client.Competitionid = msg1.Competitionid;
2022-05-10 19:23:32 +08:00
client.Model = msg1.Model;
2022-05-18 10:39:35 +08:00
if (client.Model == "")
{
client.RoomId = msg1.RoomId;
}
2021-07-07 09:49:36 +08:00
if (msg1.V > 0)
{
client.V = msg1.V;
}
receiveMes.Add(msg1);
2022-05-18 10:39:35 +08:00
HandleGameRoomSaved(msg1);
2021-07-07 09:49:36 +08:00
}
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;
2022-05-10 19:23:32 +08:00
//GameRoom
case 3:
{
HandleGameRoom(msg);
}
break;
2021-07-07 09:49:36 +08:00
default:
break;
}
if (msg.CommandType == 0)
{
2022-05-10 19:23:32 +08:00
//client.ShowVirtual = msg.ShowVirtual;
}
else if (msg.CommandType == 1)
{
2022-05-10 19:23:32 +08:00
2020-10-13 08:54:24 +08:00
}
2022-05-10 19:23:32 +08:00
2020-10-13 08:54:24 +08:00
});
}
private void Timer_Elapsed(object sender, System.Timers.ElapsedEventArgs e)
{
2022-05-18 10:39:35 +08:00
Ticks++;
NotifyClient();
2022-05-18 10:39:35 +08:00
//定时保存当前房间信息
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);
}
}
}
}
2022-05-10 19:23:32 +08:00
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()));
}
2022-05-18 10:39:35 +08:00
int total = 0;
var G = $"{total}l[{gameRoom},detail{{{ss}}}]";
2022-05-10 19:23:32 +08:00
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()
{
//广播
2022-05-18 10:39:35 +08:00
var needlist = Clients.Where(c => c.Model != null && c.Model.Equals("GameRoom") && !string.IsNullOrEmpty(c.Request));
2022-05-10 19:23:32 +08:00
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);
2022-05-18 10:39:35 +08:00
var strV21 = $"*l{{{ temp }}};g{{{G}}};#";
2022-05-10 19:23:32 +08:00
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))
{
2022-05-18 10:39:35 +08:00
rooms = RoomList.ToList().Where(c => c.Name.Contains(query.Name) || c.RoomId.ToString() == query.Name).OrderBy(c => c.Status).ThenByDescending(c => c.CreateTime).ToList();
2022-05-10 19:23:32 +08:00
}
else
{
2022-05-18 10:39:35 +08:00
rooms = RoomList.ToList().OrderBy(c => c.Status).ThenByDescending(c => c.CreateTime).ToList();
2022-05-10 19:23:32 +08:00
}
2022-05-18 10:39:35 +08:00
//计算总页数
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";
2022-05-10 19:23:32 +08:00
foreach (var r in rooms)
{
string ss = "";
if (r.List != null && r.List.Count > 0)
{
ss = string.Join("|", r.List.Select(c => c.ToString()));
}
2022-05-18 10:39:35 +08:00
roomInfo += $"[{r.ToString()},detail{{{ss}}}]";
2022-05-10 19:23:32 +08:00
}
2022-05-18 10:39:35 +08:00
var strV21 = $"*l{{{ temp }}};g{{{roomInfo}}};#";
2022-05-10 19:23:32 +08:00
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;
2022-05-18 10:39:35 +08:00
RemoveOtherRoomInfo(createMsg.UserId);
2022-05-10 19:23:32 +08:00
var list = new List<RoomDetailModel>();
list.Add(new RoomDetailModel()
{
UserId = createMsg.UserId,
JoinAt = DateTime.Now.ToUniversalTime(),
IsOwner = true,
});
2022-05-18 10:39:35 +08:00
var roomId = RoomMaxId + 1;
2022-05-10 19:23:32 +08:00
var room = new RoomModel
{
2022-05-18 10:39:35 +08:00
RoomId = roomId,
2022-05-10 19:23:32 +08:00
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);
2022-05-18 10:39:35 +08:00
RoomMaxId = room.RoomId;
}
//先移除当前用户在其他房间的信息(考虑服务器重启的时候没有响应客户端退出命令)
private void RemoveOtherRoomInfo(int userId)
{
var preRoom = RoomList.ToList().Where(c => c.Status == 0 && c.List.Where(c => c.UserId == userId).Any()).FirstOrDefault();
if (preRoom != null)
{
var needRemove = preRoom.List.Where(c => c.UserId == userId).FirstOrDefault();
preRoom.List.Remove(needRemove);
if (preRoom.List.Count == 0)
{
RoomList.Remove(preRoom);
}
//发送给这个房间的人
SendGameRoomMessage(preRoom);
}
2022-05-10 19:23:32 +08:00
}
//处理当前用户加入房间
private void HandleJoinGameRoom(ReceiveModel msg)
{
var msg1 = msg as JoinGameRoomCommand;
2022-05-18 10:39:35 +08:00
RemoveOtherRoomInfo(msg1.UserId);
2022-05-10 19:23:32 +08:00
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
{
2022-05-18 10:39:35 +08:00
//如果房间人数已经满了就拒绝加入
var currentCount = room.List.Count;
if (currentCount + 1 <= room.MaxMembers)
2022-05-10 19:23:32 +08:00
{
2022-05-18 10:39:35 +08:00
list.Add(new RoomDetailModel
{
UserId = msg1.UserId,
JoinAt = msg1.JoinAt,
RoomId = msg1.RoomId
});
if (client != null)
{
client.RoomId = room.RoomId;
client.Request = "";
}
}
2022-05-10 19:23:32 +08:00
}
}
//发送当前房间的信息给当前房间内的人
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;
2022-05-18 10:39:35 +08:00
var client = Clients.Where(c => c.MemberId == msg1.UserId).FirstOrDefault();
if (client != null)
{
client.RoomId = msg1.RoomId;
}
2022-05-10 19:23:32 +08:00
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().Where(c => c.RoomId == msg1.RoomId).FirstOrDefault();
if (room != null)
{
var list = room.List;
var needRemove = list.Where(c => c.UserId == msg1.UserId).FirstOrDefault();
if (needRemove != null)
{
list.Remove(needRemove);
//如果当前是房主退出房间,房主替换成其他人
if (needRemove.IsOwner && list.Count() > 0)
{
var newOwner = list.FirstOrDefault();
newOwner.IsOwner = true;
room.UserId = newOwner.UserId;
}
}
//人数为0删除房间
2022-05-18 10:39:35 +08:00
if (list.Count() == 0 && room.Status == 0)
2022-05-10 19:23:32 +08:00
{
RoomList.Remove(room);
}
var mine = Clients.Where(c => c.MemberId == msg1.UserId).FirstOrDefault();
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;
2022-05-18 10:39:35 +08:00
2022-05-10 19:23:32 +08:00
if (!string.IsNullOrEmpty(querName))
{
2022-05-18 10:39:35 +08:00
rooms = RoomList.ToList().Where(c => c.Name.Contains(querName) || c.RoomId.ToString() == querName).OrderBy(c => c.Status).ThenByDescending(c => c.CreateTime).ToList();
2022-05-10 19:23:32 +08:00
}
else
{
2022-05-18 10:39:35 +08:00
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;
2022-05-10 19:23:32 +08:00
}
2022-05-18 10:39:35 +08:00
G = $"{total}l";
rooms = rooms.Skip(pageIndex * pageSize).Take(pageSize).ToList();
2022-05-10 19:23:32 +08:00
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}}}]";
}
}
}
2022-05-18 10:39:35 +08:00
return G;
2022-05-10 19:23:32 +08:00
}
2020-10-13 08:54:24 +08:00
private void NotifyClient()
{
try
{
2022-05-10 19:23:32 +08:00
if (!receiveMes.Any())
2021-06-24 09:20:01 +08:00
{
dispatcher.Invoke(() =>
{
2021-07-07 09:49:36 +08:00
//Customers.Clear();
2021-06-24 09:20:01 +08:00
//删除已经发送的数据
//receiveMes.Clear();
//移除5钟内连接不上的客户端
Clients.ToList().ForEach(item =>
{
if (item.Expire)
{
Clients.Remove(item);
}
});
});
return;
}
2020-10-13 08:54:24 +08:00
lock (locker)
{
2021-07-07 09:49:36 +08:00
var msgs = CloneJson(receiveMes).ToList();
receiveMes.Clear();
2021-12-24 18:35:21 +08:00
if (!CloseVirtualUser)
{
//加入虚拟人物消息
var virtualData = mapRecordRankingHander.GetVirtualUserData();
VirtualData = $"{virtualData.Count}";
WriteLine(DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss") + "-当前在线人数:" + Clients.Count + "-当前虚拟人数:" + virtualData.Count);
2020-10-13 08:54:24 +08:00
#if DEBUG
2021-12-24 18:35:21 +08:00
WriteLine($"在线人:{Newtonsoft.Json.JsonConvert.SerializeObject(msgs)}");
//\r\n虚拟人{Newtonsoft.Json.JsonConvert.SerializeObject(virtualData)}
#endif
msgs.AddRange(virtualData);
}
2022-05-10 19:23:32 +08:00
//屏蔽房间模式的用户
var c = Clients.Where(c => string.IsNullOrEmpty(c.Model)).ToList();
SendMessage(c, msgs);
2020-10-13 08:54:24 +08:00
dispatcher.Invoke(() =>
{
Customers.Clear();
2021-07-07 09:49:36 +08:00
foreach (var item in msgs)
2020-10-13 08:54:24 +08:00
{
2020-10-27 10:20:47 +08:00
if (Customers.Any(c => c.MemberId == item.MemberId))
{
continue;
}
2020-10-13 08:54:24 +08:00
Customers.Add(item);
}
//移除下线的客户端
2021-07-07 09:49:36 +08:00
for (int i = 0; i < msgs.Count; i++)
2020-10-13 08:54:24 +08:00
{
2022-05-10 19:23:32 +08:00
if (msgs[i].exit && msgs[i].MemberId > 0)//客户端退出,并且不是虚拟的人物
2020-10-13 08:54:24 +08:00
{
//这个地方有严重的逻辑错误(虚拟的人物不能和真实的人用同一个名字)
2021-07-07 09:49:36 +08:00
var info = Clients.FirstOrDefault(n => n.MemberId == msgs[i].MemberId);
2020-10-13 08:54:24 +08:00
if (info != null)
{
Clients.Remove(info);
}
}
}
//删除已经发送的数据
//receiveMes.Clear();
//移除5钟内连接不上的客户端
2020-10-13 08:54:24 +08:00
Clients.ToList().ForEach(item =>
{
if (item.Expire)
{
Clients.Remove(item);
}
});
});
}
//更新虚拟人物信息
mapRecordRankingHander.RemoveEndAndAddNewVirtualUser(Customers.Count);
2020-10-13 08:54:24 +08:00
}
catch (Exception e)
{
2020-10-27 10:20:47 +08:00
Log.Error($"NotifyClient:{ e.Message }\r\n{ e.StackTrace }");
2020-10-13 08:54:24 +08:00
}
}
2022-05-10 19:23:32 +08:00
private void SendMessage(IList<HostModel> clients, List<MsgModel> msgModels)
2020-10-13 08:54:24 +08:00
{
if (!clients.Any() || !msgModels.Any())
2021-06-24 09:20:01 +08:00
{
return;
}
var clients1 = clients.ToList();
2022-05-10 19:23:32 +08:00
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);
}
2022-05-10 19:23:32 +08:00
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,
2020-12-16 13:47:20 +08:00
m.Competitionid,
m.Saved,
2022-05-10 19:23:32 +08:00
m.FrameRate,
}));
2020-10-13 08:54:24 +08:00
var data = Encoding.ASCII.GetBytes(jsonString);
2021-06-24 09:20:01 +08:00
//SendDataSize = (data.Length/1000D).ToString() +"KB";
var strV1 = string.Join("|", list.Select(m => m.ToString(1)));
2021-06-24 09:20:01 +08:00
if (!string.IsNullOrWhiteSpace(strV1))
{
strV1 += "|";
}
2021-07-07 09:49:36 +08:00
//strV1 = "abcdefghijklmnopqrstuvwxyz";
2021-06-24 09:20:01 +08:00
//System.IO.File.AppendAllText(System.Environment.CurrentDirectory + "要发送的数据.txt", strV1.Trim().Replace("\0", "") + "\r\n", Encoding.UTF8);
WriteLine(strV1);
WriteLine(strV1.Length.ToString());
2021-07-07 09:49:36 +08:00
//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);
2021-07-07 09:49:36 +08:00
//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);
2022-05-10 19:23:32 +08:00
SendDataSize = $"\t单客户端数据包V1{ data1.GetBytes().Length / 1000D }KB一共占用带宽{ data1.GetBytes().Length / 1000D * clients1.Count }KB压缩以后{ data1.GetBytes(true).Length / 1000D * clients1.Count }KB";
2021-07-07 09:49:36 +08:00
#region udp发送数据
foreach (var item in clients1)
2020-10-13 08:54:24 +08:00
{
try
{
2022-05-10 19:23:32 +08:00
if (item == null)
{
continue;
}
2021-07-07 09:49:36 +08:00
//if((item.Service is UdpService) ==false)
//{
// continue;
//}
if (item.V != 1 && item.V != 2)
2021-06-24 09:20:01 +08:00
{
2021-07-07 09:49:36 +08:00
item.Service.Send(data, data.Length, item.IPEndPoint);
2021-06-24 09:20:01 +08:00
continue;
}
2021-07-07 09:49:36 +08:00
if (item.V == 1 && item.Service is UdpService)
2021-06-24 09:20:01 +08:00
{
2021-07-07 09:49:36 +08:00
item.Service.Send(data1ForUdp.GetBytes(), data1ForUdp.GetBytes().Length, item.IPEndPoint);
}
else
{
2021-07-07 09:49:36 +08:00
Data1 ddd = null;// = item.V == 1 ? ;
if (item.V == 1)
{
ddd = data1;
}
else if (item.V == 2)
{
2021-08-12 12:26:43 +08:00
var temp = string.Join("|", list.Where(m => m.Competitionid == item.Competitionid).Select(m => m.ToString(2))) + "|";
2021-07-07 09:49:36 +08:00
var watchList1 = string.Join('|', clients1.Where(c => c.IsWatch && c.Competitionid == item.Competitionid).Select(c => c.MemberId));
2022-07-21 09:56:13 +08:00
var e = string.Join("|", list.Where(c => c.RoomId > 0 || c.FrameRate > 0).Select(c => $"{c.MemberId},{c.RoomId},{c.FrameRate},{c.TotalTicks}"));
2022-05-10 19:23:32 +08:00
var strV21 = $"*l{{{ temp }}};w{{{ watchList1 }}};e{{{ e }}};#";
2021-07-07 09:49:36 +08:00
ddd = new Data1(strV21);
}
else
{
continue;
}
bool isZip = item.Encoding == "gzip";
2022-05-10 19:23:32 +08:00
item.Service.Send(ddd.GetBytes(isZip), ddd.GetBytes(isZip).Length, item.IPEndPoint);
}
2020-10-13 08:54:24 +08:00
}
catch (Exception e)
{
Debug.WriteLine(e.Message);
Log.Error($"{ item.IPEndPoint.ToString() }:{ e.Message }\r\n{ e.StackTrace }");
2020-10-13 08:54:24 +08:00
}
}
2021-07-07 09:49:36 +08:00
#endregion
//#region tcp发送数据
//var tcpClient = clients1.Where(c => c.Service is TcpService1).FirstOrDefault();
//if(tcpClient != null)
//{
// tcpClient.Service.Send(dataV1, dataV1.Length, null);
//}
//#endregion
2020-10-13 08:54:24 +08:00
}
2022-05-10 19:23:32 +08:00
private void GameRoomDisConnectHandler(HostModel client)
{
//如果是在对战房间或者对战列表掉线执行,骑行阶段断开连接不移除房间信息
2022-05-18 10:39:35 +08:00
if (client.Model != null && !client.Model.Equals("GameRoom"))
2022-05-10 19:23:32 +08:00
return;
RoomList.ToList().ForEach(o => {
if (o.List != null && o.Status == 0)
{
var needRemove = o.List.Where(c => c.UserId == client.MemberId).FirstOrDefault();
o.List.Remove(needRemove);
}
});
2022-05-18 10:39:35 +08:00
var needRemoveList = RoomList.ToList().Where(c => c.List.Count == 0 && c.Status == 0).ToList();
2022-05-10 19:23:32 +08:00
foreach (var item in needRemoveList)
{
RoomList.Remove(item);
}
BroadCastGameRoomList();
}
2020-10-13 08:54:24 +08:00
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);
2020-10-13 08:54:24 +08:00
}
2021-07-07 09:49:36 +08:00
private void CientDisconnected(EndPoint point)
{
dispatcher.Invoke(() =>
2021-07-07 09:49:36 +08:00
{
try
2021-07-07 09:49:36 +08:00
{
var client = Clients.FirstOrDefault(f => f.IPEndPoint.ToString() == point.ToString());
if (client != null)
{
Clients.Remove(client);
2022-05-10 19:23:32 +08:00
GameRoomDisConnectHandler(client);
}
}
catch(Exception ex)
{
Log.Information("在CientDisconnected触发以后删除client时报错了,"+ ex.Message +", " + ex.StackTrace);
}
});
2021-07-07 09:49:36 +08:00
}
}
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)) }#");
}
2020-10-13 08:54:24 +08:00
}
}