Commit 4cf742321f0433f557d5ff99d0f48874a9c1d759
1 parent
4d8bd32c
pvp
Showing
11 changed files
with
373 additions
and
45 deletions
Show diff stats
src/GlobalVar.lua
@@ -79,7 +79,7 @@ ItemId = { | @@ -79,7 +79,7 @@ ItemId = { | ||
79 | LoveUp = 14, --好感度提升道具 | 79 | LoveUp = 14, --好感度提升道具 |
80 | DinerSpTask = 20, -- 餐厅任务采购券 | 80 | DinerSpTask = 20, -- 餐厅任务采购券 |
81 | LoveBreak = 21, --好感度突破道具 | 81 | LoveBreak = 21, --好感度突破道具 |
82 | - PvpKey = 22, -- 开箱钥匙 | 82 | + PvpKey = 22, -- pvp钥匙 |
83 | LunchFragment = 23, | 83 | LunchFragment = 23, |
84 | HeroFC = {700, 701, 702, 703}, -- 通用角色碎片 | 84 | HeroFC = {700, 701, 702, 703}, -- 通用角色碎片 |
85 | AdvKey = 80, -- 冒险钥匙 | 85 | AdvKey = 80, -- 冒险钥匙 |
src/ProtocolCode.lua
@@ -34,6 +34,7 @@ actionCodes = { | @@ -34,6 +34,7 @@ actionCodes = { | ||
34 | Role_achiveRpc = 119, | 34 | Role_achiveRpc = 119, |
35 | Role_chatRpc = 120, | 35 | Role_chatRpc = 120, |
36 | Role_chat = 121, | 36 | Role_chat = 121, |
37 | + Role_chatGet = 122, | ||
37 | 38 | ||
38 | Adv_startAdvRpc = 151, | 39 | Adv_startAdvRpc = 151, |
39 | Adv_startHangRpc = 152, | 40 | Adv_startHangRpc = 152, |
@@ -126,6 +127,17 @@ actionCodes = { | @@ -126,6 +127,17 @@ actionCodes = { | ||
126 | Friend_pointRpc = 459, | 127 | Friend_pointRpc = 459, |
127 | Friend_updateProperty = 460, | 128 | Friend_updateProperty = 460, |
128 | Friend_randomRpc = 461, | 129 | Friend_randomRpc = 461, |
130 | + | ||
131 | + | ||
132 | + Pvp_formatCommonRpc = 500, | ||
133 | + Pvp_infoRpc = 501, | ||
134 | + Pvp_refreshMatchCRpc = 502, | ||
135 | + Pvp_buyCountRpc = 503, | ||
136 | + Pvp_startBattleRpc = 504, | ||
137 | + Pvp_endBattleRpc = 505, | ||
138 | + Pvp_rankListRpc = 506, | ||
139 | + Pvp_recordListRpc = 507, | ||
140 | + | ||
129 | } | 141 | } |
130 | 142 | ||
131 | rpcResponseBegin = 10000 | 143 | rpcResponseBegin = 10000 |
src/RedisKeys.lua
@@ -18,6 +18,7 @@ RANK_DINER = {"rank:diner1", "rank:diner2"} -- é¤åŽ…æŽ’è¡Œæ¦œ 两个æ¯å¤©äº’æ | @@ -18,6 +18,7 @@ RANK_DINER = {"rank:diner1", "rank:diner2"} -- é¤åŽ…æŽ’è¡Œæ¦œ 两个æ¯å¤©äº’æ | ||
18 | RANK_DINER_INFO = "rank:diner:info" | 18 | RANK_DINER_INFO = "rank:diner:info" |
19 | 19 | ||
20 | RANK_PVP_COMMON = "rank:pvpc" | 20 | RANK_PVP_COMMON = "rank:pvpc" |
21 | +RECORD_PVP_COMMON = "record:pvpc:%d" | ||
21 | RANK_PVP_HIGHT = "rank:pvph" | 22 | RANK_PVP_HIGHT = "rank:pvph" |
22 | -- -- role | 23 | -- -- role |
23 | -- R_FARM_KEY = "role:%d:farm" | 24 | -- R_FARM_KEY = "role:%d:farm" |
src/actions/PvpAction.lua
@@ -3,10 +3,16 @@ local table = table | @@ -3,10 +3,16 @@ local table = table | ||
3 | local math = math | 3 | local math = math |
4 | local redisproxy = redisproxy | 4 | local redisproxy = redisproxy |
5 | local MsgPack = MsgPack | 5 | local MsgPack = MsgPack |
6 | +local httpc = require("http.httpc") | ||
7 | +local remoteUrl = skynet.getenv("codeurl") | ||
6 | 8 | ||
7 | 9 | ||
8 | local _M = {} | 10 | local _M = {} |
11 | +local _pvpBattleInfoCacheC = {} --查询列表 缓存pvp战斗相关数据缓存 | ||
12 | +local _pvpStartBattleCache = nil -- | ||
9 | 13 | ||
14 | +local _pvpRecordInfoCache = {} -- 记录缓存 | ||
15 | +local _pvpRecordBattleInfoCache = {} -- 记录战斗数据缓存 | ||
10 | 16 | ||
11 | function _M.formatCommonRpc(agent , data) | 17 | function _M.formatCommonRpc(agent , data) |
12 | local role = agent.role | 18 | local role = agent.role |
@@ -34,46 +40,314 @@ function _M.formatCommonRpc(agent , data) | @@ -34,46 +40,314 @@ function _M.formatCommonRpc(agent , data) | ||
34 | return true | 40 | return true |
35 | end | 41 | end |
36 | 42 | ||
37 | -function _M.formatHighRpc(agent , data) | 43 | + |
44 | +local function getMatchInfo(pvpList, battleCache) | ||
45 | + table.clear(battleCache) | ||
46 | + local redret = redisproxy:pipelining(function(red) | ||
47 | + for _, info in ipairs(pvpList) do | ||
48 | + if info.t == 1 then | ||
49 | + red:zscore(RANK_PVP_COMMON, info.id) | ||
50 | + end | ||
51 | + end | ||
52 | + end) | ||
53 | + | ||
54 | + local matches = {} | ||
55 | + local curIdx = 1 | ||
56 | + for idx, info in ipairs(pvpList) do | ||
57 | + local curInfo = {idx = idx} | ||
58 | + if info.t == 1 then --玩家 | ||
59 | + curInfo.roleId = info.id | ||
60 | + curInfo.score = tonumber(redret[curIdx] or 0) | ||
61 | + curIdx = curIdx + 1 | ||
62 | + -- name, level, headId, battleV, heros | ||
63 | + local online, roleInfo = rpcRole(curInfo.roleId, "pvpCInfo") | ||
64 | + for k , v in pairs(roleInfo) do | ||
65 | + if k == "battleInfo" then | ||
66 | + battleCache[curInfo.roleId] = v | ||
67 | + else | ||
68 | + curInfo[k] = v | ||
69 | + end | ||
70 | + end | ||
71 | + elseif info.t == 2 then -- robot | ||
72 | + curInfo.robot = info.id | ||
73 | + end | ||
74 | + table.insert(matches, curInfo) | ||
75 | + end | ||
76 | + return matches | ||
77 | +end | ||
78 | + | ||
79 | +-- 获取pvp信息 | ||
80 | +function _M.infoRpc(agent, data) | ||
38 | local role = agent.role | 81 | local role = agent.role |
82 | + local roleId = role:getProperty("id") | ||
39 | local msg = MsgPack.unpack(data) | 83 | local msg = MsgPack.unpack(data) |
40 | - local pvpTH = role.pvpData:getProperty("pvpTH") | 84 | + local ptype = msg.ptype or 1 |
41 | 85 | ||
86 | + local response = {} | ||
87 | + if ptype == 1 then -- 普通pvp | ||
88 | + local redret = redisproxy:pipelining(function(red) | ||
89 | + red:zscore(RANK_PVP_COMMON, roleId) | ||
90 | + red:zrevrank(RANK_PVP_COMMON, roleId) | ||
91 | + end) | ||
92 | + local score = tonumber(redret[1] or 0) | ||
93 | + local rank = tonumber(redret[2] or -2) + 1 --排名 1 - ... -1 未上榜 没打过pvp | ||
94 | + local pvpMC = role:getProperty("pvpMC") | ||
95 | + if not next(pvpMC) then --没有分配过对手 | ||
96 | + role:refreshPvpMatchC(score) | ||
97 | + pvpMC = role:getProperty("pvpMC") | ||
98 | + end | ||
99 | + if not next(pvpMC) then return end | ||
100 | + | ||
101 | + response.score = score | ||
102 | + response.rank = rank | ||
103 | + response.matches = getMatchInfo(pvpMC, _pvpBattleInfoCacheC) | ||
42 | 104 | ||
43 | - role.pvpData:updateProperty({field = "pvpTH", value = pvpTH}) | ||
44 | - SendPacket(actionCodes.Pvp_formatHighRpc, '') | 105 | + elseif ptype == 2 then -- 高级pvp |
106 | + return | ||
107 | + else | ||
108 | + return | ||
109 | + end | ||
110 | + SendPacket(actionCodes.Pvp_infoRpc, MsgPack.pack(response)) | ||
45 | return true | 111 | return true |
46 | end | 112 | end |
47 | 113 | ||
48 | -function _M.refreshMatchRpc(agent, data) | 114 | +function _M.refreshMatchCRpc(agent, data) |
49 | local role = agent.role | 115 | local role = agent.role |
50 | local msg = MsgPack.unpack(data) | 116 | local msg = MsgPack.unpack(data) |
51 | - local pvpData = role.pvpData | ||
52 | - pvpData:refreshMatchC() | 117 | + role:refreshPvpMatchC() |
118 | + | ||
119 | + local pvpMC = role:getProperty("pvpMC") | ||
120 | + local matches = getMatchInfo(pvpMC, _pvpBattleInfoCacheC) | ||
53 | 121 | ||
54 | - SendPacket(actionCodes.Pvp_refreshMatchRpc, '') | 122 | + SendPacket(actionCodes.Pvp_refreshMatchCRpc, MsgPack.pack({matches = matches})) |
55 | return true | 123 | return true |
56 | end | 124 | end |
57 | 125 | ||
58 | function _M.buyCountRpc(agent, data) | 126 | function _M.buyCountRpc(agent, data) |
59 | local role = agent.role | 127 | local role = agent.role |
60 | local msg = MsgPack.unpack(data) | 128 | local msg = MsgPack.unpack(data) |
129 | + local count = msg.count | ||
61 | 130 | ||
131 | + if math.illegalNum(count, 1, math.huge) then | ||
132 | + return 1 | ||
133 | + end | ||
134 | + | ||
135 | + local cost = {[ItemId.Diamond] = globalCsv.pvp_buy_cost * count} | ||
136 | + if not role:checkItemEnough(cost) then return 2 end | ||
137 | + role:costItems(cost) | ||
138 | + role:award({[ItemId.PvpKey] = count}) | ||
62 | 139 | ||
63 | SendPacket(actionCodes.Pvp_buyCountRpc, '') | 140 | SendPacket(actionCodes.Pvp_buyCountRpc, '') |
64 | return true | 141 | return true |
65 | end | 142 | end |
66 | 143 | ||
67 | function _M.startBattleRpc(agent, data) | 144 | function _M.startBattleRpc(agent, data) |
145 | + local role = agent.role | ||
146 | + local msg = MsgPack.unpack(data) | ||
68 | 147 | ||
148 | + local idx = msg.idx | ||
149 | + local revenge = msg.revenge | ||
150 | + | ||
151 | + local matchInfo | ||
152 | + | ||
153 | + if revenge then --复仇 | ||
154 | + if not _pvpRecordInfoCache[idx] then return end | ||
155 | + if _pvpRecordInfoCache[idx].t == 1 then | ||
156 | + matchInfo = _pvpRecordBattleInfoCache[_pvpRecordInfoCache[idx].id] | ||
157 | + elseif _pvpRecordInfoCache[idx].t == 2 then | ||
158 | + matchInfo = {robot = _pvpRecordInfoCache[idx].id} | ||
159 | + end | ||
160 | + else --打正常 | ||
161 | + local pvpMC = role:getProperty("pvpMC") | ||
162 | + if not pvpMC[idx] then return end | ||
163 | + if pvpMC[idx].t == 1 then | ||
164 | + matchInfo = _pvpBattleInfoCacheC[pvpMC[idx].id] | ||
165 | + elseif pvpMC[idx].t == 2 then | ||
166 | + matchInfo = {robot = pvpMC[idx].id} | ||
167 | + end | ||
168 | + end | ||
169 | + | ||
170 | + if not matchInfo then return end | ||
171 | + | ||
172 | + -- 次数扣一波 | ||
173 | + local pvpFree = role.dailyData:getProperty("pvpFree") | ||
174 | + if pvpFree >= globalCsv.pvp_battle_free_count then | ||
175 | + local cost = {[ItemId.PvpKey] = 1} | ||
176 | + if not role:checkItemEnough(cost) then return end | ||
177 | + role:costItems(cost) | ||
178 | + else | ||
179 | + role.dailyData:updateProperty({field = "pvpFree", delta = 1}) | ||
180 | + end | ||
181 | + | ||
182 | + local key = tostring(math.random()) | ||
183 | + _pvpStartBattleCache = {idx = idx, key = key, revenge = revenge} | ||
184 | + | ||
185 | + SendPacket(actionCodes.Pvp_startBattleRpc, MsgPack.pack({matchInfo = matchInfo, key = key})) | ||
186 | + return true | ||
69 | end | 187 | end |
70 | 188 | ||
71 | function _M.endBattleRpc(agent, data) | 189 | function _M.endBattleRpc(agent, data) |
190 | + local role = agent.role | ||
191 | + local roleId = role:getProperty("id") | ||
192 | + local msg = MsgPack.unpack(data) | ||
72 | 193 | ||
73 | -end | 194 | + if not msg.key or not _pvpStartBattleCache or msg.key ~= _pvpStartBattleCache.key then |
195 | + return 1 | ||
196 | + end | ||
197 | + if not msg.idx or not msg.idx ~= _pvpStartBattleCache.idx then | ||
198 | + return 2 | ||
199 | + end | ||
74 | 200 | ||
75 | -function _M.matchListRpc(agent, data) | 201 | + local isWin = msg.starNum and msg.starNum > 0 |
202 | + | ||
203 | + local revenge = _pvpStartBattleCache.revenge | ||
204 | + local match | ||
205 | + if revenge then | ||
206 | + match = _pvpRecordInfoCache[msg.idx] | ||
207 | + else | ||
208 | + local pvpMC = role:getProperty("pvpMC") | ||
209 | + match = pvpMC[msg.idx] | ||
210 | + end | ||
211 | + | ||
212 | + if not match then return end | ||
213 | + | ||
214 | + local temp = string.randWeight(csvdb["player_expCsv"][role:getProperty("level")].pvpBonus, true) | ||
215 | + local reward = role:award({[temp[1]] = temp[2]}) | ||
216 | + local myScore, matchScore, oldmyScore, oldMatchScore, myRank, oldMyRank = role:changePvpScoreCommon(match.t == 1 and match.id or -1, isWin) | ||
217 | + | ||
218 | + _pvpBattleInfoCacheC = {} --重新发阵容了 没毛病 | ||
219 | + _pvpRecordInfoCache = {} -- 记录刷新了 | ||
220 | + _pvpRecordBattleInfoCache = {} -- 取新纪录的时候搞 | ||
221 | + _pvpStartBattleCache = nil | ||
222 | + | ||
223 | + -- 请求上传录像 | ||
224 | + local now = skynet.timex() | ||
225 | + local params = { | ||
226 | + ["roleid"] = roleId, | ||
227 | + ["key"] = "zhaolugame20191016", | ||
228 | + ["time"] = now, | ||
229 | + } | ||
230 | + local status, body = httpc.get(remoteUrl, "/applyvideo?" .. httpGetFormatData(params), {}, {}) | ||
231 | + local video = nil | ||
232 | + if tonumber(status) == 200 then | ||
233 | + local result = json.decode(body) | ||
234 | + video = result.name | ||
235 | + else | ||
236 | + skynet.error("applyvideo", "error", status, body, content) | ||
237 | + end | ||
238 | + | ||
239 | + -- 加入战斗记录 | ||
240 | + redisproxy:pipelining(function(red) | ||
241 | + local dbKey = string.format(RECORD_PVP_COMMON, roleId) | ||
242 | + red:lpush(dbKey, MsgPack.pack({ | ||
243 | + id = match.id, | ||
244 | + t = match.t, | ||
245 | + win = isWin, | ||
246 | + time = now, | ||
247 | + video = video, | ||
248 | + sdelta = myScore - oldmyScore, | ||
249 | + })) | ||
250 | + red:trim(dbKey, 0, 9) | ||
251 | + -- 对方加入战斗记录 | ||
252 | + if match.t == 1 then | ||
253 | + dbKey = string.format(RECORD_PVP_COMMON, match.id) | ||
254 | + red:lpush(dbKey, MsgPack.pack({ | ||
255 | + id = roleId, | ||
256 | + t = 1, | ||
257 | + win = not isWin, | ||
258 | + time = now, | ||
259 | + video = video, | ||
260 | + sdelta = matchScore - oldMatchScore, | ||
261 | + })) | ||
262 | + red:trim(dbKey, 0, 9) | ||
263 | + end | ||
264 | + end) | ||
76 | 265 | ||
266 | + SendPacket(actionCodes.Pvp_endBattleRpc, MsgPack.pack({ | ||
267 | + reward = reward, | ||
268 | + myScore = myScore, | ||
269 | + matchScore = matchScore, | ||
270 | + oldmyScore = oldmyScore, | ||
271 | + oldMatchScore = oldMatchScore, | ||
272 | + myRank = myRank, | ||
273 | + oldMyRank = oldMyRank, | ||
274 | + video = video, | ||
275 | + })) | ||
276 | + return true | ||
277 | +end | ||
278 | + | ||
279 | +function _M.rankListRpc(agent, data) | ||
280 | + local role = agent.role | ||
281 | + local roleId = role:getProperty("id") | ||
282 | + local ptype = msg.ptype or 1 | ||
283 | + | ||
284 | + local response = {} | ||
285 | + if ptype == 1 then -- 普通pvp | ||
286 | + local redret = redisproxy:pipelining(function(red) | ||
287 | + red:zscore(RANK_PVP_COMMON, roleId) | ||
288 | + red:zrevrank(RANK_PVP_COMMON, roleId) | ||
289 | + red:zrevrange(RANK_PVP_COMMON, 0, 99, "WITHSCORES") | ||
290 | + end) | ||
291 | + local score = tonumber(redret[1] or 0) | ||
292 | + local rank = tonumber(redret[2] or -2) + 1 --排名 1 - ... -1 未上榜 没打过pvp | ||
293 | + | ||
294 | + local rankList = {} | ||
295 | + for i = 1, #redret[3], 2 do | ||
296 | + local roleId = tonumber(redret[i]) | ||
297 | + local score = tonumber(redret[i + 1]) | ||
298 | + local online, curInfo = rpcRole(roleId, "friendSInfo") | ||
299 | + curInfo.score = score | ||
300 | + curInfo.roleId = roleId | ||
301 | + table.insert(rankList, curInfo) | ||
302 | + end | ||
303 | + | ||
304 | + response.score = score | ||
305 | + response.rank = rank | ||
306 | + response.rankList = rankList | ||
307 | + | ||
308 | + elseif ptype == 2 then -- 高级pvp | ||
309 | + return | ||
310 | + else | ||
311 | + return | ||
312 | + end | ||
313 | + SendPacket(actionCodes.Pvp_rankListRpc, MsgPack.pack(response)) | ||
314 | + return true | ||
315 | +end | ||
316 | + | ||
317 | +function _M.recordListRpc(agent, data) | ||
318 | + local role = agent.role | ||
319 | + local roleId = role:getProperty("id") | ||
320 | + local ptype = msg.ptype or 1 | ||
321 | + | ||
322 | + local recordList = {} | ||
323 | + local now = skynet.timex() | ||
324 | + if ptype == 1 then -- 普通pvp | ||
325 | + local rlist = redisproxy:lrange(string.format(RECORD_PVP_COMMON, roleId), 0 , 9) | ||
326 | + local tempList = {} | ||
327 | + for _, temp in ipairs(rlist) do | ||
328 | + local one = MsgPack.unpack(temp) | ||
329 | + if now - one.time <= 24 * 3600 then -- 大于一天的弃之 | ||
330 | + table.insert(tempList, one) | ||
331 | + end | ||
332 | + end | ||
333 | + _pvpRecordInfoCache = tempList | ||
334 | + | ||
335 | + recordList = getMatchInfo(tempList, _pvpRecordBattleInfoCache) | ||
336 | + for idx, info in ipairs(recordList) do | ||
337 | + local temp = tempList[idx] | ||
338 | + info.win = temp.win | ||
339 | + info.time = temp.time | ||
340 | + info.video = temp.video | ||
341 | + info.sdelta = temp.sdelta | ||
342 | + end | ||
343 | + | ||
344 | + elseif ptype == 2 then -- 高级pvp | ||
345 | + return | ||
346 | + else | ||
347 | + return | ||
348 | + end | ||
349 | + SendPacket(actionCodes.Pvp_recordListRpc, MsgPack.pack({list = recordList})) | ||
350 | + return true | ||
77 | end | 351 | end |
78 | 352 | ||
79 | return _M | 353 | return _M |
80 | \ No newline at end of file | 354 | \ No newline at end of file |
src/actions/RoleAction.lua
@@ -222,7 +222,11 @@ function _M.loginRpc( agent, data ) | @@ -222,7 +222,11 @@ function _M.loginRpc( agent, data ) | ||
222 | msgs = {} | 222 | msgs = {} |
223 | end | 223 | end |
224 | worldChatResponse.worldChats = msgs | 224 | worldChatResponse.worldChats = msgs |
225 | - worldChatResponse.p2pChats = redisproxy:lrange(CHAT_OFFLINE:format(roleId), 0, -1) | 225 | + local redret = redisproxy:pipelining(function(red) |
226 | + red:lrange(CHAT_OFFLINE:format(roleId), 0, -1) | ||
227 | + red:del(CHAT_OFFLINE:format(roleId)) | ||
228 | + end) | ||
229 | + worldChatResponse.p2pChats = redret[1] | ||
226 | worldChatResponse.chatWave = curWave + 1 | 230 | worldChatResponse.chatWave = curWave + 1 |
227 | curWave = curWave + 1 | 231 | curWave = curWave + 1 |
228 | 232 | ||
@@ -236,6 +240,13 @@ function _M.loginRpc( agent, data ) | @@ -236,6 +240,13 @@ function _M.loginRpc( agent, data ) | ||
236 | agent.role = role | 240 | agent.role = role |
237 | 241 | ||
238 | start_agent_timer() | 242 | start_agent_timer() |
243 | + | ||
244 | + | ||
245 | + -- 玩家登陆做的一些操作 | ||
246 | + role:saveHangTeam() | ||
247 | + role:savePvpCTeam() | ||
248 | + | ||
249 | + | ||
239 | -- role:log("login", { ip = agent.ip, diamond = role:getProperty("diamond"), reDiamond = role:getProperty("reDiamond")}) | 250 | -- role:log("login", { ip = agent.ip, diamond = role:getProperty("diamond"), reDiamond = role:getProperty("reDiamond")}) |
240 | 251 | ||
241 | return true | 252 | return true |
@@ -644,23 +655,36 @@ function _M.chatRpc(agent, data) | @@ -644,23 +655,36 @@ function _M.chatRpc(agent, data) | ||
644 | [2] = function () | 655 | [2] = function () |
645 | local objectId = msg.roleId | 656 | local objectId = msg.roleId |
646 | response.objId = objectId | 657 | response.objId = objectId |
647 | - if 0 == redisproxy:exists(string.format("role:%d", objectId)) then | ||
648 | - result = 1 | 658 | + local redret = redisproxy:pipelining(function(red) |
659 | + red:exists(string.format("role:%d", objectId)) | ||
660 | + red:sismember(FRIEND_BLACK_KEY:format(roleId), objectId) | ||
661 | + red:sismember(FRIEND_BLACK_KEY:format(objectId), roleId) | ||
662 | + end) | ||
663 | + if redret[1] ~= 1 then | ||
664 | + result = 1 | ||
665 | + return | ||
666 | + end | ||
667 | + -- 你把对方拉黑拉黑 | ||
668 | + if redret[2] == 1 then | ||
669 | + result = 2 | ||
649 | return | 670 | return |
650 | end | 671 | end |
672 | + -- 对方把你拉黑 | ||
673 | + local isBlock = redret[3] == 1 | ||
651 | 674 | ||
652 | - -- 若在线,实时发送聊天信息 | ||
653 | - local agent = datacenter.get("agent", objectId) | ||
654 | local bin = MsgPack.pack(response) | 675 | local bin = MsgPack.pack(response) |
655 | - if agent then | ||
656 | - SendPacket(actionCode, bin, agent.fd) | ||
657 | - else | 676 | + if not isBlock then |
658 | redisproxy:pipelining(function(red) | 677 | redisproxy:pipelining(function(red) |
659 | red:rpush(CHAT_OFFLINE:format(objectId), bin) | 678 | red:rpush(CHAT_OFFLINE:format(objectId), bin) |
660 | - red:ltrim(CHAT_OFFLINE:format(objectId), 0, 200) | 679 | + red:ltrim(CHAT_OFFLINE:format(objectId), -200, -1) |
661 | end) | 680 | end) |
681 | + -- 若在线,实时发送聊天信息 | ||
682 | + local agent = datacenter.get("agent", objectId) | ||
683 | + if agent then | ||
684 | + SendPacket(actionCodes.Role_chat, bin, agent.fd) | ||
685 | + end | ||
662 | end | 686 | end |
663 | - SendPacket(actionCode, bin, fromFd) | 687 | + SendPacket(actionCodes.Role_chat, bin) |
664 | end, | 688 | end, |
665 | } | 689 | } |
666 | if not check[cmd] then return end | 690 | if not check[cmd] then return end |
@@ -672,5 +696,11 @@ function _M.chatRpc(agent, data) | @@ -672,5 +696,11 @@ function _M.chatRpc(agent, data) | ||
672 | return true | 696 | return true |
673 | end | 697 | end |
674 | 698 | ||
699 | +function _M.chatGet(agent, data) | ||
700 | + local role = agent.role | ||
701 | + local roleId = role:getProperty("id") | ||
702 | + redisproxy:del(CHAT_OFFLINE:format(roleId)) | ||
703 | + return true | ||
704 | +end | ||
675 | 705 | ||
676 | return _M | 706 | return _M |
677 | \ No newline at end of file | 707 | \ No newline at end of file |
src/config
@@ -7,7 +7,7 @@ bootstrap = "snlua bootstrap" -- The service for bootstrap | @@ -7,7 +7,7 @@ bootstrap = "snlua bootstrap" -- The service for bootstrap | ||
7 | logd = 0 -- 是否开启日志 | 7 | logd = 0 -- 是否开启日志 |
8 | servId = 1 | 8 | servId = 1 |
9 | baseId = 0 | 9 | baseId = 0 |
10 | -codeurl = "127.0.0.1:8686" | 10 | +codeurl = "120.26.43.151:9090" |
11 | 11 | ||
12 | lua_path = root .."skynet/lualib/?.lua;"..root.."src/?.lua;"..root.."tools/?.lua" | 12 | lua_path = root .."skynet/lualib/?.lua;"..root.."src/?.lua;"..root.."tools/?.lua" |
13 | luaservice = root.."skynet/service/?.lua;"..root.."src/?.lua" | 13 | luaservice = root.."skynet/service/?.lua;"..root.."src/?.lua" |
src/models/Daily.lua
@@ -18,6 +18,7 @@ Daily.schema = { | @@ -18,6 +18,7 @@ Daily.schema = { | ||
18 | bonusC = {"table", {}}, -- 奖励副本 次数 {[type] = {c = 0, b = 0}} | 18 | bonusC = {"table", {}}, -- 奖励副本 次数 {[type] = {c = 0, b = 0}} |
19 | giveFP = {"table", {}}, -- 给谁送过心心 | 19 | giveFP = {"table", {}}, -- 给谁送过心心 |
20 | getFP = {"table", {}}, -- 领过谁的心心 | 20 | getFP = {"table", {}}, -- 领过谁的心心 |
21 | + pvpFree = {"number", 0}, -- pvp使用免费次数 | ||
21 | } | 22 | } |
22 | 23 | ||
23 | function Daily:updateProperty(params) | 24 | function Daily:updateProperty(params) |
@@ -65,6 +66,7 @@ function Daily:data() | @@ -65,6 +66,7 @@ function Daily:data() | ||
65 | bonusC = self:getProperty("bonusC"), | 66 | bonusC = self:getProperty("bonusC"), |
66 | giveFP = self:getProperty("giveFP"), | 67 | giveFP = self:getProperty("giveFP"), |
67 | getFP = self:getProperty("getFP"), | 68 | getFP = self:getProperty("getFP"), |
69 | + pvpFree = self:getProperty("pvpFree"), | ||
68 | } | 70 | } |
69 | end | 71 | end |
70 | 72 |
src/models/Role.lua
@@ -142,9 +142,7 @@ function Role:updateProperty(params) | @@ -142,9 +142,7 @@ function Role:updateProperty(params) | ||
142 | end | 142 | end |
143 | 143 | ||
144 | function Role:updateProperties(params, notNotify) | 144 | function Role:updateProperties(params, notNotify) |
145 | - for field, value in pairs(params) do | ||
146 | - self:setProperty(field, value) | ||
147 | - end | 145 | + self:setProperties(params) |
148 | if not notNotify then | 146 | if not notNotify then |
149 | SendPacket(actionCodes.Role_updateProperties, MsgPack.pack(params)) | 147 | SendPacket(actionCodes.Role_updateProperties, MsgPack.pack(params)) |
150 | end | 148 | end |
src/models/RoleCross.lua
@@ -29,20 +29,15 @@ RoleCross.bind = function (Role) | @@ -29,20 +29,15 @@ RoleCross.bind = function (Role) | ||
29 | return self:getProperty("pvpTBVC") ~= 0 and self:getProperty("pvpTBC") or self:getProperty("hangTB") | 29 | return self:getProperty("pvpTBVC") ~= 0 and self:getProperty("pvpTBC") or self:getProperty("hangTB") |
30 | end | 30 | end |
31 | 31 | ||
32 | - -- pvp 战斗数据 | ||
33 | - function Role:pvpCBattleInfo() | ||
34 | - return self:getProperty("pvpTBC") | ||
35 | - end | ||
36 | - | ||
37 | - -- pvp 简略数据 | ||
38 | - function Role:pvpCSInfo() | 32 | + -- pvp 数据 |
33 | + function Role:pvpCInfo() | ||
39 | local info = { | 34 | local info = { |
40 | name = self:getProperty("name"), | 35 | name = self:getProperty("name"), |
41 | level = self:getProperty("level"), | 36 | level = self:getProperty("level"), |
42 | headId = self:getProperty("headId"), | 37 | headId = self:getProperty("headId"), |
43 | - ltime = self:getProperty("ltime"), | ||
44 | battleV = self:getProperty("pvpTBVC"), | 38 | battleV = self:getProperty("pvpTBVC"), |
45 | heros = self:getProperty("pvpTSC"), | 39 | heros = self:getProperty("pvpTSC"), |
40 | + battleInfo = self:getProperty("pvpTBC") | ||
46 | } | 41 | } |
47 | return info | 42 | return info |
48 | end | 43 | end |
@@ -149,18 +144,15 @@ function CMD.friendBattleInfo(roleId) | @@ -149,18 +144,15 @@ function CMD.friendBattleInfo(roleId) | ||
149 | return next(info.pvpTBC) and info.pvpTBC or info.hangTB | 144 | return next(info.pvpTBC) and info.pvpTBC or info.hangTB |
150 | end | 145 | end |
151 | 146 | ||
152 | -function CMD.pvpCBattleInfo(roleId) | ||
153 | - return CMD.getProperty(roleId, "pvpTBC") | ||
154 | -end | ||
155 | - | ||
156 | -function CMD.pvpCSInfo(roleId) | ||
157 | - local info = CMD.getProperties(roleId, {"name", "level", "headId", "pvpTBVC", "pvpTSC"}) | 147 | +function CMD.pvpCInfo(roleId) |
148 | + local info = CMD.getProperties(roleId, {"name", "level", "headId", "pvpTBVC", "pvpTSC", "pvpTBC"}) | ||
158 | return { | 149 | return { |
159 | name = info.name, | 150 | name = info.name, |
160 | level = info.level, | 151 | level = info.level, |
161 | headId = info.headId, | 152 | headId = info.headId, |
162 | battleV = info.pvpTBVC, | 153 | battleV = info.pvpTBVC, |
163 | heros = info.pvpTSC, | 154 | heros = info.pvpTSC, |
155 | + battleInfo = info.pvpTBC | ||
164 | } | 156 | } |
165 | end | 157 | end |
166 | 158 |
src/models/RolePlugin.lua
@@ -843,8 +843,13 @@ function RolePlugin.bind(Role) | @@ -843,8 +843,13 @@ function RolePlugin.bind(Role) | ||
843 | return battleV | 843 | return battleV |
844 | end | 844 | end |
845 | 845 | ||
846 | + -- 不传参数 只修改保存的阵容信息 | ||
846 | function Role:saveHangTeam(team) | 847 | function Role:saveHangTeam(team) |
847 | - self:updateProperty({field = "hangTeam", value = team}) | 848 | + if not team then |
849 | + team = self:getProperty("pvpTSC") | ||
850 | + else | ||
851 | + self:updateProperty({field = "hangTeam", value = team}) | ||
852 | + end | ||
848 | self:setProperties({ | 853 | self:setProperties({ |
849 | hangTS = self:getTeamHerosInfo(team.heros), | 854 | hangTS = self:getTeamHerosInfo(team.heros), |
850 | hangTB = self:getTeamBattleInfo(team), | 855 | hangTB = self:getTeamBattleInfo(team), |
@@ -853,7 +858,11 @@ function RolePlugin.bind(Role) | @@ -853,7 +858,11 @@ function RolePlugin.bind(Role) | ||
853 | end | 858 | end |
854 | 859 | ||
855 | function Role:savePvpCTeam(team) | 860 | function Role:savePvpCTeam(team) |
856 | - self:updateProperty({field = "pvpTSC", value = team}) | 861 | + if not team then |
862 | + team = self:getProperty("pvpTSC") | ||
863 | + else | ||
864 | + self:updateProperty({field = "pvpTSC", value = team}) | ||
865 | + end | ||
857 | self:setProperties({ | 866 | self:setProperties({ |
858 | pvpTSC = self:getTeamHerosInfo(team.heros), | 867 | pvpTSC = self:getTeamHerosInfo(team.heros), |
859 | pvpTBC = self:getTeamBattleInfo(team), | 868 | pvpTBC = self:getTeamBattleInfo(team), |
src/models/RolePvp.lua
@@ -24,15 +24,18 @@ function Role:changePvpScoreCommon(matchId, isWin) | @@ -24,15 +24,18 @@ function Role:changePvpScoreCommon(matchId, isWin) | ||
24 | local isPlayer = matchId ~= -1 | 24 | local isPlayer = matchId ~= -1 |
25 | local redret = redisproxy:pipelining(function(red) | 25 | local redret = redisproxy:pipelining(function(red) |
26 | red:zscore(RANK_PVP_COMMON, roleId) | 26 | red:zscore(RANK_PVP_COMMON, roleId) |
27 | + red:zrevrank(RANK_PVP_COMMON, roleId) | ||
27 | if isPlayer then | 28 | if isPlayer then |
28 | red:zscore(RANK_PVP_COMMON, matchId) | 29 | red:zscore(RANK_PVP_COMMON, matchId) |
29 | end | 30 | end |
30 | end) | 31 | end) |
31 | local myScore = unpackScore(redret[1]) | 32 | local myScore = unpackScore(redret[1]) |
33 | + local oldMyRank = tonumber(redret[2] or -2) + 1 | ||
32 | local matchScore = PVP_RANK_ROBOT_SCORE | 34 | local matchScore = PVP_RANK_ROBOT_SCORE |
33 | if isPlayer then | 35 | if isPlayer then |
34 | - matchScore = unpackScore(redret[2]) | 36 | + matchScore = unpackScore(redret[3]) |
35 | end | 37 | end |
38 | + local oldmyScore, oldMatchScore = myScore, matchScore | ||
36 | 39 | ||
37 | if isWin then | 40 | if isWin then |
38 | local scoreChange = math.ceil(60 / (1 + 10 ^ ((myScore - matchScore) / 400))) | 41 | local scoreChange = math.ceil(60 / (1 + 10 ^ ((myScore - matchScore) / 400))) |
@@ -53,14 +56,21 @@ function Role:changePvpScoreCommon(matchId, isWin) | @@ -53,14 +56,21 @@ function Role:changePvpScoreCommon(matchId, isWin) | ||
53 | if isPlayer then | 56 | if isPlayer then |
54 | red:zadd(RANK_PVP_COMMON, packScore(matchScore, now), matchId) | 57 | red:zadd(RANK_PVP_COMMON, packScore(matchScore, now), matchId) |
55 | end | 58 | end |
59 | + red:zrevrank(RANK_PVP_COMMON, roleId) | ||
56 | end) | 60 | end) |
57 | - self:refreshMatchC(myScore) | ||
58 | - return myScore | 61 | + local myRank |
62 | + if isPlayer then | ||
63 | + myRank = tonumber(redret[3] or -2) + 1 | ||
64 | + else | ||
65 | + myRank = tonumber(redret[2] or -2) + 1 | ||
66 | + end | ||
67 | + self:refreshPvpMatchC(myScore) | ||
68 | + return myScore, matchScore, oldmyScore, oldMatchScore, myRank, oldMyRank | ||
59 | end | 69 | end |
60 | 70 | ||
61 | function Role:refreshPvpMatchC(score) | 71 | function Role:refreshPvpMatchC(score) |
62 | local roleId = self:getProperty("id") | 72 | local roleId = self:getProperty("id") |
63 | - local score = score or redisproxy:zscore(RANK_PVP_COMMON, roleId) | 73 | + local score = score or redisproxy:zscore(RANK_PVP_COMMON, roleId) or 0 |
64 | 74 | ||
65 | local function getPlayers(levels) | 75 | local function getPlayers(levels) |
66 | local redret = redisproxy:pipelining(function(red) | 76 | local redret = redisproxy:pipelining(function(red) |