You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

322 lines
9.1 KiB

  1. local ProtocolZhanJi = class("ProtocolZhanJi")
  2. --[[
  3. table中的key在经过json转换之后,全部都会变成string,所以在使用的时候都使用string
  4. --]]
  5. local InterfaceKey =
  6. {
  7. brief = "gamb.brief", -- 获取简要的战绩列表信息
  8. detail = "gamb.replay", -- 获取某一局的详细战绩
  9. }
  10. function ProtocolZhanJi:ctor()
  11. -- 添加分发事件的组件
  12. cc.GameObject.extend(self)
  13. self:addComponent(require("luaScript.cc.components.behavior.EventProtocol"):new()):exportMethods()
  14. self.phpUrl = getGlobalPhpUrl()
  15. -- 保存到本地的文件名,所有子游戏必须重写并且保证不冲突
  16. self.fileName = "";
  17. -- 是否茶馆模式
  18. self.isClubMode = false
  19. -- 每页以及每次拉取最大数量
  20. self.numPrePage = 20;
  21. -- 茶馆战绩最多保存几天内的数据
  22. self.numMaxDay = 7;
  23. -- 所有的战绩保存在这里
  24. self.zhanjiInfoList = {}
  25. end
  26. -- 子游戏的战绩协议应该重写此接口
  27. function ProtocolZhanJi:init()
  28. end
  29. -- 从本地文件读取以前的战绩信息
  30. function ProtocolZhanJi:loadFromFile()
  31. local jsonString = loadStringFromFile(self.fileName)
  32. if jsonString then
  33. self.zhanjiInfoList = json.decode(jsonString) or {}
  34. end
  35. end
  36. -- 保存战绩信息到本地文件
  37. function ProtocolZhanJi:saveToFile()
  38. if self.isClubMode then
  39. -- 茶馆在存储之前要先剔除那些过期的战绩
  40. -- 首先计算出N天前0点0分0秒对应的时间戳
  41. local timeBegin = endtime - self.numMaxDay * 24 * 3600
  42. local dateBegin = os.date("*t", timeBegin)
  43. dateBegin.hour = 0;
  44. dateBegin.min = 0;
  45. dateBegin.sec = 0;
  46. timeBegin = os.time(dateBegin);
  47. -- 逐个比较文件中的数据,剔除过期的内容
  48. for k,v in pairs(self.zhanjiInfoList) do
  49. local endtime = tonumber(v.endtime) or 0
  50. if endtime < timeBegin then
  51. self.zhanjiInfoList[k] = nil
  52. end
  53. end
  54. end
  55. local jsonString = json.encode(self.zhanjiInfoList)
  56. saveStringToFile(jsonString, self.fileName)
  57. -- PC端另外再存一份数据以方便查看
  58. if cc.Application:getInstance():getTargetPlatform() == 0 then
  59. table.saveToLocFile(self.zhanjiInfoList, self.fileName..".lua")
  60. end
  61. end
  62. -- 检查战绩列表,找到需要下载的战绩进行下载
  63. function ProtocolZhanJi:checkAndDownload(idxList)
  64. local idxListDownload = {}
  65. if idxList then
  66. for k,v in pairs(idxList) do
  67. if not self.zhanjiInfoList[v] then
  68. table.insert(idxListDownload, v)
  69. end
  70. end
  71. end
  72. if table.nums(idxListDownload) >0 then
  73. self:getZhanjiBrief(idxListDownload)
  74. else
  75. self:dispatchEvent({name = "getZhanjiBriefResponse"})
  76. end
  77. end
  78. -- 获取指定房间的战绩概要
  79. -- 因为所有子游戏和茶馆的概要信息结构都是一致的。所以可以都使用同一个接口
  80. -- 如果发现某个游戏的概要信息结构不一样,请通知服务器改动
  81. function ProtocolZhanJi:getZhanjiBrief(idxListDownload)
  82. local strList
  83. local cnt = 0;
  84. for k,v in pairs(idxListDownload) do
  85. cnt = cnt + 1
  86. if cnt < self.numPrePage then
  87. if not strList then
  88. strList = tostring(v)
  89. else
  90. strList = strList..","..tostring(v)
  91. end
  92. end
  93. end
  94. local tt =
  95. {
  96. action = InterfaceKey.brief, -- 接口名
  97. app = getAppId(), -- appId
  98. uid = app.user.loginInfo.uid, -- userId
  99. idx = strList, -- 索引id,以","分割
  100. }
  101. logD("ProtocolZhanJi:getZhanjiList()", table.tostring(tt))
  102. httpPost(self.phpUrl, tt, handler(self, self.getZhanjiBriefResponse));
  103. end
  104. function ProtocolZhanJi:getZhanjiBriefResponse(status, response)
  105. logD("ProtocolZhanJi:getZhanjiBriefResponse()", status, response)
  106. local ret, ttResult = checkPhpResponse(status, response)
  107. if not ret then
  108. logE("ProtocolZhanJi:getZhanjiBriefResponse()", tostring(ttResult))
  109. return
  110. end
  111. -- 解析服务器下发的战绩信息
  112. if ttResult.gamb then
  113. for pid, info in pairs(ttResult.gamb) do
  114. if table.nums(info) > 0 then
  115. local zhanjiInfo = {}
  116. zhanjiInfo.pid = pid;
  117. zhanjiInfo.gameid = info.gameid; -- 游戏ID
  118. zhanjiInfo.gext = info.gext; -- 游戏拓展属性
  119. zhanjiInfo.roomid = info.roomid; -- 房间号
  120. zhanjiInfo.fbound = info.fbound; -- 完成的局数
  121. zhanjiInfo.nbound = info.nbound; -- 需要完成的局数
  122. zhanjiInfo.endtime = info.endtime; -- 完成时间,unix时间戳
  123. zhanjiInfo.baseChips = tostring(info.baseChips); -- 底分
  124. zhanjiInfo.nCards = info.nCards; -- 消耗房卡
  125. -- 总输赢
  126. zhanjiInfo.tscore = {}
  127. if info.tscore then
  128. for uid, score in pairs(info.tscore) do
  129. zhanjiInfo.tscore[tostring(uid)] = tonumber(score)
  130. end
  131. end
  132. -- 每个玩家的输赢次数
  133. zhanjiInfo.tgamb = {}
  134. if info.tgamb then
  135. for uid, wInfo in pairs(info.tgamb) do
  136. zhanjiInfo.tgamb[tostring(uid)] = {win = tonumber(wInfo.w) or 0, lose = tonumber(wInfo.l) or 0};
  137. end
  138. end
  139. -- 每一局的详细信息
  140. zhanjiInfo.detail = {}
  141. if info.detail then
  142. for jushu, jushuInfo in pairs(info.detail) do
  143. local jsInfo = {}
  144. -- 每一局下面可能有多轮,所以这里还有一次循环
  145. for lunshu, lunshuInfo in pairs(jushuInfo) do
  146. local lsInfo = {}
  147. -- 本轮基本信息
  148. lsInfo.flag = lunshuInfo.flag or 0 -- 0=正常结束 1=吃臭牌 2=吃牌不比 3=无牌赔包子 4=胡臭牌 7=黄庄 8=长时间自动解散 9=解散游戏 , 如果为0、8、9则表示正常结束
  149. lsInfo.subid = lunshuInfo.subid or "" -- 此次小局结束的日志id
  150. lsInfo.endtime = lunshuInfo.endtime or 0 -- 结束时间
  151. -- 本轮结算信息
  152. lsInfo.score = {}
  153. if lunshuInfo.score then
  154. for uid, fenshu in pairs(lunshuInfo.score) do
  155. lsInfo.score[tostring(uid)] = tonumber(fenshu)
  156. end
  157. end
  158. jsInfo[tostring(lunshu)] = lsInfo
  159. end
  160. zhanjiInfo.detail[tostring(jushu)] = jsInfo
  161. end
  162. end
  163. self.zhanjiInfoList[pid] = zhanjiInfo
  164. end
  165. end
  166. end
  167. -- 保存玩家信息
  168. if ttResult.user then
  169. for uid, info in pairs(ttResult.user) do
  170. local name = tostring(info.n) or tostring(uid)
  171. local head = tostring(info.h) or ""
  172. local sex = tonumber(info.s) or 0
  173. -- 添加玩家信息到管理器
  174. if app.playerInfoManager then
  175. app.playerInfoManager:addPlayerInfo(tostring(uid), name, head, sex);
  176. end
  177. end
  178. end
  179. -- 保存到文件
  180. self:saveToFile()
  181. -- 发送事件
  182. self:dispatchEvent({name = "getZhanjiBriefResponse" , result = ttResult})
  183. end
  184. -- 获取指定房间、指定轮数的战绩详情
  185. -- 对于像黄十八、麻将这种,某一局可能出现吃包子需要打多轮或者详细信息量非常大的情况,必须指定subid
  186. -- 类似扑克这种详情量比较小,可以一次拉取所有局数的数据的,才使用 subid = 0
  187. function ProtocolZhanJi:getZhanJiDetail(pid, subid, endcallback)
  188. -- 如果连这个战绩的概要信息都没有的话,就不要拉取详细信息了
  189. local zhanjiInfo = self.zhanjiInfoList[pid]
  190. if not zhanjiInfo then
  191. self:dispatchEvent({name = "getZhanJiDetailResponse"})
  192. return
  193. end
  194. -- 判断本地是否有这个详情,有就不用更新了
  195. local needDownload = false;
  196. if zhanjiInfo.detail then
  197. if subid == 0 then
  198. for k,v in pairs(zhanjiInfo.detail) do
  199. if not v.user then
  200. needDownload = true
  201. end
  202. end
  203. else
  204. if not zhanjiInfo.detail[subid] or not zhanjiInfo.detail[subid].user then
  205. needDownload = true
  206. end
  207. end
  208. end
  209. if not needDownload then
  210. self:dispatchEvent({name = "getZhanJiDetailResponse"})
  211. if endcallback then
  212. endcallback();
  213. end
  214. return
  215. end
  216. -- 没有这个战绩的详情,还是要从服务器下载
  217. local tt =
  218. {
  219. action = InterfaceKey.detail,
  220. app = getAppId(), -- appId
  221. uid = app.user.loginInfo.uid, -- userId
  222. idx = pid, -- 日志ID
  223. subid = subid, -- 小局id 如果需要idx全部战绩,此时subid=0,单个则传subid
  224. }
  225. logD("ProtocolZhanJi:getZhanJiDetail", table.tostring(tt))
  226. httpPost(self.phpUrl, tt, function(status, response)
  227. self:getZhanJiDetailResponse(status, response, pid, subid, endcallback)
  228. end )
  229. end
  230. function ProtocolZhanJi:getZhanJiDetailResponse(status, response, pid, subid, endcallback)
  231. logD("ProtocolZhanJi:getZhanJiDetailResponse()", status, response, pid)
  232. local ret, ttResult = checkPhpResponse(status, response)
  233. if not ret then
  234. logE("ProtocolZhanJi:getZhanJiDetailResponse()", tostring(ttResult))
  235. return
  236. end
  237. local zhanjiInfo = self.zhanjiInfoList[pid]
  238. if zhanjiInfo and zhanjiInfo.detail then
  239. if subid == 0 then
  240. for jushu, lunshuInfo in pairs(ttResult) do
  241. local jsInfo = zhanjiInfo.detail[tostring(jushu)]
  242. if jsInfo then
  243. local lsInfo = jsInfo["1"]
  244. if lsInfo then
  245. for k,v in pairs(lunshuInfo) do
  246. lsInfo[k] = v
  247. end
  248. end
  249. end
  250. end
  251. else
  252. for jushu, jushuInfo in pairs(zhanjiInfo.detail) do
  253. for lunshu, lunshuInfo in pairs(jushuInfo) do
  254. if lunshuInfo.subid == subid then
  255. for k,v in pairs(ttResult) do
  256. lunshuInfo[k] = v
  257. end
  258. end
  259. end
  260. end
  261. end
  262. end
  263. -- 更新本地文件
  264. self:saveToFile();
  265. -- 发送事件
  266. self:dispatchEvent({name = "getZhanJiDetailResponse"})
  267. -- 执行可能存在的回调
  268. if endcallback then
  269. endcallback();
  270. end
  271. end
  272. return ProtocolZhanJi