public class MatchmakerManager : ScriptableObject
{
// 在本地测试 Matchmaker 时,此值应为 http://localhost:51504
// 在测试 Matchmaker 的在线发布时,不需要在 URL 末尾指定端口
public const string MATCHMAKER_URL = "<FRONTEND_COMPONENT_URL>";
private readonly HttpClient _httpClient = new();
public KcpTransport transport = (KcpTransport)NetworkManager.singleton.transport;
/// <summary>
/// 从 Matchmaker 获取票据的数据
/// </summary>
/// <param name="ticketId">票据的 ID</param>
/// <returns>票据数据</returns>
public async Task<Ticket> GetTicket(string ticketId)
{
var response = await _httpClient.GetAsync($"{MATCHMAKER_URL}/v1/tickets/{ticketId}");
if (!response.IsSuccessStatusCode)
{
throw new HttpRequestException($"Error code: {response.StatusCode}");
}
var responseContent = await response.Content.ReadAsStringAsync();
Ticket content = JsonConvert.DeserializeObject<Ticket>(responseContent);
return content;
}
/// <summary>
/// 为 Matchmaker 创建新票据
/// </summary>
/// <param name="modeTag">玩家希望进入的游戏模式</param>
/// <returns>票据数据</returns>
public async Task<Ticket> CreateTicket(string modeTag)
{
CreateTicketPayload objectToSerialize = new()
{
mode = modeTag
};
var jsonContent = new StringContent(JsonConvert.SerializeObject(objectToSerialize), Encoding.UTF8, "application/json");
var response = await _httpClient.PostAsync($"{MATCHMAKER_URL}/v1/tickets", jsonContent);
if (!response.IsSuccessStatusCode)
{
throw new HttpRequestException($"Error code: {response.StatusCode}");
}
var responseContent = await response.Content.ReadAsStringAsync();
Ticket content = JsonConvert.DeserializeObject<Ticket>(responseContent);
return content;
}
/// <summary>
/// 从 Matchmaker 删除票据
/// </summary>
/// <param name="ticketId">票据的 ID</param>
public async Task DeleteTicket(string ticketId)
{
var response = await _httpClient.DeleteAsync($"{MATCHMAKER_URL}/v1/tickets/{ticketId}");
if (!response.IsSuccessStatusCode)
{
throw new HttpRequestException($"Error code: {response.StatusCode}");
}
}
/// <summary>
/// 将玩家连接到比赛
/// </summary>
/// <param name="assignment">票据的分配数据</param>
public void ConnectPlayer(Assignment assignment)
{
string[] networkComponents = assignment.connection.Split(':');
NetworkManager.singleton.networkAddress = networkComponents[0];
if (ushort.TryParse(networkComponents[1], out ushort port))
{
transport.port = port;
}
else
{
throw new Exception("port couldn't be parsed");
}
NetworkManager.singleton.StartClient();
}
/// <summary>
/// 将玩家从比赛中断开连接
/// </summary>
public void DisconnectPlayer()
{
NetworkManager.singleton.StopClient();
}
}