Files
2HUCardTDGame/scripts/vscripts/system/service.lua
2021-10-24 15:36:18 -04:00

1066 lines
44 KiB
Lua
Executable File
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.
-- local JSON = require( "component/dkjson") --系统自带json
-- local sha = require("libraries/sha")
if Service == nil then
Service = class({})
end
-- 配置项 start
SERVER_KEY = GetDedicatedServerKeyV2("mydota")
REQUEST_TIME_OUT = 30
Service.Config = table.loadkv("scripts/npc/config.txt")
-- 游戏配置项
GameRules.GameData = {
ver = "S8",
admin = Service.Config.admin,
max_food = 12,
code = "", -- 0000为正常完成其它为错误发生
msg = "", -- 出错消息
game_code = "",
game_msg = "",
luck_card = "",
luck_crit = 0,
new_card_list = "",
open_day_list = "",
is_open_day = 0,
server_time = GetRealDateTime(),
}
-- endregion
-- 通用方法 start
-- 通用请求fTimeout超时秒不传则默认hFunc(iStatusCode, sBody)
function Service:Request(method, url, hParams, hFunc, fTimeout)
local handle = CreateHTTPRequestScriptVM(method, url) -- 需要放在Load阶段后即DOTA_GAMERULES_STATE_CUSTOM_GAME_SETUP及以后阶段
handle:SetHTTPRequestHeaderValue("Content-Type", "application/json;charset=uft-8")
if hParams == nil then hParams = {} end
hParams.randomCode = tostring(RandomInt(1, 99999999))
hParams.serverKey = SERVER_KEY
hParams.gameCode = self.Config.gameCode
if method == "get" or method == "GET" then
for k,v in pairs(hParams) do
handle:SetHTTPRequestGetOrPostParameter(tostring(k), tostring(v))
end
else
handle:SetHTTPRequestRawPostBody("application/json", json.encode(hParams))
end
handle:SetHTTPRequestAbsoluteTimeoutMS((fTimeout or REQUEST_TIME_OUT) * 1000)
handle:Send(function(response)
hFunc(response.StatusCode, response.Body)
end)
end
-- 同步模式通用请求,需在 coroutine.wrap 中调用。
function Service:RequestSync(method, url, hParams, fTimeout)
local co = coroutine.running()
self:Request(method, url, hParams, function(iStatusCode, sBody)
coroutine.resume(co, iStatusCode, sBody)
end, fTimeout)
return coroutine.yield()
end
function Service:Get(url, params, func)
local req = CreateHTTPRequestScriptVM("GET", url) -- 需要放在Load阶段后即DOTA_GAMERULES_STATE_CUSTOM_GAME_SETUP及以后阶段
if params == nil then params = {} end
params.randomCode = RandomInt(1, 99999999)
params.serverKey = SERVER_KEY
params.gameCode = self.Config.gameCode
for k,v in pairs(params) do
req:SetHTTPRequestGetOrPostParameter(tostring(k), tostring(v))
end
req:SetHTTPRequestAbsoluteTimeoutMS((REQUEST_TIME_OUT or 60) * 1000)
req:Send(function(response)
func(response.StatusCode, response.Body)
end)
end
function Service:Post(url, data, func)
local req = CreateHTTPRequestScriptVM("POST", url) -- 需要放在Load阶段后即DOTA_GAMERULES_STATE_CUSTOM_GAME_SETUP及以后阶段
req:SetHTTPRequestHeaderValue("Content-Type", "application/json;charset=uft-8")
if data == nil then data = {} end
data.serverKey = SERVER_KEY
data.gameCode = self.Config.gameCode
req:SetHTTPRequestRawPostBody("application/json", json.encode(data))
req:SetHTTPRequestAbsoluteTimeoutMS((REQUEST_TIME_OUT or 60) * 1000)
req:Send(function(response)
func(response.StatusCode, response.Body)
end)
end
-- endregion
-- 编码 start
-- 卡组数据明细解码hex编码的卡组名称#卡牌及数量#卡牌及数量#...卡牌及数量为卡牌物品后4位加数量如00011表示item_0001数量1个。
-- 输入 string e68891e79a84e58da1e7bb84#20084#00023#00801#00922#000410#00571#20044#20194#20204
-- 返回 data : {"name":"我的卡组","item_2008":4,"item_0002":3,"item_0080":1,"item_0092":2,...}
function Service:decodeCardGroup(cardString)
local retData = {}
if cardString == nil or cardString == "" then return retData end
local a = string.split(cardString, "#")
if a == nil or #a < 2 then return retData end
retData["name"] = string.fromhex(a[1])
for i=2, #a do
retData["item_"..string.sub(a[i],1,4)] = tonumber(string.sub(a[i],5,6))
end
return retData
end
-- 卡组数据明细编码hex编码的卡组名称#卡牌及数量#卡牌及数量#...卡牌及数量为卡牌物品后4位加数量如00011表示item_0001数量1个。
-- 输入data = {"name":"我的卡组","item_2008":4,"item_0002":3,"item_0080":1,"item_0092":2,...}
-- 返回string: e68891e79a84e58da1e7bb84#20084#00023#00801#00922#000410#00571#20044#20194#20204#00583#20174#00362#20074#00522#20154#20241#20014#20064#00885#20231#00077#20164#00068#00973#00341#00962#20021#00162#00412
function Service:encodeCardGroup(cardGroup)
local retString = ""
if cardGroup["name"] ~= nil then retString = string.tohex(cardGroup["name"]) end
for k,v in pairs(cardGroup) do
if k ~= "name" then
retString = retString.."#"..string.sub(k,6,9)..tostring(v)
end
end
return retString
end
-- 等级解码
function Service:decodeCardLevel(cardString)
local retData = {}
if cardString == nil or cardString == "" then return retData end
local a = string.split(cardString, "#")
if a == nil or #a < 1 then return retData end
for i=1, #a do
retData["item_0"..string.sub(a[i],1,3)] = tonumber(string.sub(a[i],4,9))
end
return retData
end
-- 等级编码
function Service:encodeCardLevel(cardLevel)
local retString = ""
for k,v in pairs(cardLevel) do
if retString == "" then
retString = string.sub(k,7,9)..tostring(v)
elseif v ~= nil then
retString = retString.."#"..string.sub(k,7,9)..tostring(v)
end
end
return retString
end
-- endregion
-- 加载游戏数据 start
-- 获取游戏用户数据,按顺序
function Service:LoadGameData()
coroutine.wrap(function()
print("----> start request game config : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
local iStatusCode, sBody = Service:RequestSync("get", self.Config.urlGameConfig)
print("<---- end request game config : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
self:InitGameConfig(iStatusCode, sBody)
local input = {method = "get", ids = {}}
for i=0, PlayerResource:GetPlayerCount()-1 do
input.ids[i] = tostring(PlayerResource:GetSteamID(i))
end
print("----> start request player data : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
local iStatusCode, sBody = Service:RequestSync("post", self.Config.urlPlayerData, input)
print("<---- end request player data : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
self:InitPlayerData(iStatusCode, sBody, input)
end)()
end
-- 游戏配置
function Service:InitGameConfig(iStatusCode, sBody)
if iStatusCode == 200 then
local data = json.decode(sBody)
if data then
GameRules.GameData.code = data.code
GameRules.GameData.msg = data.msg
GameRules.GameData.game_code = data.game_code or ""
GameRules.GameData.game_msg = data.game_msg or ""
GameRules.GameData.luck_card = data.luck_card or ""
GameRules.GameData.luck_crit = data.luck_crit or 0
GameRules.GameData.new_card_list = data.new_card_list or ""
GameRules.GameData.open_day_list = data.open_day_list or ""
GameRules.GameData.is_open_day = data.is_open_day or 0
GameRules.GameData.server_time = data.server_time
else
GameRules.GameData.code = "0003"
GameRules.GameData.msg = "游戏配置数据解析失败"
end
else
GameRules.GameData.code = "0004"
GameRules.GameData.msg = "无法访问服务器"
end
CustomNetTables:SetTableValue("CustomGameInfo", "GameData", GameRules.GameData)
end
-- 玩家数据
function Service:InitPlayerData(iStatusCode, sBody, input)
if iStatusCode == 200 then
local data = json.decode(sBody)
if data then
for k,v in pairs(data.bo) do
for i=1,20 do
v["cardgroup"..i] = self:decodeCardGroup(v["cardgroup"..i])
end
v["level_list"] = self:decodeCardLevel(v["level_list"])
local index = tonumber(k)
for key,value in pairs(v) do
GameRules.PlayerData[index][key] = value
end
end
else
for k,v in pairs(input.ids) do
GameRules.PlayerData[k].code = "0003"
GameRules.PlayerData[k].msg = "用户数据解析失败"
end
end
else
for k,v in pairs(input.ids) do
GameRules.PlayerData[k].code = "0004"
GameRules.PlayerData[k].msg = "无法访问服务器"
end
end
for k,v in pairs(input.ids) do
CustomNetTables:SetTableValue("CustomGameInfo", "PlayerData_"..v, GameRules.PlayerData[k])
-- print("--------- PlayerData "..tostring(k))
-- DeepPrintTable(GameRules.PlayerData[k])
end
end
-- endregion
-- 加载排行榜数据 start
-- 获取排行榜通用方法
function Service:GetRank(rankType)
-- 初始化
if GameRules.players_rank_ok == nil then
GameRules.players_rank_ok = false -- 是否载入成功
GameRules.players_rank = {} -- 排行榜基本数据
GameRules.players_rank_data = {} -- 排行榜明细数据
GameRules.players_team_rank = {}
GameRules.players_team_rank_data = {}
end
print("----> start request get rank : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
local input = {}
input["rank_type"] = rankType or "all" --或取值SDT中一个 S 原始榜D 巅峰榜T 挑战榜
self:Get(
self.Config.urlRankData,
input,
function(iStatusCode, sBody)
print("<---- end request get rank : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
if iStatusCode == 200 then
local data = json.decode(sBody)
if data then
if data.code == "0000" then
GameRules.players_rank_ok = true
local datas = data.bo["S"]
if #datas > 0 then
local ranks = {}
for i = 1, #datas do
ranks[i] = {
['steamid'] = datas[i].steamid,
['userid'] = datas[i].userid,
['username'] = string.fromhex(datas[i].username),
['wave'] = datas[i].wave,
['damage'] = datas[i].damage,
['version'] = datas[i].version,
['host'] = datas[i].host,
['updatetime'] = datas[i].update_time
}
for k,v in pairs(datas[i]) do
if string.sub(k,1,4) == "card" then
datas[i][k] = json.decode(string.fromhex(v))
end
end
for id=0, PlayerResource:GetPlayerCount()-1 do
if PlayerResource:IsValidPlayerID(id) then
if GameRules.PlayerData[id].steamid == datas[i].steamid then
GameRules.PlayerData[id].max_wave = datas[i].wave
print("----- 玩家"..tostring(id).."原始榜波数:"..tostring(datas[i].wave))
break
end
end
end
end
GameRules.players_rank = ranks
GameRules.players_rank_data = datas
ranks = {}
datas = {}
CustomNetTables:SetTableValue("CustomGameInfo", "PlayersRank", GameRules.players_rank)
end
local datas = data.bo["D"]
if #datas > 0 then
local ranks = {}
for i = 1, #datas do
ranks[i] = {
['steamid'] = datas[i].steamid,
['userid'] = datas[i].userid,
['username'] = string.fromhex(datas[i].username),
['wave'] = datas[i].wave,
['damage'] = datas[i].damage,
['version'] = datas[i].version,
['host'] = datas[i].host,
['updatetime'] = datas[i].update_time
}
for k,v in pairs(datas[i]) do
if string.sub(k,1,4) == "card" then
datas[i][k] = json.decode(string.fromhex(v))
end
end
for id=0, PlayerResource:GetPlayerCount()-1 do
if PlayerResource:IsValidPlayerID(id) then
if GameRules.PlayerData[id].steamid == datas[i].steamid then
GameRules.PlayerData[id].max_team_wave = datas[i].wave
print("----- 玩家"..tostring(id).."巅峰榜波数:"..tostring(datas[i].wave))
break
end
end
end
end
GameRules.players_team_rank = ranks
GameRules.players_team_rank_data = datas
ranks = {}
datas = {}
CustomNetTables:SetTableValue("CustomGameInfo", "PlayersTeamRank", GameRules.players_team_rank)
end
else
CustomGameEventManager:Send_ServerToAllClients("thtd_server_msg", {code = "0005", msg = data.msg, duration = 10, pos = 200})
end
else
CustomGameEventManager:Send_ServerToAllClients("thtd_server_msg", {code = "0003", msg = "获取排行榜数据出错,本次游戏将无法上传原始榜,数据解析失败", duration = 10, pos = 200})
end
else
CustomGameEventManager:Send_ServerToAllClients("thtd_server_msg", {code = "0004", msg = "获取排行榜数据出错本次游戏将无法上传原始榜StatusCode: "..tostring(iStatusCode), duration = 10, pos = 200})
end
end
)
end
-- 重置排行榜
function Service:ResetRank(index, rankType)
print("----> start request reset rank : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
local input = {method = "reset"}
input["rank_type"] = rankType
if rankType == "S" then
input["steamid"] = GameRules.players_rank[index].steamid
input["userid"] = GameRules.players_rank[index].userid
elseif rankType == "D" then
input["steamid"] = GameRules.players_team_rank[index].steamid
input["userid"] = GameRules.players_team_rank[index].userid
else
return
end
self:Post(
self.Config.urlRankData,
input,
function(iStatusCode, sBody)
print("<---- end request reset rank : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
if iStatusCode == 200 then
local data = json.decode(sBody)
if data then
if data.code == "0000" then
if rankType == "S" then
CustomGameEventManager:Send_ServerToAllClients("thtd_reset_rank", {index = index, msg = ""})
elseif rankType == "D" then
CustomGameEventManager:Send_ServerToAllClients("thtd_reset_team_rank", {index = index, msg = ""})
end
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_server_msg", {code = data.code, msg = "重置排行榜失败,"..data.msg, duration = 5, pos = 100})
end
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_server_msg", {code = "0003", msg = "重置排行榜失败,无法解析数据", duration = 5, pos = 100})
end
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_server_msg", {code = "0004", msg = "重置排行榜失败,无法连接服务器", duration = 5, pos = 100})
end
end
)
end
-- 上传排行榜
function Service:UploadRank(playerId, rankType, wavedata)
print("----> start request upload rank : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
local steamid = tostring(PlayerResource:GetSteamID(playerId))
local input = {method = "update"}
input["rank_type"] = rankType
input["steamid"] = steamid
input["userid"] = tostring(PlayerResource:GetSteamAccountID(playerId))
input["username"] = string.tohex(PlayerResource:GetPlayerName(playerId))
input["version"] = GameRules.GameData.ver
input["wave"] = wavedata["wave"]
input["damage"] = wavedata["damage"]
for k,v in pairs(wavedata) do
if string.sub(k,1,4) == "card" then
input[k] = string.tohex(json.encode(v))
end
end
local teamText = ""
if rankType == "D" then
teamText = "巅峰"
elseif rankType == "S" then
teamText = "原始"
end
local bonus = 10
if wavedata["rank_index"] <= 4 then
bonus = 500 - (wavedata["rank_index"] - 1) * 100
elseif wavedata["rank_index"] <= 9 then
bonus = 170 - (wavedata["rank_index"] - 5) * 10
elseif wavedata["rank_index"] <= 15 then
bonus = 125 - (wavedata["rank_index"] - 10) * 5
elseif wavedata["rank_index"] <= 25 then
bonus = 96 - (wavedata["rank_index"] - 16) * 4
elseif wavedata["rank_index"] <= 50 then
bonus = 58 - (wavedata["rank_index"] - 26) * 2
end
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_server_msg", {code = "0000", msg = "恭喜上榜,排名:".. wavedata["rank_index"] ..",此排名赛季结算奖励:符卡精华 ×"..tostring(bonus), duration = 30, pos = -100})
self:Post(
self.Config.urlRankData,
input,
function(iStatusCode, sBody)
print("<---- end request upload rank : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
if iStatusCode == 200 then
local data = json.decode(sBody)
if data then
if data.code == "0000" then
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_server_msg", {code = "0000", msg = "恭喜!你打破了历史记录,达到了新的最高波数,上传"..teamText.."排行榜成功!", duration = 30})
if SpawnSystem:GetCount() == 0 then Service:ClearSameRank() end
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_server_msg", {code = data.code, msg = "上传排行榜失败,"..data.msg, duration = 10})
end
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_server_msg", {code = "0003", msg = "上传排行榜失败,无法解析数据", duration = 10})
end
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_server_msg", {code = "0004",msg = "上传排行榜失败,无法连接服务器", duration = 10})
end
end
)
end
-- 清除相同的排行榜
function Service:ClearSameRank()
if GameRules.GameData.is_clear_rank == true then return end
GameRules.GameData.is_clear_rank = true
local toplist
local isTeam = GameRules.HeroList[0].is_team_mode
if isTeam == true then
toplist = GameRules.players_team_rank_data
else
toplist = GameRules.players_rank_data
end
if #toplist == 0 then return end
local toDelList = {}
for i=1,#toplist-1 do
local wavedata = toplist[i]
if table.hasvalue(toDelList, i) == false then
for j=i+1,#toplist do
local topdata = toplist[j]
local isSameRank = false
if wavedata["card1"] ~= "" and wavedata["card1"] ~= nil and topdata["card1"] ~= "" and topdata["card1"] ~= nil and wavedata["card1"]["itemname"] == topdata["card1"]["itemname"] then
if wavedata["card1"]["damage"] / (10000 * wavedata["damage"]) >= 0.6 and topdata["card1"]["damage"] / (10000 * topdata["damage"]) >= 0.6 then
isSameRank = true
end
end
if isSameRank == false then
local topDamage1 = 0
local topDamage2 = 0
local topNum = 0
for x=1,12 do
if wavedata["card"..tostring(x)] ~= "" and wavedata["card"..tostring(x)] ~= nil then
topDamage1 = topDamage1 + wavedata["card"..tostring(x)]["damage"]
end
if topdata["card"..tostring(x)] ~= "" and topdata["card"..tostring(x)] ~= nil then
topDamage2 = topDamage2 + topdata["card"..tostring(x)]["damage"]
end
if topDamage1 / (10000 * wavedata["damage"]) >= 0.8 and topDamage2 / (10000 * topdata["damage"]) >= 0.8 then
topNum = x
break
end
end
if topNum > 0 then
local sameCount = 0
local usedIndex = ""
for x=1,topNum do
for y=1,topNum do
if string.find(usedIndex,tostring(y)) == nil and wavedata["card"..tostring(x)] ~= "" and topdata["card"..tostring(y)] ~= "" and topdata["card"..tostring(y)] ~= nil and wavedata["card"..tostring(x)]["itemname"] == topdata["card"..tostring(y)]["itemname"] then
sameCount = sameCount + 1
usedIndex = usedIndex..tostring(y)..","
break
end
end
end
if sameCount == topNum then isSameRank = true end
end
end
if isSameRank == true then
table.insert(toDelList, j)
end
end
end
end
for k,v in pairs(toDelList) do
if isTeam == true then
Service:ResetRank(v, "D")
else
Service:ResetRank(v, "S")
end
end
print("---------- the same rank : ", json.encode(toDelList))
end
-- endregion
-- 玩家数据 start
-- 保存玩家卡组
function Service:SaveCardGroup(playerId, groupKey, groupData)
print("----> start request save card group : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
local steamid = tostring(PlayerResource:GetSteamID(playerId))
local input = {method = "save_card_group"}
input["steamid"] = steamid
input["userid"] = tostring(PlayerResource:GetSteamAccountID(playerId))
input["group_key"] = groupKey
input["group_data"] = self:encodeCardGroup(groupData)
self:Post(
self.Config.urlPlayerData,
input,
function(iStatusCode, sBody)
print("<---- end request save card group : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
if iStatusCode == 200 then
local data = json.decode(sBody)
if data then
if data.code == "0000" then
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_save_cardgroup", {code = data.code, msg = ""})
GameRules.PlayerData[playerId][groupKey] = groupData
CustomNetTables:SetTableValue("CustomGameInfo", "PlayerData_"..steamid, GameRules.PlayerData[playerId])
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_save_cardgroup", {code = data.code, msg = data.msg})
end
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_save_cardgroup", {code = "0005", msg = "数据解析失败:"..sBody})
end
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_save_cardgroup", {code = "0009", msg = "无法连接服务器StatusCode: "..tostring(iStatusCode)})
end
end
)
end
-- 获取玩家基础数据
function Service:GetPlayerBaseData(playerId)
local steamid = tostring(PlayerResource:GetSteamID(playerId))
print("----> start request player base data : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
self:Get(
self.Config.urlPlayerBaseData,
{id = steamid},
function(iStatusCode, sBody)
print("<---- end request player base data : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
if iStatusCode == 200 then
local data = json.decode(sBody)
if data then
if data.code == "0000" then
self:UpdatePlayerData(playerId, data)
end
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_update_player_data", data)
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_update_player_data", {code = "0003", msg = "返回数据解析失败"})
end
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_update_player_data", {code = "0004", msg = "无法连接服务器StatusCode: "..tostring(iStatusCode)})
end
end
)
end
-- 更新玩家基础数据信息
function Service:UpdatePlayerData(playerId, data)
GameRules.PlayerData[playerId].point = data.point
GameRules.PlayerData[playerId].level_list = self:decodeCardLevel(data.level_list)
GameRules.PlayerData[playerId].pet_level = data.pet_level
GameRules.PlayerData[playerId].end_time = data.end_time
GameRules.PlayerData[playerId].key_total = data.key_total
GameRules.PlayerData[playerId].key_save_date = data.key_save_date
GameRules.PlayerData[playerId].vip = data.vip
if GameRules:State_Get() == DOTA_GAMERULES_STATE_GAME_IN_PROGRESS then
-- 更新宠物等级
local hero = GameRules.HeroList[playerId]
local pet = hero.reimu_pet
if pet ~= nil and pet.pet_level ~= data.pet_level then
local oldLevel = pet.pet_level
pet.pet_level = data.pet_level
pet:FindModifierByName("modifier_reimu_pet_01_level"):SetStackCount(data.pet_level)
pet:CreatureLevelUp(data.pet_level - oldLevel)
end
-- 更新钥匙数量
local item = hero:FindItemInInventory("item_3121")
if item ~= nil then
if data.key_total ~= item:GetCurrentCharges() then
item:SetCurrentCharges(data.key_total)
if data.key_total <= 0 then
hero:RemoveItem(item)
end
end
elseif data.key_total > 0 then
item = CreateItem("item_3121", nil, nil)
if item ~= nil then
item.owner_player_id = playerId
item:SetPurchaser(hero)
item:SetCurrentCharges(data.key_total)
hero:AddItem(item)
end
end
end
CustomNetTables:SetTableValue("CustomGameInfo", "PlayerData_"..tostring(PlayerResource:GetSteamID(playerId)), GameRules.PlayerData[playerId])
end
-- 培养卡牌
function Service:SaveCardLevel(playerId, card, level)
print("----> start request save card group : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
local steamid = tostring(PlayerResource:GetSteamID(playerId))
local input = {method = "save_card_level"}
input["steamid"] = steamid
input["userid"] = tostring(PlayerResource:GetSteamAccountID(playerId))
input["card"] = card --item_0001
input["level"] = level --增加等级
self:Post(
self.Config.urlPlayerData,
input,
function(iStatusCode, sBody)
print("<---- end request save card group : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
if iStatusCode == 200 then
local data = json.decode(sBody)
if data then
if data.code == "0000" then
GameRules.PlayerData[playerId].point = GameRules.PlayerData[playerId].point - data.cost_point
GameRules.PlayerData[playerId]["level_list"][card] = (GameRules.PlayerData[playerId]["level_list"][card] or 0) + level
CustomNetTables:SetTableValue("CustomGameInfo", "PlayerData_"..steamid, GameRules.PlayerData[playerId])
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_update_game_point", {point = GameRules.PlayerData[playerId].point})
data.level_list = GameRules.PlayerData[playerId]["level_list"]
end
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_train_card_complete", data)
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_train_card_complete", {code = "0003", msg = "返回数据解析失败"})
end
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_train_card_complete", {code = "0004", msg = "无法连接服务器StatusCode: "..tostring(iStatusCode)})
end
end
)
end
-- 保存宠物
function Service:SavePetCustom(playerId)
print("----> start request save pet custom : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
local steamid = tostring(PlayerResource:GetSteamID(playerId))
local input = {method = "save_pet_custom"}
input["steamid"] = steamid
input["userid"] = tostring(PlayerResource:GetSteamAccountID(playerId))
input["pet_model"] = GameRules.PlayerData[playerId].pet_model
input["pet_effect"] = GameRules.PlayerData[playerId].pet_effect
self:Post(
self.Config.urlPlayerData,
input,
function(iStatusCode, sBody)
print("<---- end request save pet custom : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
if iStatusCode == 200 then
local data = json.decode(sBody)
if data then
if data.code == "0000" then
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "show_message", {msg="pet_cumstom_saved", duration=15, params={}, color="#ff0"})
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_server_msg", {code = data.code, msg = data.msg})
end
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "display_custom_error", {msg="user_server_error"})
end
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "display_custom_error", {msg="connect_server_error"})
end
end
)
end
-- 购买魔法钥匙
function Service:BuyMagicKey(playerId, count)
print("----> start request buy magic key : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
local steamid = tostring(PlayerResource:GetSteamID(playerId))
local input = {method = "buy_key"}
input["steamid"] = steamid
input["userid"] = tostring(PlayerResource:GetSteamAccountID(playerId))
input["count"] = count
self:Post(
self.Config.urlPlayerData,
input,
function(iStatusCode, sBody)
print("<---- end request buy magic key : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
if iStatusCode == 200 then
local data = json.decode(sBody)
if data then
if data.code == "0000" then
GameRules.PlayerData[playerId]["point"] = GameRules.PlayerData[playerId]["point"] - data.cost_point
CustomNetTables:SetTableValue("CustomGameInfo", "PlayerData_"..steamid, GameRules.PlayerData[playerId])
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_update_game_point", {point = GameRules.PlayerData[playerId]["point"]})
local hero = GameRules.HeroList[playerId]
local item = hero:FindItemInInventory("item_3121")
if item ~= nil then
item:SetCurrentCharges(item:GetCurrentCharges() + count)
else
item = CreateItem("item_3121", nil, nil)
if item ~= nil then
item.owner_player_id = playerId
item:SetPurchaser(hero)
item:SetCurrentCharges(count)
hero:AddItem(item)
end
end
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "show_message", {msg="key_made_tip", duration=3, params={}, color="#ff0"})
ParticleManager:DestroyParticleSystem(hero.thtd_emoji_effect,true)
hero.thtd_emoji_effect = ParticleManager:CreateParticle("particles/thtd/emoji/thtd_msg_hongliange.vpcf", PATTACH_OVERHEAD_FOLLOW, hero)
ParticleManager:SetParticleControlEnt(hero.thtd_emoji_effect , 0, hero, PATTACH_OVERHEAD_FOLLOW, "attach_hitloc", Vector(0,0,0), true) --灵梦用 attach_emoji
ParticleManager:SetParticleControl(hero.thtd_emoji_effect, 3, Vector(1,0,0))
ParticleManager:DestroyParticleSystemTime(hero.thtd_emoji_effect,5.0)
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_server_msg", {code = data.code, msg = "购买钥匙失败,"..data.msg})
end
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "display_custom_error", {msg="user_server_error"})
end
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "display_custom_error", {msg="connect_server_error"})
end
end
)
end
-- 保存魔法钥匙
function Service:SaveKeyCount(playerId)
if GameRules.PlayerData[playerId].code ~= "0000" then
return
end
local keyCount = 0
local hero = GameRules.HeroList[playerId]
local itemTpSlot = hero:GetItemInSlot(DOTA_ITEM_TP_SCROLL) --15
if itemTpSlot then
keyCount = itemTpSlot:GetCurrentCharges()
end
if keyCount == GameRules.PlayerData[playerId]["key_total"] then
return
end
print("----> start request save key count : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
local steamid = tostring(PlayerResource:GetSteamID(playerId))
local input = {method = "save_key_count"}
input["steamid"] = steamid
input["userid"] = tostring(PlayerResource:GetSteamAccountID(playerId))
input["key_total"] = keyCount
input["key_use_count"] = GameRules.PlayerData[playerId]["key_use_count"]
self:Post(
self.Config.urlPlayerData,
input,
function(iStatusCode, sBody)
print("<---- end request save key count : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
if iStatusCode == 200 then
local data = json.decode(sBody)
if data then
if data.code == "0000" then
GameRules.PlayerData[playerId]["key_total"] = keyCount
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_server_msg", {code = data.code, msg = "保存钥匙数量失败,"..data.msg, duration = 10, pos = 150})
end
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_server_msg", {code = "0003", msg = "保存钥匙数量失败,无法解析数据", duration = 10, pos = 150})
end
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_server_msg", {code = "0004", msg = "保存钥匙数量失败,无法连接服务器", duration = 10, pos = 150})
end
end
)
end
-- 保存凤凰之灵
function Service:SavePowerMaxCount(playerId, isAdd)
print("----> start request save power max count : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
local steamid = tostring(PlayerResource:GetSteamID(playerId))
local input = {method = "save_power_max"}
input["steamid"] = steamid
input["userid"] = tostring(PlayerResource:GetSteamAccountID(playerId))
if isAdd == true then
input["op"] = "add"
else
input["op"] = "sub"
end
self:Post(
self.Config.urlPlayerData,
input,
function(iStatusCode, sBody)
print("<---- end request save power max count : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
if iStatusCode == 200 then
local data = json.decode(sBody)
if data then
if data.code == "0000" then
print("----- 玩家"..tostring(playerId).."的凤凰之灵已保存")
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_server_msg", {code = data.code, msg = "保存凤凰之灵失败,"..data.msg, duration = 10})
end
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_server_msg", {code = "0003", msg = "保存凤凰之灵失败,无法解析数据", duration = 10})
end
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_server_msg", {code = "0004", msg = "保存凤凰之灵失败,无法连接服务器", duration = 10})
end
end
)
end
-- 首胜奖励
function Service:GiveDayFirstWinBonus(playerId)
print("----> start request day first win : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
local steamid = tostring(PlayerResource:GetSteamID(playerId))
local input = {method = "day_first_win"}
input["steamid"] = steamid
input["userid"] = tostring(PlayerResource:GetSteamAccountID(playerId))
self:Post(
self.Config.urlPlayerData,
input,
function(iStatusCode, sBody)
print("<---- end request day first win : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
if iStatusCode == 200 then
local data = json.decode(sBody)
if data then
if data.code == "0000" then
GameRules.PlayerData[playerId]["point"] = GameRules.PlayerData[playerId]["point"] + data.bonus_point
CustomNetTables:SetTableValue("CustomGameInfo", "PlayerData_"..steamid, GameRules.PlayerData[playerId])
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_update_game_point", {point = GameRules.PlayerData[playerId]["point"]})
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_server_msg", {code = "0000", msg = "获得 符卡精华 x"..tostring(data.bonus_point)})
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_server_msg", {code = data.code, msg = "每日开箱奖励失败,"..data.msg})
end
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_server_msg", {code = "0003", msg = "每日开箱奖励失败,无法解析数据"})
end
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_server_msg", {code = "0004", msg = "每日开箱奖励失败,无法连接服务器"})
end
end
)
end
-- endregion
-- 赞助 start
-- 创建订单
function Service:CreateShopOrder(playerId, payType, amount, price, goods)
print("----> start request buy order : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
local current = 0
local tips = ""
if goods == "fairy" then
current = GameRules.PlayerData[playerId].point
tips = "获得:符卡精华 ×"..tostring(amount)
elseif goods == "pet" then
current = GameRules.PlayerData[playerId].pet_level
tips = "宠物等级提升 "..tostring(amount).." 级,特别奖励时间增加 "..tostring(amount*2).." 个月"
end
local steamid = tostring(PlayerResource:GetSteamID(playerId))
local input = {method = "create_shop_order"}
input["steamid"] = steamid
input["userid"] = tostring(PlayerResource:GetSteamAccountID(playerId))
input["pay_type"] = payType -- 1支付宝2微信
input["amount"] = amount -- 订单数量
input["price"] = price -- 价格,整数,分
input["goods"] = goods -- 商品
input["current"] = current -- 当前数量
GameRules.PlayerData[playerId].order_tips = "没有生成订单"
self:Post(
self.Config.urlPlayerData,
input,
function(iStatusCode, sBody)
print("<---- end request buy order : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
if iStatusCode == 200 then
local data = json.decode(sBody)
if data then
if data.code == "0000" then
GameRules.PlayerData[playerId].order_no = data.order_no
GameRules.PlayerData[playerId].order_tips = tips
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_pay_post", {code = 1, method = payType})
local time = 45
local tick = 1.5
GameRules:GetGameModeEntity():SetContextThink(DoUniqueString("Query_Order_State"),
function()
if GameRules.PlayerData[playerId].order_no == nil then return nil end
if time < 0 then return nil end
self:PayAutoCheck(playerId)
time = time - tick
return tick
end,
tick)
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_pay_post", {code = 505, msg = data.msg})
end
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_pay_post", {code = 505, msg = "无法解析数据,"..sBody})
end
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_pay_post", {code = 201, msg = "无法连接StatusCode: "..tostring(iStatusCode)})
end
end
)
end
-- 支付检查,自动模式
function Service:PayAutoCheck(playerId)
if GameRules.PlayerData[playerId].order_no == nil then
return
end
if GameRules.PlayerData[playerId].query_order == 1 then
return
end
GameRules.PlayerData[playerId].query_order = 1
print("----> start request query pay order : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
local steamid = tostring(PlayerResource:GetSteamID(playerId))
local input = {method = "query_order"}
input["steamid"] = steamid
input["userid"] = tostring(PlayerResource:GetSteamAccountID(playerId))
input["order_no"] = GameRules.PlayerData[playerId].order_no
self:Post(
self.Config.urlPlayerData,
input,
function(iStatusCode, sBody)
print("<---- end request query pay order : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
GameRules.PlayerData[playerId].query_order = nil
if iStatusCode == 200 then
local data = json.decode(sBody)
if data then
if data.code == "0000" then
data.msg = GameRules.PlayerData[playerId].order_tips
GameRules.PlayerData[playerId].order_no = nil
GameRules.PlayerData[playerId].order_tips = "订单已经处理完成"
self:UpdatePlayerData(playerId, data)
data.hide = 1
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_update_player_data", data)
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_pay_result", data)
end
end
end
end
)
end
-- 支付检查
function Service:PayCheck(playerId)
if GameRules.PlayerData[playerId].order_no == nil then
local data = {code = "0001", msg = GameRules.PlayerData[playerId].order_tips}
if data.msg == "订单已经处理完成" then data.code = "0000" end
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_pay_result", data)
return
end
print("----> start request query pay order : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
local steamid = tostring(PlayerResource:GetSteamID(playerId))
local input = {method = "query_order"}
input["steamid"] = steamid
input["userid"] = tostring(PlayerResource:GetSteamAccountID(playerId))
input["order_no"] = GameRules.PlayerData[playerId].order_no
self:Post(
self.Config.urlPlayerData,
input,
function(iStatusCode, sBody)
print("<---- end request query pay order : ", tostring(math.floor(GameRules:GetGameTime()*100 + 0.5)/100))
if iStatusCode == 200 then
local data = json.decode(sBody)
if data then
if data.code == "0000" then
data.msg = GameRules.PlayerData[playerId].order_tips
GameRules.PlayerData[playerId].order_no = nil
GameRules.PlayerData[playerId].order_tips = "订单已经处理完成"
self:UpdatePlayerData(playerId, data)
data.hide = 1
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_update_player_data", data)
end
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_pay_result", data)
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_pay_result", {code = "0003", msg = "查询订单返回数据解析失败,稍后会人工处理,处理完请点击刷新即可,加急请进群联系作者", hide = hideMsg})
end
else
CustomGameEventManager:Send_ServerToPlayer(PlayerResource:GetPlayer(playerId), "thtd_pay_result", {code = "0004", msg = "查询订单无法连接服务器,稍后会人工处理,处理完请点击刷新即可,加急请进群联系作者", hide = hideMsg})
end
end
)
end
-- endregion