在传奇服务端脚本中限制一个账号只能领取一次武器,关键是用账号做记录而不是角色名。用角色名做限制,玩家建小号就能重复领取。正确做法是使用账号列表文件。以下范例基于多数引擎通用的账号列表命令,文件路径设为QuestDiary\武器领取记录.txt。
先创建NPC脚本,放在Envir\Market_Def\目录下,比如武器领取员-3.txt。脚本内容如下:
[@main]
#IF
CHECKACCOUNTLIST QuestDiary\武器领取记录.txt $ACCOUNT
#ACT
MESSAGEBOX 您的账号已经领取过武器,无法再次领取。
CLOSE
BREAK
#SAY
欢迎,这里可以领取一把武器,每个账号只能领取一次。\
请选择你需要的武器:\
<屠龙/@领取屠龙> <开天/@领取开天> <镇天/@领取镇天>\
[@领取屠龙]
#IF
CHECKACCOUNTLIST QuestDiary\武器领取记录.txt $ACCOUNT
#ACT
MESSAGEBOX 您的账号已经领取过武器,无法再次领取。
CLOSE
BREAK
#IF
CHECKLEVELEX > 40
#ACT
GIVE 屠龙 1
ADDACCOUNTLIST QuestDiary\武器领取记录.txt $ACCOUNT
SENDMSG 0 恭喜玩家<$USERNAME>领取了武器屠龙!
CLOSE
#ELSESAY
你的等级不足40级,无法领取。\
[@领取开天]
#IF
CHECKACCOUNTLIST QuestDiary\武器领取记录.txt $ACCOUNT
#ACT
MESSAGEBOX 您的账号已经领取过武器,无法再次领取。
CLOSE
BREAK
#IF
CHECKLEVELEX > 40
#ACT
GIVE 开天 1
ADDACCOUNTLIST QuestDiary\武器领取记录.txt $ACCOUNT
SENDMSG 0 恭喜玩家<$USERNAME>领取了武器开天!
CLOSE
#ELSESAY
你的等级不足40级,无法领取。\
[@领取镇天]
#IF
CHECKACCOUNTLIST QuestDiary\武器领取记录.txt $ACCOUNT
#ACT
MESSAGEBOX 您的账号已经领取过武器,无法再次领取。
CLOSE
BREAK
#IF
CHECKLEVELEX > 40
#ACT
GIVE 镇天 1
ADDACCOUNTLIST QuestDiary\武器领取记录.txt $ACCOUNT
SENDMSG 0 恭喜玩家<$USERNAME>领取了武器镇天!
CLOSE
#ELSESAY
你的等级不足40级,无法领取。\
脚本中$ACCOUNT是引擎内置变量,代表当前玩家账号。CHECKACCOUNTLIST检测账号是否存在于指定文件,ADDACCOUNTLIST将账号追加写入文件。每个领取选项都先检测一次账号,防止玩家通过直接跳转标签绕过主检测。等级条件可自行修改。文件路径QuestDiary\武器领取记录.txt需要确保目录存在,引擎会自动创建文件,如果没有自动创建,手动新建空文件即可。
如果使用的引擎不支持CHECKACCOUNTLIST和ADDACCOUNTLIST,可以用全局变量或文本操作替代。例如用G变量记录领取状态,但全局变量数量有限,不适合大量账号。另一种方法是用个人变量加上账号检测脚本,但实现复杂。最直接的是升级到支持账号列表的引擎版本,或者使用插件命令。部分GOM引擎支持CHECKACCOUNTLIST,GEE引擎则使用CHECKACCOUNTLIST类似命令,注意查询对应引擎的说明书。
为了避免玩家在领取时因为背包满导致物品掉落,可以在领取前用CHECKBAGGAGE命令检测背包空位。增加如下判断:
#IF
CHECKBAGGAGE
#ACT
GIVE 屠龙 1
...
#ELSESAY
背包已满,请清理后再来领取。\
同时,为了防止玩家利用挂机或多人同时点击造成重复领取,可以在领取脚本中加入延迟或锁机制,但账号列表本身是实时写入的,连续点击第二次时第一次已经写入文件,第二次检测就会拒绝,基本可以防止。如果服务器负载高,写入可能有延迟,可以在ADDACCOUNTLIST之后加一个SENDMSG提示领取成功并CLOSE,减少并发。
文件编码问题需要注意。QuestDiary目录下的文本文件通常使用ANSI编码,如果引擎使用UTF-8可能乱码。建议用记事本另存为ANSI。账号列表每行一个账号,不要有多余空格或空行。如果手动编辑,确保没有BOM头。引擎读取时区分大小写,账号变量$ACCOUNT通常是大写,写入也是大写,检查时一致即可。
如果希望更严格地限制,可以同时记录IP或角色名,但账号限制已经足够。有些玩家可能会尝试删除自己账号在文件中的记录,但文件在服务端,玩家无法访问。只要服务器文件权限设置正确,不存在这个问题。
以上脚本示例中,领取后关闭对话框,玩家无法再次打开领取界面,因为主标签会检测并提示已领取。武器名称必须与DB数据库中的物品名完全一致,包括括号、空格等。如果物品不存在,GIVE命令会失败,但账号仍然被记录,导致玩家无法再次领取。因此,在正式使用前,先用GM命令测试物品名称是否正确。
如果需要在领取时扣除元宝或物品,可以在GIVE之前加入GAMEGOLD - 数量或TAKE命令,并确保扣除成功后再写入账号列表。顺序很重要:先扣费,再给物品,最后记录账号。如果扣费后给物品失败,需要回滚扣费,但脚本中不易实现,建议先检测所有条件,确保无误后再执行。
关于引擎兼容性,3K引擎和HERO引擎对账号列表的支持命令可能是CHECKACCOUNTLIST和ADDACCOUNTLIST,具体查看引擎帮助文档。若没有,可以改用CHECKNAMELIST检查角色名,但那就变成角色限制而不是账号限制。账号限制必须用账号相关命令。
完整脚本中还可以加入领取次数变量,比如每个账号只能领取一次,但可以允许选择武器后反悔?不能,一旦领取就记录,无法更换。所以选择前要提示玩家确认。可以在选择武器后加一个确认对话框,例如:
<确认领取屠龙/@确认屠龙> <返回/@main>
但会增加复杂度,可根据需要添加。
测试时,用两个不同账号登录,分别领取,确认第二个账号可以领取。再用同一账号的另一个角色登录,尝试领取,应提示已领取。查看QuestDiary\武器领取记录.txt,里面应该每行一个账号。如果需要重置某个账号的领取状态,用GM权限编辑该文件,删除对应行即可。注意修改文件时服务端最好停止或重新加载NPC脚本,避免缓存问题。
如果使用GEE引擎,账号列表命令可能为CHECKACCOUNTLIST和ADDACCOUNTLIST,但路径写法可能要求相对路径不带QuestDiary前缀,或者使用绝对路径。建议先在测试服验证。另一种通用方案是使用全局变量G,例如G100记录领取过的账号数量,但无法对应具体账号,不能防止重复。也可以用个人变量U,但U变量是账号变量还是角色变量取决于引擎。部分引擎支持U变量为账号变量,即同一账号下所有角色共享。如果引擎支持账号U变量,则可以用CHECKVAR HUMAN U1来判断,但需要确认。多数引擎的U变量是人物变量,换角色会重置,所以不推荐。
账号列表文件是跨角色、跨账号最稳妥的方案。只要引擎支持CHECKACCOUNTLIST和ADDACCOUNTLIST,就可以直接使用。如果引擎不支持,可以考虑用脚本调用外部程序或数据库,但那就超出脚本范围了。
以上脚本可以扩展为领取其他物品,只需修改GIVE后面的物品名和SENDMSG中的提示文字。如果希望一个账号只能领取一次,但可以领取多件不同物品中的一件,则整个账号记录一次即可。如果希望每个物品分别限制一次,则使用不同的记录文件,例如武器领取记录.txt、衣服领取记录.txt等。
最后提醒一点,ADDACCOUNTLIST写入的账号如果包含特殊字符,可能导致列表解析错误。大多数引擎只允许字母数字账号,所以问题不大。如果账号有下划线或点号,通常也支持。写入后可以打开文件检查格式是否正确,每行一个账号,没有逗号或其他分隔符。
脚本中所有命令的大小写不敏感,但变量$ACCOUNT必须大写。文件路径中的反斜杠在脚本中直接写,不要转义。如果引擎要求用双引号包裹路径,则写为"QuestDiary\武器领取记录.txt"。具体看引擎说明。测试时先在一个NPC上测试,确认无误后再复制到其他NPC。
如果玩家领取时掉线,物品已经发放但账号记录可能没有写入,导致玩家可以再次领取。解决方法是先写入账号记录,再发放物品。但这样如果发放失败,玩家无法再次领取。更稳妥的做法是使用事务机制,但脚本不支持。可以在写入账号后立即发放,并在发放前再次检测背包,确保成功。如果发放失败,用GOTO跳转到一个补偿标签,由GM手动处理。但这种情况极少发生,不必过度设计。
以上就是完整的武器领取一账号仅限一次的脚本范例和实现细节。按照这个结构编写,可以避免绝大多数重复领取问题。
传奇脚本经典范例武器领取一账号仅限一次完整代码解析与教程篇
来源:
作者:
点击:

