Like Share Discussion Bookmark Smile

J.J. Huang   2021-10-15   天堂私服 05.核心分析/修改   瀏覽次數:次   DMCA.com Protection Status

天堂私服 | GM指令分析/修改 (金幣)「L1J版」

章節用意

adena的指令,給GM使用給予自己增加金幣,或許可以套用物品上,用於節日活動開啟特定物品贈送金幣。

核心版本

  • L1J-3.80c

分析

在開始分析前,要知道GM指令的指令效果與使用方式,才方便開啟除錯(Debug)進行分析。

效果:產生金幣。
範例:

1
.adena ${金幣數量}
  • 1.分析資料表:

    • 先進入commands表,找到adena的指令。
    • class_nameL1Adena
  • 2.分析程式碼:

    • 透過搜尋L1Adena開啟程式碼。
      1
      src/l1j/server/server/command/executor/L1Adena.java
    • 登入遊戲稍微確認一下目前物品欄內的物品和數量。
    • 使用除錯模式,斷點在38行。
    • 38~39行單純取得指令所帶的金幣數量參數,放於count變數中。
    • 41行可以特別分析一下pc.getInventory()
    • 使用評估表達式Evaluate Expression來分析。
    • 可發現物品欄的物件是L1PcInventory.class
    • _ownerL1PcInstance.class;這個之前就分析過此為客戶端的完整資料。
    • _items可以發現數量與人物物品欄內的數量一致,將其展開並點開其中一個的_item
    • 這邊可以發現_itemL1Weapon,說明是武器的物品,裡面的_name歐西斯匕首
    • 接著在方法storeItem上,按下Ctrl + 左鍵。
    • 會直接跳轉到該方法位置。
      1
      src/l1j/server/server/model/L1PcInventory.java
    • 設定斷點在142繼續分析。
    • 142~148行,是在判斷數量是否大於0、物品資料是否合法存在。
    • 150行,40312物品查看資料庫後可以發現是旅館鑰匙;這一段判斷就先不分析。
    • 160行,是判斷該物品是否是可堆疊的物品。
    • 163~166行,判斷該物品是否已經在物品欄內存在,如果不存在則直接新增,
    • 168行,物品已存在的狀態,會將數量相加,並更新物品資訊。
    • 最後Return該新增的物品L1ItemInstance資訊。

      註:部分程式碼沒有特別分析到,可自行深入分析。

    • 回到L1Adena
    • 42~44行,根據Return回來的L1ItemInstance資訊,可以做一些判斷或是組合回傳回客戶端的數據。

修改

目前指令只有針對自己,希望將此指令修改程可以指定玩家做查詢。

以下是修改後所使用的指令方式:

1
.desc me|${玩家名稱} ${金幣數量}
  • 修改前
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    @Override
    public void execute(L1PcInstance pc, String cmdName, String arg) {
    try {
    StringTokenizer stringtokenizer = new StringTokenizer(arg);
    int count = Integer.parseInt(stringtokenizer.nextToken());

    L1ItemInstance adena = pc.getInventory().storeItem(L1ItemId.ADENA, count);
    if (adena != null) {
    pc.sendPackets(new S_SystemMessage((new StringBuilder()).append(count).append(" 金幣產生。").toString()));
    }
    }
    catch (Exception e) {
    pc.sendPackets(new S_SystemMessage((new StringBuilder()).append("請輸入 .adena 數量||.金幣 數量。").toString()));
    }
    }
  • 修改後
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    @Override
    public void execute(L1PcInstance pc, String cmdName, String arg) {
    try {
    StringTokenizer stringtokenizer = new StringTokenizer(arg);
    String char_name = stringtokenizer.nextToken();
    int count = Integer.parseInt(stringtokenizer.nextToken());

    L1PcInstance target = null;
    if (char_name.equalsIgnoreCase("me")) {
    target = pc;
    }
    else {
    target = L1World.getInstance().getPlayer(char_name);
    }

    if (target == null) {
    pc.sendPackets(new S_ServerMessage(73, char_name));
    return;
    }

    L1ItemInstance adena = target.getInventory().storeItem(L1ItemId.ADENA, count);
    if (adena != null) {
    pc.sendPackets(new S_SystemMessage((new StringBuilder()).append("贈與 ").append(target.getName()).append(" ").append(count).append(" 金幣。").toString()));
    }
    }
    catch (Exception e) {
    pc.sendPackets(new S_SystemMessage((new StringBuilder()).append("請輸入 .adena 玩家名稱|me 數量。").toString()));
    }
    }
  • 修改後儲存,啟動模擬器。
  • 啟動天堂登入遊戲,登入GM帳號與另一個帳號。
  • GM使用指令贈與另一位玩家金幣,該玩家金幣確實已經增加。

結論

  • 程式碼:
    • src/l1j/server/server/command/executor/L1Adena.java
      • 處理客戶端來的GM指令desc的處理。
    • src/l1j/server/server/model/L1PcInventory.java
      • 物品欄的相關資訊與方法。

結語

雖然文章的一些修改,非常簡單,但是建議一定要自己動手做做看。

原創文章真的不易,希望多多支持,感謝。
最後建議回顧一下首章天堂私服 | 天堂私服架設教學,了解其章節目錄。

免責聲明

  • 本部落格文章中皆不提供任何所謂的遊戲「主程式」、「模擬器」、「登入器」…等等相關程式的下載點。
  • 本部落格文章中所見之遊戲主程式和服務器端程序均來自網路發佈,版本歸原作者所有
  • 本部落格文章為研究SQL資料庫與修改JAVA語法使用,非商業用途,亦無做營運事實等任何一切商業行為
  • 本部落格文章內容是為研究學習設計思想和原理為目的,絕沒有故意侵權或惡意抄襲、篡改其他遊戲內容