jarlyyn 发表于 2021-9-6 02:16:46

一步一步在北侠做机器人

本帖最后由 jarlyyn 于 2021-10-24 01:54 AM 编辑

周末,带娃之余发现,日常玩的Mud当了……

想起之前已经在http://pkuxkx.net/forum/thread-46312-1-1.html 问过北侠机器人的尺度。

那么便先做一点吧。

https://github.com/hellclient-scripts/pkuxkx.noob



正好边做边说下思路,希望对别人的做机器有所启发。

这次的目标是做一个新人用机器人。


[*]能方便快速的在城市关键点(广场,醉仙楼)和门派掌门之间进行移动
[*]能补充食物,水,存取款,吃喝,修理武器
[*]能做简单的新人任务,抄书之类
[*]能做整备,恢复内力,学习消耗pot, 打坐等
[*]能让用户自定义去学习和学习回来的路径
[*]能提供工具让用户输入路径,进行遍历定位,在用户输入的路径上搜索制定目标,下命令(比如kill)停止等待用户操作

基本是一个全面的机器人,当然,功能上是受不少限制的,但架构还是比较完整的。

机器人会基于我自己的客户端开发。但我的客户端本身就是提供对mushclient的一定程度的兼容,甚至有mcl转换的工具,所以对mush机器人制作应该还是有一定的参考意义的。


进阶篇见

http://pkuxkx.net/forum/thread-46453-1-1.html

jarlyyn 发表于 2021-9-6 02:21:07

要做机器人,先要解决一个问题。什么是机器人。

单单一个触发是不能称之为机器人的。

那么很简单,机器人本质就是一个状态机罢了。

一个核心主程序,根据当前的状态,判断下一步应该进行什么操作,再加上一点意外判断。

恩,就是这么简单。

写Mud机器人是一个没什么难度的事情。当然,这不是说写机器人没意义。而是说,写机器人是一个更工程化的事情。

机器人更多要解决的问题时:


[*]长期稳定性
[*]可维护性
[*]多功能性

所以,是个复杂而不难的事情,非常需要耐心,责任心,毅力。

话题说话回来,写机器人,无非是解决这3个问题

我是谁 我在哪 我要做什么



jarlyyn 发表于 2021-9-6 02:26:51

上一楼说过了,写机器人是一个工程问题。

所以,我们先要订好机器人的架构。

首先,我把机器人分为3层,5个部分,分别是


[*]入口,main.js,用于接受游戏的时间(如断线等),并引入其他代码
[*]框架层,app.js,建立一个全局对象,所以开发将建立于这个对象之上,引入常用模块,统一管理数据,接口,模块,回调,并提供Debug工具。
[*]核心层 core,对于mud本身最核心的信息发送/接受处理,不包含义务逻辑
[*]数据层 info 路径,城市,npc,道具的信息,属于业务支撑部分。在数据层有个最特殊的地方,是和行走/移动紧密集合。
[*]业务层 bussness 实际的功能实现的部分


jarlyyn 发表于 2021-9-6 02:29:44

核心层-数据收集-我是谁

好了,来到代码阶段了。

做机器人,首先就是要做好信息收集,给状态机做决策依据

对于类侠客行mud来说,基本信息一般包括这几类


[*]当前房间信息
[*]用户状态(气血,内力等)
[*]用户信息(门派,存款)
[*]道具
[*]技能

由于我并不玩北侠,唯一的id没有道具和技能,所以今天先把前三块做了。



nny 发表于 2021-9-6 02:31:55

大师级的人物啊!!!

jarlyyn 发表于 2021-9-6 02:37:34

本帖最后由 jarlyyn 于 2021-9-6 02:38 AM 编辑

房间信息

北侠的房间信息是很好处理的,至少比我玩的mud简单。

北侠的房间信息打开是这样的

移动或look后看到

先是房间名 ,特点是顶格,后面有个减号
然后是房间描述
接着是出口信息
最后是房间内的对象,特点是连续的空两个开头的,带括号的文字

那么简单,让我们通过房间名来触发后续其他gourp,以出口信息为第二阶段,到收到第一个不是连续两个空格的信息结束,收集信息

https://github.com/hellclient-sc ... script/core/room.js

有一个特殊点是,虽然我这个机器人为了不踩线应该不使用出口信息,我还是处理了下,排了下序。

使用我app.js 自带的/Debug()函数,在查看房间后,可以看到收集到的信息如下

{
"Room": {
    "Name": "中央广场",
    "Desc": "                           北大街            \n                           |   \n               西大街---中央广场---东大街    \n                           |   \n                           南大街            \n    这里是扬州城的中心,一个很宽阔的广场,地面由青石铺就。一些游手好闲的人在这里溜溜达达,\n经常有艺人在这里表演。中央有一棵大榕树,盘根错节,据传已有千年的树龄,是这座城市的历史见证\n。树干底部有一个很大的洞 (shudong)。你可以看到北边有来自各地的行人来来往往,南面人声鼎沸,\n一派繁华景象,东边不时地传来朗朗的读书声,西边则见不到几个行人,一片肃静。\n    你可以看看(look):baoku,shudong,<air>,<node>。\n    「盛夏」: 起风了,空气中弥漫着燥热的气息。\n",
    "Objs": [
      {
      "ID": "Rong shu",
      "Name": "大榕树"
      }
    ],
    "ObjsMap": {
      "rong shu": "大榕树"
    },
    "Exits": [
      "down",
      "east",
      "north",
      "south",
      "up",
      "west"
    ]
},
"HP": {},
"Score": {}
}
恩,信息还是比较全的。

这是在扬州广场,很明显有个独一无二的对象,大榕树。

之后做行走模块的时候,我应该会通过当前房间是否有Rong shu然判断是否在扬州广场。

jarlyyn 发表于 2021-9-6 02:42:59

用户信息

这个就是脏活……

北侠有一点好,描述清晰

在看到

┌───个人状态────────────┬───────────────────┐


这行话后,打开player_hp触发器组

同时player_hp的

└──────────────────────────────北大侠客行────┘

负责关闭本组

代码在

https://github.com/hellclient-scripts/pkuxkx.noob/blob/cfd483d980938d9a8fb1e3abe0fbb81290637f7b/script/core/player.js

同样的在hp命令使用 /Debug()

得到的信息如下

{
"Room": {},
"HP": {
      "eff_jing": 112,
      "jing": 142,
      "per_jing": 100,
      "eff_jingli": 100,
      "jingli": 100,
      "jiajing": 0,
      "eff_qixue": 121,
      "qixue": 121,
      "per_qixue": 100,
      "eff_neili": 0,
      "neili": 0,
      "jiali": 0,
      "eff_zhenqi": 0,
      "zhengqi": 330,
      "eff_jingqi": null,
      "jingqi": 2929,
      "eff_drink": 0,
      "drink": 330,
      "drink_status": "饥渴",
      "exp": 3,
      "status": "健康"
    },
"Score": {}
}
恩,我这个id饿了真实世界的好几个月了,饿不死人真是好事。



jarlyyn 发表于 2021-9-6 02:47:34

然后就是个人信息,也就是score了

传统来说,侠客行类游戏score虽然没hp那么重要,但要做人性化,特别是新人向的机器的话,也是很重要的。

score里的数据其实有3类

[*]数值型的,通过 -0进行类型转换
[*]字符型的,直接保存
[*]中文数字,这个我用我其他mud的代码,转成了阿拉伯数字

做法也一样

┌───人物详情────────────────────────┬───────┐


开启触发组

触发组里的 └────────────┴────────────┴────北大侠客行────┘


负责关闭触发组

代码也在 https://github.com/hellclient-scripts/pkuxkx.noob/blob/cfd483d980938d9a8fb1e3abe0fbb81290637f7b/script/core/player.js

同样的,/Debug()的信息为

{
      "rank": "武当派第四代弟子",
      "name": "杰林修",
      "id": "Jarlyyn",
      "bl": 23,
      "wx": 17,
      "gg": 21,
      "sf": 19,
      "fy": 15,
      "rm": 18,
      "lx": 30,
      "ds": "?",
      "country": "无国籍",
      "family": "武当派",
      "age": 15,
      "teacher": "谷虚道长",
      "gender": "男性",
      "loyalty": 0,
      "birthday": "戊子年十一月二十一日子时七刻",
      "chushi": "无",
      "marry": "未婚",
      "panshi": "无",
      "kill": 0,
      "job": "未入职",
      "saving": 0,
      "killed": 0,
      "morality": 0,
      "wuxuepoint": 0,
      "deaths": 1,
      "reputation": 0,
      "guojiapoint": 0,
      "shaqi": "正常",
      "wish": 0,
      "shizhan": 0
      }
}





jarlyyn 发表于 2021-9-6 02:50:41

好了,我今天的工作就是这三个部分,其实是比较脏的活了。

最后统一获取到的信息为

{
"Room": {
    "Name": "中央广场",
    "Desc": "                           北大街            \n                           |   \n               西大街---中央广场---东大街    \n                           |   \n                           南大街            \n    这里是扬州城的中心,一个很宽阔的广场,地面由青石铺就。一些游手好闲的人在这里溜溜达达,\n经常有艺人在这里表演。中央有一棵大榕树,盘根错节,据传已有千年的树龄,是这座城市的历史见证\n。树干底部有一个很大的洞 (shudong)。你可以看到北边有来自各地的行人来来往往,南面人声鼎沸,\n一派繁华景象,东边不时地传来朗朗的读书声,西边则见不到几个行人,一片肃静。\n    你可以看看(look):baoku,shudong,<air>,<node>。\n    「盛夏」: 夜幕笼罩著大地。\n",
    "Objs": [
      {
      "ID": "Rong shu",
      "Name": "大榕树"
      }
    ],
    "ObjsMap": {
      "rong shu": "大榕树"
    },
    "Exits": [
      "down",
      "east",
      "north",
      "south",
      "up",
      "west"
    ]
},
"HP": {
    "eff_jing": 112,
    "jing": 142,
    "per_jing": 100,
    "eff_jingli": 100,
    "jingli": 100,
    "jiajing": 0,
    "eff_qixue": 121,
    "qixue": 121,
    "per_qixue": 100,
    "eff_neili": 0,
    "neili": 0,
    "jiali": 0,
    "eff_zhenqi": 0,
    "zhengqi": 330,
    "eff_jingqi": null,
    "jingqi": 2929,
    "eff_drink": 0,
    "drink": 330,
    "drink_status": "饥渴",
    "exp": 3,
    "status": "健康"
},
"Score": {
    "rank": "武当派第四代弟子",
    "name": "杰林修",
    "id": "Jarlyyn",
    "bl": 23,
    "wx": 17,
    "gg": 21,
    "sf": 19,
    "fy": 15,
    "rm": 18,
    "lx": 30,
    "ds": "?",
    "country": "无国籍",
    "family": "武当派",
    "age": 15,
    "teacher": "谷虚道长",
    "gender": "男性",
    "loyalty": 0,
    "birthday": "戊子年十一月二十一日子时七刻",
    "chushi": "无",
    "marry": "未婚",
    "panshi": "无",
    "kill": 0,
    "job": "未入职",
    "saving": 0,
    "killed": 0,
    "morality": 0,
    "wuxuepoint": 0,
    "deaths": 1,
    "reputation": 0,
    "guojiapoint": 0,
    "shaqi": "正常",
    "wish": 0,
    "shizhan": 0
}
}

很明显,这已经够制作很完善的新人机器人了。

如果我会玩pkuxkx,已经能在脑海里构想几十个机器人模块怎么做了。

可惜,我不会,我的id还饿的死去活来的。

所以,我先休息下,明天周一还要上班,剩下的慢慢弄。

jarlyyn 发表于 2021-9-6 02:54:42

然后我所有用到的触发在

https://github.com/hellclient-scripts/pkuxkx.noob/blob/cfd483d980938d9a8fb1e3abe0fbb81290637f7b/script.toml

这个相当于mush的mcl文件,只是mush是xml文件,我用的是toml。

格式,参数基本是完全一致,但我的事件和mush有所不同。我是b/s架构,没有on_focus系列,多了一个on_assist(我有个类似windows 开始按钮的工具)和broadcast(跨游戏广播)时间


触发和脚本最大的区别是

我使用的是UTF-8,不是gbk的,中文不是固定2字节的,还是每个中文/英文长度都是1。

原因么,都2021,实在不想用gbk了。


页: [1] 2 3 4 5 6 7 8 9
查看完整版本: 一步一步在北侠做机器人