Преглед изворни кода

添加关卡挑战前提前获取掉落奖励的API.

gwang пре 5 година
родитељ
комит
217c430be1

+ 5 - 0
Gameserver/Amfphp/base/CmdCode.php

@@ -615,6 +615,11 @@ class CmdCode {
     //
     // <editor-fold defaultstate="collapsed" desc="战斗操作码 - 68xx">
 
+    /**
+     * 关卡战斗-预掉落计算
+     */
+    const cmd_fight_arenas_preFight = 6800;
+
     /**
      * 关卡战斗
      */

+ 14 - 0
Gameserver/Amfphp/base/MemKey_User.php

@@ -303,4 +303,18 @@ class MemKey_User {
 
 // </editor-fold>
 //
+    // <editor-fold defaultstate="collapsed" desc="   临时/时效性数据   ">
+    // 
+
+    /**
+     * 玩家临时/时效性数据 - 战场奖励与计算串的MD5值
+     * @param int $zoneid
+     * @param string $uid
+     */
+    public static function temp_arenas_pre_reward_md5_str($zoneid, $uid) {
+        return self::Key_($zoneid, $uid) . (self::bUseShort() ? "-t-aprwd5" : "-temp-arenasPreRewardMD5");
+    }
+
+    // 
+// </editor-fold>
 }

+ 4 - 0
Gameserver/Amfphp/main.php

@@ -151,6 +151,10 @@ function Err($err, $msg = "") {
         Index::$debugMsg .= '内存占用:' . number_format(memory_get_usage() / 1024) . 'kb';  # 内存使用数量(kb)
     }
     CLog::err("发生错误直接中断逻辑执行.");
+    if (is_string($err)) {                                                      # 防御Err中直接输入字符串的货
+        $msg = $err . $msg;
+        $err = ErrCode::err_innerfault;
+    }
     exit(Index::OverPass(Resp::err($err, $msg)));                               # 直接返回错误信息  
 }
 

+ 4 - 0
Gameserver/Amfphp/process/FightProc.php

@@ -19,6 +19,8 @@ class FightProc {
     static function procMain($req) {
         switch ($req->cmd) {
             # 关卡-征战
+            case CmdCode::cmd_fight_arenas_preFight:                            # 6800 关卡挑战 - 预先计算掉落
+                return SweepGatesProc::Arenas_preFight($req);
             case CmdCode::cmd_fight_arenasfight:                                # 6801 挑战关卡
                 return SweepGatesProc::Arenas_Fight($req);
             case CmdCode::cmd_fight_arenassweep:                                # [6802] 扫荡
@@ -32,6 +34,8 @@ class FightProc {
                 return PVPProc::LogChallengeInfo($req);
             case CmdCode::cmd_fight_GetChallengeLog:                            # 6805 拉取挑战记录
                 return PVPProc::GetChagllengeLog($req);
+
+
 // </editor-fold>
             //  <editor-fold defaultstate="collapsed" desc="   PVP 模块 681x ">
             case CmdCode::cmd_fight_pvp_maininfo:                               # [6810] 竞技场 主界面拉取信息

+ 107 - 16
Gameserver/Amfphp/process/FightProc/SweepGatesProc.php

@@ -25,42 +25,98 @@ class SweepGatesProc {
         return null;
     }
 
+    /**
+     * [6800] 关卡战斗 - 预计算掉落
+     * @param req $req
+     */
+    public static function Arenas_preFight($req) {
+        list($gateId, $difficulty) = $req->paras;                               # 提取参数
+
+        my_Assert($gateId > 0, "关卡id非法");
+        echoLine("TTWW");
+        $isFirst = self::isFirstChallenge($req, $gateId, $difficulty);          # 是否首次通关
+
+        $smGate = GameConfig::gate_getItem($gateId);                            # 关卡配置数据
+        $i = $difficulty + 1;                                                   # 按三个难度取不同的值.
+//        $tili = self::getProperty_n($smGate, "tili", $i);                     # 体力暂时未用上
+        $rwdstr = self::getProperty_n($smGate, "reward", $i);
+        $firstPassRewardStr = self::getProperty_n($smGate, 'first_reward', $i);
+        if ($isFirst) {                                                         # 是否首次通关切换奖励内容
+            $rwdstr = $firstPassRewardStr;
+        }
+        $rsarr = explode(';', $rwdstr);
+        my_Assert(count($rsarr) > 0, "关卡奖励数据异常");
+        foreach ($rsarr as $rs) {
+            $rarr = explode(',', $rs);
+            $id = intval($rarr[0]);
+            $num = intval($rarr[1]);
+            $percent = intval(rtrim($rarr[2], '%'));
+            if (CommUtil::randomPercent($percent)) {                            # 投骰子 决定是否本次掉落
+                $dic[] = array($id => $num);                                    # 掉落
+            }
+        }
+        $arr = array();                                                         # 拼接返回字符串
+        foreach ($dic as $item) {
+            foreach ($item as $k => $v) {
+                $arr[] = sprintf("%s,%s", $k, $v);
+            }
+        }
+//        var_dump($isFirst);
+        $_rewards = implode(";", $arr);                                         # 最终奖励字符串
+        $redis_key = MemKey_User::temp_arenas_pre_reward_md5_str($req->zoneid, $req->uid);
+//        var_dump($gateId . $difficulty . $_rewards);
+        $md5 = md5($gateId . $difficulty . $_rewards);
+        $req->mem->set($redis_key, $md5, 86400);                                # 有效期一天,有新的就覆盖
+        return Resp::ok($_rewards);                                             # 返回奖励字符串
+        // 生成奖励串, 写入redis一个md5(过期时间1day)
+        // 奖励串返回客户端
+        //客户端根据奖励串展示奖励
+        // 最后再将奖励串通过挑战接口返回给服务端,
+        // 服务端计算奖励传的md5并与redis中的md5做对比.(这里最好采用字段排序后的字符串或者啥的,避免中间因json序列化/反序列化时改变字符串)
+    }
+
     /**
      * [6801] 关卡挑战1次
      * @param Req $req 
      */
     public static function Arenas_Fight($req) {
-        list($gateId, $difficulty, $star, $TeamObj) = $req->paras;              # 提取参数: 挑战的关卡Id, 关卡难度(0,1,2), 几星, 队伍
+//        Err(ErrCode::err_innerfault, "这里需要修改逻辑, 放一个奖励字段预算接口,战斗开始前就先确定掉落字符串,含红蓝瓶,红蓝瓶无需带出战场/放入背包");
+        list($gateId, $difficulty, $star, $TeamObj, $rewardStr, $_killedbossId) = $req->paras;  # 提取参数: 挑战的关卡Id, 关卡难度(0,1,2), 几星, 队伍, 奖励字符串
         my_Assert($gateId > 0, "关卡id非法");
-        echoLine("TTWW");
+        $md5 = $req->mem->get(MemKey_User::temp_arenas_pre_reward_md5_str($req->zoneid, $req->uid));
+        $_md5 = md5($gateId . $difficulty . $rewardStr);
+        my_Assert($md5 == $_md5, "后台奖励结果匹配失败");
         $isFirst = false;                                                       # 是否首次通关
         self::recordFight($req, $gateId, $difficulty, $star, $isFirst);         # 更新挑战记录 
         $smGate = GameConfig::gate_getItem($gateId);                            # 关卡配置数据
         $i = $difficulty + 1;                                                   # 按三个难度取不同的值.
 //        $tili = self::getProperty_n($smGate, "tili", $i);                     # 体力暂时未用上
-        $rwdstr = self::getProperty_n($smGate, "reward", $i);
-        $firstPassRewardStr = self::getProperty_n($smGate, 'first_reward', $i);
+//        $rwdstr = self::getProperty_n($smGate, "reward", $i);
+//        $firstPassRewardStr = self::getProperty_n($smGate, 'first_reward', $i);
         $gold = self::getProperty_n($smGate, "gold", $i);
         $exp = self::getProperty_n($smGate, "exp", $i);
         $firstExp = self::getProperty_n($smGate, "first_exp", $i);
         $firstHero = self::getProperty_n($smGate, "first_hero", $i);
         $heroExp = self::getProperty_n($smGate, "heroExp", $i);
-        echoLine("TTWW");
+//        echoLine("TTWW");
         if ($isFirst) {                                                         # 是否首次通关切换奖励内容
             $exp = $firstExp;
-            $rwdstr = $firstPassRewardStr;
+//            $rwdstr = $firstPassRewardStr;
             if ($firstHero > 0) {                                               # 首次通关解锁英雄
                 HeroProc::AddHeroWithStar($req, $firstHero, 0);                 # 添加英雄
             }
         }
+//        echoLine("wwTT");
 //        ActiveProc::ChangeTili(-$tili, $req);                                   # 扣减体力变化  
         foreach ($TeamObj as $heroUID) {
             if ($heroUID > 0) {
+                echoLine("$heroUID");
                 HeroProc::HeroAddEXP($heroUID, $heroExp);                       # 增加英雄经验 
             }
         }
-
-        $rewardArr = self::SetRewards($req, $rwdstr);                           # 发通关奖励 
+//        echoLine("wwTT");
+        var_dump($rewardStr);
+        $rewardArr = self::SetRewards($req, $rewardStr);                           # 发通关奖励 
         UserGameModel::Add_Gold($req->userInfo->game, $gold);                   # 发金币
         UserGameModel::Add_Exp($req->userInfo->game, $exp);                     # 给玩家(指挥官)增加经验
 
@@ -94,19 +150,54 @@ class SweepGatesProc {
             if (strlen($r) <= 0) {                                              # 奖励串为空
                 Err(ErrCode::err_innerfault);
             }
-            $percentStr = explode(',', $r)[2];
-            $percent = intval(trim($percentStr, "%"));                          # 剔除%
-            if (CommUtil::randomPercent($percent)) {
-                $err = StoreProc::AddMultiItemInStore($req, $r);                # 发放奖励物品
-                if ($err != ErrCode::ok) {                                      # 出错了
-                    Err($err);
-                }
-                $getedArr[] = substr($r, 0, strrpos($r, ','));                  # 剔除最后一段概率字符串
+//            $percentStr = explode(',', $r)[2];
+//            $percent = intval(trim($percentStr, "%"));                          # 剔除%
+//            if (CommUtil::randomPercent($percent)) {
+            $err = StoreProc::AddMultiItemInStore($req, $r);                    # 发放奖励物品
+            if ($err != ErrCode::ok) {                                          # 出错了
+                Err($err);
             }
+            $getedArr[] = $r;                                                    # 剔除最后一段概率字符串
+//            }
         }
         return $getedArr;
     }
 
+    /**
+     * 更新战斗记录
+     * @param req $req
+     * @param type $gateId
+     * @param type $difficulty
+     * @param type $star
+     */
+    private static function isFirstChallenge($req, $gateId, $difficulty) {
+        $userGates = $req->userInfo->game->gates;
+        if ($difficulty == 0) {                                                 # 按照难度查找
+            $diffCult = $userGates->normal;
+        } else if ($difficulty == 1) {
+            $diffCult = $userGates->hard;
+        } else if ($difficulty == 2) {
+            $diffCult = $userGates->elite;
+        } else {
+            Err(ErrCode::err_arenas_difficulty);                                # 找不到难度类型
+        }
+
+        $typeId = substr($diffCult->highest, 0, 3);                             # 防御: 分类头不对
+        if ($typeId != '503') {
+            $diffCult->highest = 503000;                                        # 设置为关卡第一关
+        }
+        if ($gateId > $diffCult->highest + 1) {                                 # 不能跳关
+            Err(ErrCode::err_arenasgate_indexillegal);
+        }
+
+        $uGate = new UGateModel();                                              # 当前关卡的记录数据
+        if (isset($diffCult->gates->$gateId)) {
+            $uGate = $diffCult->gates->$gateId;
+        }
+
+        return !$uGate->cleared;
+    }
+
     /**
      * 更新战斗记录
      * @param req $req

+ 1 - 2
Gameserver/Amfphp/test.php

@@ -13,6 +13,5 @@ $key = "testzset";
 $key_new = "wanggang";
 //gMem()->zcopy($key, $key_new);
 
-\loyalsoft\EmailProc::SendPvpRankReward_Lastday(1, "B2511C69AF2C7BFB845BB5AE2AB165CF", 1);
-
+echoLine(sprintf("%s:%s", $key, $key_new));
 //var_dump(gMem()->zrevrangebyscore($key_new, 100, 1, $withScore));

+ 1 - 9
Gameserver/nbproject/private/private.xml

@@ -11,14 +11,6 @@
         </file>
     </editor-bookmarks>
     <open-files xmlns="http://www.netbeans.org/ns/projectui-open-files/2">
-        <group>
-            <file>file:/E:/www/ylsj2019/Gameserver/Amfphp/process/PreProc.php</file>
-            <file>file:/E:/www/ylsj2019/Gameserver/Amfphp/process/UserProc.php</file>
-            <file>file:/E:/www/ylsj2019/Gameserver/Amfphp/process/EmailProc.php</file>
-            <file>file:/E:/www/ylsj2019/Gameserver/Amfphp/model/User/EmailModel.php</file>
-            <file>file:/E:/www/ylsj2019/Gameserver/Amfphp/util/DebugHelper.php</file>
-            <file>file:/E:/www/ylsj2019/Gameserver/Amfphp/process/FightProc/PVPProc.php</file>
-            <file>file:/E:/www/ylsj2019/Gameserver/Amfphp/test.php</file>
-        </group>
+        <group/>
     </open-files>
 </project-private>