frida插件教程

站在了巨人的肩膀头上,感谢造轮子的大佬。根据自己的喜好进行了修改 自用Frida

仅供测试使用

换装

装备栏检索全部格子,时装和宠物栏只检索最上面两行

注意:1️⃣时装和宠物换装后外观不会改变,但是属性变化了(不知道有没有刷新外观的接口)2️⃣镶嵌换不了

frida插件教程

 

frida插件教程

函数

部分函数

读取套装

从数据库读取指定套装

/**
* 根据套装编号获取指定换装
*
* 20250102 by Tim
* @param cid
* @param num 套装编号
*/
function get_user_equ_replace(cid, num) {
var suit_record = {};
var selectQuery = `SELECT cid, suit_num, equip_0, equip_1, equip_2, equip_3, equip_4, equip_5,
equip_6, equip_7, equip_8, equip_9, equip_10, equip_11, equip_12, equip_13, equip_14,
equip_15, equip_16, equip_17, equip_18, equip_19, equip_20, equip_21, equip_22
FROM user_equ_replace
WHERE cid = ${cid} AND suit_num = ${num}; `;
if (api_MySQL_exec(mysql_frida, selectQuery)) {
// 获取查询的行数
var rows = MySQL_get_n_rows(mysql_frida);
if (rows > 0) {
// 查询成功,读取数据
MySQL_fetch(mysql_frida); // 获取单行数据
//读取套装
for (let index = 0; index <= 22; index++) {
suit_record[index] = {};
suit_record[index] = JSON.parse(api_MySQL_get_str(mysql_frida, 0 + 2 + index));
// log(index + ‘ ‘ + api_MySQL_get_str(mysql_frida, 0 + 2 + index));
}
return suit_record;
}
}
}

保存套装

保存到数据库

20250103 数据库改为保存 equBackPack.add(7).readU32()

/**
* 保存用户指定套装
*
* 20250102 by Tim
* @param user
* @param suit_num
*/
function saveEquSuit(user, suit_num) {
let userSuit = {};
let inven = CUserCharacInfo_getCurCharacInvenW(user);
let itemSize = 61; // 每个物品的大小
for (let index = 0; index <= 22; index++) {
let equ = CInventory_GetInvenRef(inven, INVENTORY_TYPE.INVENTORY_TYPE_BODY, index);//身上的装备
let data = Memory.readByteArray(equ, itemSize);
let str = arrayBufferToHexStr(data);
let item_id = Inven_Item_getKey(equ);
userSuit[index] = {};
userSuit[index].id = item_id;
userSuit[index].data = str;
// log(index + ‘ ‘ + JSON.stringify(userSuit[index]));
}
let charac_no = CUserCharacInfo_getCurCharacNo(user);
//写入数据库
api_MySQL_exec(mysql_frida, `
INSERT INTO user_equ_replace (
cid, suit_num, equip_0, equip_1, equip_2, equip_3, equip_4, equip_5, equip_6,
equip_7, equip_8, equip_9, equip_10, equip_11, equip_12, equip_13, equip_14,
equip_15, equip_16, equip_17, equip_18, equip_19, equip_20, equip_21, equip_22
) VALUES (
${charac_no}, ${suit_num},
${JSON.stringify(userSuit[0])}‘, ‘${JSON.stringify(userSuit[1])}‘, ‘${JSON.stringify(userSuit[2])}‘, ‘${JSON.stringify(userSuit[3])}‘, ‘${JSON.stringify(userSuit[4])}‘,
${JSON.stringify(userSuit[5])}‘, ‘${JSON.stringify(userSuit[6])}‘, ‘${JSON.stringify(userSuit[7])}‘, ‘${JSON.stringify(userSuit[8])}‘, ‘${JSON.stringify(userSuit[9])}‘,
${JSON.stringify(userSuit[10])}‘, ‘${JSON.stringify(userSuit[11])}‘, ‘${JSON.stringify(userSuit[12])}‘, ‘${JSON.stringify(userSuit[13])}‘, ‘${JSON.stringify(userSuit[14])}‘,
${JSON.stringify(userSuit[15])}‘, ‘${JSON.stringify(userSuit[16])}‘, ‘${JSON.stringify(userSuit[17])}‘, ‘${JSON.stringify(userSuit[18])}‘, ‘${JSON.stringify(userSuit[19])}‘,
${JSON.stringify(userSuit[20])}‘, ‘${JSON.stringify(userSuit[21])}‘, ‘${JSON.stringify(userSuit[22])}
)
ON DUPLICATE KEY UPDATE
equip_0 = ‘${JSON.stringify(userSuit[0])}‘, equip_1 = ‘${JSON.stringify(userSuit[1])}‘, equip_2 = ‘${JSON.stringify(userSuit[2])}‘,
equip_3 = ‘${JSON.stringify(userSuit[3])}‘, equip_4 = ‘${JSON.stringify(userSuit[4])}‘, equip_5 = ‘${JSON.stringify(userSuit[5])}‘,
equip_6 = ‘${JSON.stringify(userSuit[6])}‘, equip_7 = ‘${JSON.stringify(userSuit[7])}‘, equip_8 = ‘${JSON.stringify(userSuit[8])}‘,
equip_9 = ‘${JSON.stringify(userSuit[9])}‘, equip_10 = ‘${JSON.stringify(userSuit[10])}‘, equip_11 = ‘${JSON.stringify(userSuit[11])}‘,
equip_12 = ‘${JSON.stringify(userSuit[12])}‘, equip_13 = ‘${JSON.stringify(userSuit[13])}‘, equip_14 = ‘${JSON.stringify(userSuit[14])}‘,
equip_15 = ‘${JSON.stringify(userSuit[15])}‘, equip_16 = ‘${JSON.stringify(userSuit[16])}‘, equip_17 = ‘${JSON.stringify(userSuit[17])}‘,
equip_18 = ‘${JSON.stringify(userSuit[18])}‘, equip_19 = ‘${JSON.stringify(userSuit[19])}‘, equip_20 = ‘${JSON.stringify(userSuit[20])}‘,
equip_21 = ‘${JSON.stringify(userSuit[21])}‘, equip_22 = ‘${JSON.stringify(userSuit[22])}‘;
`);
api_CUser_SendNotiPacketMessage(user, ‘保存成功!’, 1);
}

换装(新)

通过接口实现换装(未找到换宠物的方法)

/**
* 换装HOOK
* @param a1 User指针
* @param a2 换装类型 0:装备 1:时装
* @param a3 背包slot
* @param a4 穿戴栏slot (10-21)
* @retval 返回值 0代表成功
*/
var CUser_change_equip = new NativeFunction(ptr(0x0865EED2), ‘int’, [‘pointer’, ‘int’, ‘int’, ‘int’], { “abi”: “sysv” });

换装(旧)

/**
* 交换装备
*
* 20250102 by Tim
* @param user
* @param minIndex 栏位格子的开始索引
* @param maxIndex 栏位格子的结束索引
* @param bodyIndex 身上装备的位置索引
* @param suit 保存的换装套装
* @param inventoryType 栏位类型 INVENTORY_TYPE
* @param itemspaceType 更新栏位的类型 ENUM_ITEMSPACE
*/
function exchangeEqu(user, minIndex, maxIndex, bodyIndex, suit, inventoryType, itemspaceType) {
let inven = CUserCharacInfo_getCurCharacInvenW(user);
let itemSize = 61; // 每个物品的大小
//范围内循环匹配
for (let i = minIndex; i <= maxIndex; i++) {
let equBackPack = CInventory_GetInvenRef(inven, inventoryType, i);//背包装备
let dataBackPack = Memory.readByteArray(equBackPack, itemSize);
let item_id = Inven_Item_getKey(equBackPack);//背包装备id
let str = arrayBufferToHexStr(dataBackPack);
//匹配
if (suit.data != str || suit.id != item_id || !suit.id)
continue;
let equ = CInventory_GetInvenRef(inven, INVENTORY_TYPE.INVENTORY_TYPE_BODY, bodyIndex);//身上的装备
let data = Memory.readByteArray(equ, itemSize);
// 交换物品的数据
Memory.writeByteArray(equBackPack, data);
Memory.writeByteArray(equ, dataBackPack);
CUser_SendUpdateItemList(user, 1, inventoryType – 1, i);//更新槽位(0:物品 1:时装 2:宠物 3:身上)
CUser_SendUpdateItemList(user, 1, 3, bodyIndex);//更新身上的
CUser_SendNotiPacket(user, 1, 2, 1);
CUser_send_itemspace(user, itemspaceType);
break;
}
}
/**
* 角色更换指定套装
*
* 20250102 by Tim
* @param user
* @param suit_num 套装编号
*/
function changeEquSuit(user, suit_num) {
let charac_no = CUserCharacInfo_getCurCharacNo(user);
let userSuit = get_user_equ_replace(charac_no, suit_num);//从数据库读取保存的套装
if (!userSuit)
return;
for (const key in userSuit) {
let bodyIndex = parseInt(key);
if (bodyIndex >= 0 && bodyIndex <= 9) {
//检查时装 0~13
exchangeEqu(user, 0, 13, bodyIndex, userSuit[bodyIndex], INVENTORY_TYPE.INVENTORY_TYPE_AVARTAR, ENUM_ITEMSPACE.ENUM_ITEMSPACE_AVATAR);
}
else if (bodyIndex >= 10 && bodyIndex <= 21) {
//检查装备 9-56
exchangeEqu(user, 9, 56, bodyIndex, userSuit[bodyIndex], INVENTORY_TYPE.INVENTORY_TYPE_ITEM, ENUM_ITEMSPACE.ENUM_ITEMSPACE_INVENTORY);
} else if (bodyIndex == 22) {
//检查宠物 0~13
exchangeEqu(user, 0, 13, bodyIndex, userSuit[bodyIndex], INVENTORY_TYPE.INVENTORY_TYPE_CREATURE, ENUM_ITEMSPACE.ENUM_ITEMSPACE_CREATURE);
}
}
}

 

深渊奖励(旧)

退出副本后统计奖励

函数

//20240801 by Tim 添加道具
var CUser_AddItem = new NativeFunction(ptr(0x867B6D4), ‘int’, [‘pointer’, ‘int’, ‘int’, ‘int’, ‘pointer’, ‘int’], {“abi”:“sysv”});
//20240801 by Tim 给角色发道具
function api_CUser_AddItem(user, item_id, item_cnt)
{
var item_space = Memory.alloc(4);
var slot = CUser_AddItem(user, item_id, item_cnt, 6, item_space, 0);
if(slot >= 0)
{
//通知客户端有游戏道具更新
CUser_SendUpdateItemList(user, 1, item_space.readInt(), slot);
}
return;
}
//20240801 by Tim 深渊奖励
var userAddItemCountDic={};
var userDungeonStateDic={};
var awardMessages=[
“『金光三闪闪, 爽!』”,
“『史诗四连爆, 赞!』”,
“『五彩史诗雨, 强!』”,
“『六星连珠现, 牛!』”,
“『史诗满屏飞, 逆天啦!』”];
function hook_history_log2() {
// cHistoryTrace::operator()
Interceptor.attach(ptr(0x854f990), {
onEnter: function(args) {
// 解析日志内容: “18000008”,18000008,D,145636,”nickname”,1,72,8,0,192.168.200.1,192.168.200.1,50963,11, DungeonLeave,”龍人之塔”,0,0,”aabb”,”aabb”,”N/A”,”N/A”,”N/A”
var history_log = args[1].readUtf8String(-1);
var group = history_log.split(“,”);
// 角色信息
var account_id = parseInt(group[1]);
var time_hh_mm_ss = group[3];
var charac_name = group[4];
var charac_no = group[5];
var charac_level = group[6];
var charac_job = group[7];
var charac_growtype = group[8];
var user_web_address = group[9];
var user_peer_ip2 = group[10];
var user_port = group[11];
var channel_index = group[12]; // 当前频道id
// 玩家游戏事件
var game_event = group[13].slice(1); // 删除多余空格
var Dungeon_nameget = group[14];
var item_id = parseInt(group[15]); // 本次操作道具id
var item_cnt = parseInt(group[17]); // 本次操作道具数量
var reason = parseInt(group[18]); // 本次操作原因
if (game_event) {
console.log(‘history_log’, history_log)
}
// 触发游戏事件的角色
var user = GameWorld_find_user_from_world_byaccid(G_GameWorld(), account_id);
if (user.isNull()) {
return;
}
// DungeonLeave离开副本 DungeonEnter进入副本 KillMob杀死怪物 Money+
if(game_event == “DungeonEnter”)
{
//进入副本改变状态
userAddItemCountDic[user] = 0;
userDungeonStateDic[user] = true;
}
else if (game_event == “Item+”) {
var itemData = CDataManager_find_item(G_CDataManager(), item_id);
var needLevel = CItem_getUsableLevel(itemData); // 等级
var inEquRarity = CItem_getRarity(itemData); // 稀有度
// 道具增加: Item+
// reason 4副本内拾取 | inEquRarity 4史诗品级
if (reason == 4 && userDungeonStateDic[user]) {
if (inEquRarity == 4) {
userAddItemCountDic[user]++;
//api_gameWorld_SendNotiPacketMessage(‘玩家[‘ + api_CUserCharacInfo_getCurCharacName(user) + ‘]’ + ‘]在地下城中获得了[‘ + api_CItem_getItemName(item_id) + ‘] x1’, 14);
}
}
} else if (game_event == “DungeonLeave”) {
//计算奖励
userDungeonStateDic[user] = false;
var addItemCount = userAddItemCountDic[user];
userAddItemCountDic[user] = 0;//清空
if(addItemCount <3){
return ;
}
//奖励划分
var message=“”;
if(addItemCount==3)
message=awardMessages[0];
else if (addItemCount==4)
message=awardMessages[1];
else if (addItemCount==5)
message=awardMessages[2];
else if (addItemCount==6)
message=awardMessages[3];
else
message=awardMessages[4];
var goldnum=addItemCount-2;//金币
var cashnum=(addItemCount-3)*200+300;
api_GameWorld_SendNotiPacketMessage(message + ‘ 玩家[‘ + api_CUserCharacInfo_getCurCharacName(user) + ‘]在地下城中获得了【’ + addItemCount + ‘】个史诗, 奖励:\r\n璀璨水晶x’+addItemCount + ” \r\n100万金币x”+goldnum + ” \r\n”+cashnum+“点券”, 14);
api_CUser_AddItem(user,400001000,addItemCount);
api_CUser_AddItem(user,3340,goldnum);
api_recharge_cash_cera(user,cashnum);
}
},
onLeave: function(retval) {}
});
}

调用

// 加载主功能
function start() {
console.log(‘==========================================================frida start df_game_r.js – dp2.9 start ===========================================================’);
hook_history_log2();// 深渊奖励
console.log(‘==========================================================frida start df_game_r.js – dp2.9 end =============================================================’);
}

效果

旧版

frida插件教程

新版
frida插件教程

 

超链接消息 – 多表情

根据初六的dp2插件拓展,支持多个表情显示(没怎么测试)

函数

/**
* 多表情超链接高亮消息
* @param {*} user 用户
* @param {*} strarr 消息数组【消息类型str/其他,消息,rgba,Symbol】
* @param {*} msgtype 广播类型
//0为上方系统公告栏
//1为下方对话框/绿色
//2为下方对话框/蓝色
//3为下方对话框/白色
//5为下方对话框/白色
//6为下方对话框/紫色
//7为下方对话框/绿色
//8为下方对话框/橙色
//9为下方对话框/蓝色
//10为喇叭,但是会乱码
//11为喇叭
//12为喇叭
//13为喇叭
//14为喇叭
* @param {*} type 发给 1(个人)/0(全部)
*/
function api_SendHyperLinkChatMsg_multi_emoji(user, strarr, msgtype, type) {
const bufferSize = 255;
const strptr = Memory.alloc(bufferSize);
let startlen = 0;
let cnt = 0;
// 准备表情符号数据
const emojiBytes1 = [0xc2, 0x80, 0x20];
strptr.add(startlen).writeByteArray(emojiBytes1);
startlen += emojiBytes1.length;
// 处理消息字符串数组
for (const item of strarr) {
const [strtype, msgContent, flags, symbol] = item;
// strptr.add(startlen).writeByteArray([0xc2, 0x80]);
// startlen += 2; // 更新起始长度
// 准备表情符号数据
const emojiBytes = symbol >= 1 ? [0xc2, 0x80, 0x20, 0x1e, 0x20, symbol, 0x1f] : [0xc2, 0x80, 0x20];
strptr.add(startlen).writeByteArray(emojiBytes);
startlen += emojiBytes.length;
const msgstr = (strtype === ‘str’) ? msgContent + : ‘[‘ + api_CItem_GetItemName(parseInt(msgContent)) + ‘]’;
const str_ptr = Memory.allocUtf8String(msgstr);
const str_len = strlen(str_ptr);
strptr.add(startlen).writeByteArray(str_ptr.readByteArray(str_len));
startlen += str_len;
// 检查是否需要添加额外的字节
if (flags[3] === 255) {
strptr.add(startlen).writeByteArray([0xc2, 0x80]);
startlen += 2;
cnt++;
}
}
// 结束字符串并准备数据包
strptr.add(startlen).writeByteArray([0xc2, 0x80]);
startlen += 2;
const packet_guard = api_PacketGuard_PacketGuard();
InterfacePacketBuf_put_header(packet_guard, 0, 370);
InterfacePacketBuf_put_byte(packet_guard, msgtype);
InterfacePacketBuf_put_short(packet_guard, 0);
InterfacePacketBuf_put_byte(packet_guard, 0);
InterfacePacketBuf_put_int(packet_guard, startlen);
InterfacePacketBuf_put_str(packet_guard, strptr, startlen);
InterfacePacketBuf_put_byte(packet_guard, cnt);
// 处理附加信息
for (const item of strarr) {
const [_, msgtype, flags, symbo] = item;
if (flags[3] === 255) {
const RbgInfoptr = Memory.alloc(104);
RbgInfoptr.writeByteArray(flags);
// 处理消息类型
if (typeof msgtype === ‘number’) {
RbgInfoptr.add(0x4).writeU32(msgtype);
const Citem = CDataManager_find_item(G_CDataManager(), msgtype);
if (!CItem_is_stackable(Citem)) {
RbgInfoptr.add(0x8).writeU32(get_rand_int(0));
RbgInfoptr.add(0xe).writeU16(CEquipItem_get_endurance(Citem));
}
}
InterfacePacketBuf_put_binary(packet_guard, RbgInfoptr, 104);
}
}
// 完成数据包
InterfacePacketBuf_finalize(packet_guard, 1);
// 根据类型发送数据包
if (type === 1) {
CUser_SendPacket(user, 1, packet_guard);
}
else {
GameWorld_send_all_with_state(G_GameWorld(), packet_guard, 3); // 只给状态 >= 3 的玩家发送公告
}
// 清理数据包
Destroy_PacketGuard_PacketGuard(packet_guard);
}

调用

api_SendHyperLinkChatMsg_multi_emoji(user, [
[‘str’, ‘玩家’, [150, 255, 30, 255], 1],
[‘str’, ‘『test』’, [0, 136, 255, 255], 3],
[‘str’, ‘爆出’, [150, 255, 30, 255], 32],
[‘item’, 3340, [150, 255, 30, 255], 32],
], 8, 1);

效果

frida插件教程

字符串转高亮超链接数组

将字符串转化成高亮超链接数组。做了一些限制,其中字符串不能太长,会导致异常(高亮超链接函数那块不会修改)

函数

/**
* 将字符串转化成高亮超链接数组
* @param {*} str 字符串
* @param {*} rgba 指定rgba
*/
function hyperLinkChatStrConvertArray(str, rgba) {
// 如果包含 \r \n \t或空字符串,直接返回一个数组。字符串太长也不行
if (str.includes(‘\r’) || str.includes(‘\n’) || str.includes(‘\t’) || str.includes(‘ ‘) || str.length >= 15) {
return [[‘str’, str, rgba]];
}
let result = [];
for (let i = 0; i < str.length; i++) {
// 将字符和rgba值作为一个数组添加到结果数组中
result.push([‘str’, str[i], rgba]);
}
return result;
}

调用

var array = hyperLinkChatStrConvertArray('完成悬赏任务!', [150, 255, 30, 255])

效果

frida插件教程

悬赏功能

悬赏功能为全服共享,以下部分函数,需要搭配 frida_config.json 文件

处理悬赏

/**
* 处理悬赏
*
* //20241222 by Tim
* @param {*} user
* @param {*} target_id 目标id (装备id/副本id)
* @param {*} type 类型(装备/副本)
* @returns
*/
function handle_offer_reward_record(user, target_id, type) {
//20241222 by Tim 添加悬赏检查
if (!global_config[‘offer_reward’][‘isEnable’])
return;
//判断target_id是否存在配置中
var targetlist = global_config[‘offer_reward’][‘target’];
if (!targetlist[ + target_id])
return;
var targetInfo = targetlist[ + target_id];
//检查今天是否已存在记录
var today = get_date();
var record = get_offer_reward_record_byItem(target_id, today, type);
if (record)
return;
var des = ;
var targetArray = [];
//根据类型显示相关
if (type == ‘equ’) {
des = ‘爆出’;
targetArray = [‘item’, target_id, getItemRGBAByItemId(target_id)];
} else {
des = ‘通关’;
targetArray = [‘str’, ‘[‘ + api_CDungeon_getDungeonName(target_id) + ‘]’, [244, 0, 123, 255]];
}
var noticeArray = [
[‘str’, ‘玩家’, [150, 255, 30, 255]],
[‘str’, ‘『’ + api_CUserCharacInfo_getCurCharacName(user) + ‘』’, [0, 136, 255, 255]],
[‘str’, des, [150, 255, 30, 255]],
targetArray,
hyperLinkChatStrConvertArray(‘完成悬赏任务!’, [150, 255, 30, 255])
];
var charac_no = CUserCharacInfo_getCurCharacNo(user);
//20241225 by Tim 添加特殊称号
if (cidSpecialTitle[charac_no])
noticeArray.splice(1, 0, [‘str’, cidSpecialTitle[charac_no][0], cidSpecialTitle[charac_no][1]]);
api_SendHyperLinkChatMsg_emoji(user, noticeArray, 0, 0, 35);
//奖励并记录数据库
var rewards = targetInfo.reward;
for (let i = 0; i < rewards.length; i++) {
const element = rewards[i];
//发送道具到玩家背包
api_CUser_AddItem(user, element[0], element[1]);
}
api_MySQL_exec(mysql_frida, `insert into offer_reward_record (date, cid, targetid, type) values (‘${today}‘,${charac_no},${target_id},’${type}‘);`);
}

处理悬赏称号

/**
* 处理悬赏称号
*
* //20241225 by Tim
*/
function handle_offer_reward_specialTitle(user) {
//20241225 by Tim 添加悬赏结算
var charac_no = CUserCharacInfo_getCurCharacNo(user);
var date = addDaysToDate(-1);
var offer_reward = global_config[‘offer_reward’];
var completeCount = get_offer_reward_record_byUser(charac_no, date);
if (completeCount > 0 && offer_reward[‘titles’][completeCount + ])
cidSpecialTitle[charac_no] = offer_reward[‘titles’][completeCount + ];
else
cidSpecialTitle[charac_no] = ;
}

查询悬赏进度

添加到 hook_characterMessageLog 函数中

if (msg == ‘查询悬赏’) {
//20241222 by Tim
if (!global_config[‘offer_reward’][‘isEnable’]) {
api_CUser_SendNotiPacketMessage(user, ” 暂未开通悬赏!”, 8);
return;
}
var isNull = false;
var today = get_date();
var record_list = get_offer_reward_record(today);
if (!record_list)
isNull = true;
api_CUser_SendNotiPacketMessage(user, “——————今日悬赏—————–“, 8);
var targetlist = global_config[‘offer_reward’][‘target’];
for (const key in targetlist) {
if (!targetlist.hasOwnProperty(key)) continue;
var targetid = parseInt(key);
var status1 = ‘○’;//悬赏状态1
var status2 = ‘『未完成』’;//悬赏状态2
var status2Rgba = [255, 0, 0, 255];
var symbolIndex = 10;
if (!isNull) {
var record = record_list.find(x => x.targetid == targetid);
if (record) {
status1 = ‘●’;
status2 = ‘『’ + api_get_charac_name_by_charac_no(record.cid) + ‘』’;
status2Rgba = [0, 136, 255, 255];
symbolIndex = 31;
}
}
var des = ;//悬赏前缀说明
var targetArray = [];//存放悬赏目标
//区分equ(装备)和dgn(副本)类型
if (targetlist[key].type != ‘equ’) {
des = targetlist[key].des || ‘通关副本’;
targetArray = [‘str’, ‘[‘ + api_CDungeon_getDungeonName(targetid) + ‘]’, [244, 0, 123, 255]]
} else {
des = targetlist[key].des || ‘深渊爆出史诗’;
targetArray = [‘item’, targetid, getItemRGBAByItemId(targetid)]
}
api_SendHyperLinkChatMsg_emoji(user, [
[‘str’, ‘ ‘ + status1 + ‘ ‘, [255, 255, 0, 255]],
hyperLinkChatStrConvertArray(des, [150, 255, 30, 255]),
targetArray,
[‘str’, ‘ – ‘, [255, 255, 0, 255]],
[‘str’, status2, status2Rgba]
], 8, 1, symbolIndex);
}
api_CUser_SendNotiPacketMessage(user, “——————————————“, 8);
}

效果

悬赏任务

frida插件教程

 

称号效果

frida插件教程

悬赏通知

frida插件教程

配置说明

frida插件教程

 

声明:本站文章素材多源于网络,版权归原作者。 声明中文字加粗部分,仅为突出重点信息展示,无其他特殊含义。任何个人或组织,在未经原版权方及本站许可时,禁止复制、盗用、采集、发布本站内容到任何网站、书籍等各类媒体平台。如若本站内容侵犯了原著者的合法权益,可联系我们进行处理。

重要限制:本站素材仅供单机学习交流,请在24小时内删除

给TA仙缘
共{{data.count}}人
人已仙缘
DNF插件教程DNF教学资源

dp插件使用指南及常见问题配置(@9云)

2024-12-28 15:49:40

DNF攻击特效相关DNF教学资源DNF装备道具教程2

目标对象

2024-12-28 17:59:03

动态加载多个广告位

宝子们!这里可是超棒的固定广告位哟!要是你有广告推广的想法,想让更多人看到你的好东西,别犹豫,赶紧联系博主呀,咱们一起把精彩传递出去。

0 条回复 A文章作者 M管理员
    暂无讨论,说说你的看法吧
个人中心
购物车
优惠劵
今日签到
有新私信 私信列表
搜索