本WIKI由复苏的魔女申请于2021年02月02日创建,编辑权限开放,如遇Chrome浏览器登陆后无法编辑点这里 BWIKI反馈留言板
复苏的魔女已于2023年7月31日关服,建设Wiki是希望大家有一个以后可以追忆的地方,请大家多多支持收藏并保持关注。
关服人偶信件可以点击人偶别语辑录查看。

所有玩家在本Wiki游玩请遵守复苏的魔女WIKI免责声明,不会编辑可以点击复苏的魔女WIKI编辑教程学习。

全站通知:

模板:通用抽卡模拟器/文档

来自复苏的魔女WIKI_BWIKI_哔哩哔哩
跳到导航 跳到搜索

介绍

本模板基于JSON数据驱动,动态生成抽卡内容。用户一般仅需要简单配置Json内容即可达到适配游戏内卡池效果。更新日志请看后文。

演示可以查看抽卡模拟器(白夜极光),卡池模拟器(复苏的魔女),意识重构模拟器(卡拉彼丘),注意原始输出内容为表格,因此需要通过css选择器隐藏。

注意本模板的基本逻辑是先判定稀有度,再判定抽卡结果。此外,目前也提供有限池支持(如部分游戏的活动货币池)。

QQ图片20231101002706.pngQQ图片20231101002700.png

JSON入门

使用之前需要用户对JSON的基本语法有一定的了解,可以参考 JSON介绍的语法部分(其他部分不需要)。

为了方便交流,在此约定一些称呼。在此以这个JSON为例,{"A":{"B":"banana"}}。本文将称其为对象A,B将被称为A的属性,banana称为A的B属性值。

这里推荐几个JSON编写工具,以免初学者写错,注意对JSON新手来说这是必须的!!!

https://jsoneditoronline.org/#left=local.culapa&right=local.vosiya

https://www.sojson.com/editor.html

https://tomeko.net/software/JSONedit/bin/JSONedit_0_9_41.zip

第一个和第二个是网站,第三个是windows程序(个人推荐这个),此外也可以使用各种编辑器的在线JSON插件进行编写(比如本文最后一节内容),注意本模板所使用的JSON格式要求比较严格(JS特性)。

模板安装

这个模板的核心部分是MediaWiki:Gacha2.js,安装到wiki合适位置即可,请保留文件头信息。

随后需要创建Data:GachaConfig.jsonData:PoolContentInfo.json两个页面。如果需要改动这两个页面的地址,需要在Gacha2.js代码(就是刚才安装的JS)里进行修改(位于文件头)。

最后是CSS部分,这一部分主要依靠用户自行编写效果,也可以参考现有方案。

Data:PoolContentInfo.json

首先介绍PoolContentInfo。这一部分主要是描述单个抽卡内容的属性信息,用于结果展示。如果计划用MediaWiki的swm查询显示结果,可以不创建这个页面,或者将页面内容写为{}

{
    "0": {
        "名称": "优丽雅",
        "稀有度": "R",
        "影像": "优丽雅.png",
        "标签": "优丽雅",
        "分类": "角色"
    },
    "1": {
        "名称": "未来",
        "稀有度": "SR",
        "影像": "未来.png",
        "标签": "未来",
        "分类": "角色"
    }
}

这一部分外部为JSON对象,内部分为由"1"和"2"两个键值对,他们对应的值都是一个嵌套的JSON 对象,即一个抽卡内容的属性描述信息,注意这里的1和2不需要严格命名,比如后续不需要是3或者4,可以随意指定,仅作为用户识别使用,真正的id依靠的是属性信息中的名称,这个属性值需要是全局唯一的,用于绑定抽卡结果。 属性值其他部分由用户需求自行指定,如示例中稀有度、影像等信息,这些属性会用于卡池中中的设置。

Data:GachaConfig.json

{
	"卡池路径": "https://wiki.biligame.com/fsdmn/index.php?title=Data:${相对路径}&action=raw&ctype=json",
	"卡池列表": {
		"1": {
			"名称": "海中匿影",
			"启用": true,
			"相对路径": "海中匿影.json"
		},
		"2": {
			"名称": "海中匿影+",
			"启用": true,
			"启用时间": "2024/1/27 17:00",
			"相对路径": "海中匿影+.json",
			"引用卡池列表": ["1"]
		}
	}
}

这一部分用于定义卡池列表和路径。卡池路径通过${参数名}索引卡池列表中的1的属性,类似于wiki语法中模板{{{参数|}}}的用法,最终会解析成https://wiki.biligame.com/fsdmn/index.php?title=Data:海中匿影.json&action=raw&ctype=json卡池路径注意fsdmn要改成你wiki的ID。启用可以不写,默认为true。启用时间则如果设置了,则不到时间不开启。注意卡池列表里的名称是实际的显示名称,且最好唯一。

值得注意的是从1.6版本开始支持引用其他卡池的内容来简化书写,如"引用卡池列表": ["1"],这会让卡池补充本身未设定但在其他卡池中设定好的信息,支持嵌套,但是会增加加载时间,注意这里可引用的内容的可获取内容不会重复追加,如被添加引用的卡池中已经有某个角色了,那么即使引用的卡池内容中有,也不会添加第二次,以保持ID序号稳定,此外内容也可以引用结果预设。可以参考白夜极光WIKI进行查看,这将最大程度的分离卡池机制填写与内容部分(见其卡池基准内容(内容)、限时卡池(机制))。

Data:PoolContent.json

PoolContent.json是最复杂的部分,描述卡池具体机制。这个文件的名字取决于GachaConfig.json中相对路径如何定义。这里首先给一个完整演示Data:莲光落舞筵.json(原神卡池模板)。

简单配置项

名称

根据需要编写,推荐全局唯一。

单个元素模板

适用于用PoolContentInfo存储抽卡内容信息的用户,使用wiki模板的用户可以不配置。

用于单个抽卡内容的结果演示,通过${参数名}索引PoolContentInfo中对应内容的属性,类似于wiki语法中模板{{{参数|}}}的法。

简单的可以是

"单个元素模板": "${名称}"

复杂的可以是,可以部分兼容Html语法。

"单个元素模板": "<div class=\"Cellcontainer\"><div class=\"Cellcontainer_bg1 ${稀有度}\" ></div><div class=\"Cellcontainer_bg2 ${稀有度}\" ></div><div class=\"Cellcontainer_bg3 ${稀有度}\" ></div><div class=\"text2  ${稀有度}Name\" >${分类}</div><div class=\"text0  ${稀有度}Name\" >${标签}</div><img class=\"image ${稀有度}Img\" width=50 src=\"https:\/\/wiki.biligame.com\/klbq\/Special:FilePath\/${影像}\"></div>"
Wiki模板和结果连接符

适用于使用wiki模板的用户。用PoolContentInfo存储抽卡内容信息的用户无需配置。

实际上这部分的展示结果是{{抽卡结果|结果1,结果2,结果3....}}

抽卡结果模板可以是这样。arraymaptemplate的用法可以参考帮助:解析函数#arraymaptemplate

{{#arraymaptemplate:{{{1|}}}|人偶图鉴展示|,|,}}

这种情况下最终的展示结果等同于WikiText写法:

{{人偶图鉴展示|结果1}},{{人偶图鉴展示|结果2}}.....

扩展内容这里不再介绍,各位用户可以自行研究。

内容项

这个部分主要是对内容这个配置项做解读,在示例部分中内容对象还包含了四个键值对,键名对应稀有度配置项,按从低到高排列。

基础配置

一个基础的配置可以是。

"R": {
	"可获取内容": [
		"菲",
		"优丽雅",
		"阿维尔",
		["卡丝庇妲",
		"普利姆拉"]
	]
}

可获取内容是一个列表,这表示对应R这个稀有度,可以抽到这些结果,此外这里所使用的是对应在PoolContentInfo里的名称(如果PoolContentInfo未定义或者其中不存在同名对象时会将字符串内容如“优丽雅”直接输出给Wiki模板请求解析)。在1.8版本后允许列表中的元素是列表,如果模拟器发现抽到的元素是列表,会进行等概率再抽取。且如在示例中,卡丝庇妲+普利姆拉将作为整体与其他三个元素平分抽取概率,若在结果预设中可用于标识这个整体的元素序号数为3(从0开始)。

此外还可以看到在传说这个对象里还有特别内容和结果预设两个属性,通常是可以省略的,除非有保底内容或者复杂的抽取结果预设。

特别内容

仅仅用于指定保底重置的目标,不能简单等同于UP内容。

结果预设

结果预设是一个列表,模板会以一维形式依次取出元素作为阶段,穷尽时将本稀有度概率置0。注意当抽到位于特别内容的结果时,如果次数为-1,会重置本阶段,如果大于0会次数-1,除次数外其余重置,且计数器会重置。其中每一阶段可以是:

{
	"次数": -1,
	"当前总抽数": -1,
	"随机取出": false,
	"强制要求清空结果": false,
	"出货时全局重置": false,
    "锁定预设": false,
	"结果组合": [[-1,0]]
}

对象中次数表示该阶段可用的次数,-1表示无限,0时会结束预设阶段,如果有下一阶段会进入下一阶段,未定义时等价于-1。

当前总抽数用于指定在当前阶段内的总抽数阈值,总抽数不大于这个值时该阶段有效,否则进入下一阶段。

随机取出为false时,顺序抽取,true时随机顺序抽取,未定义时等价于false。

强制要求清空结果表示当抽到在特别内容中的结果时需要穷尽结果组合中的结果再重置,true表示穷尽抽取组合,未定义时等价于false。比如预设结果是[1,0],那么强制清空会要求必须全部取完,以适应双保底机制。

出货时全局重置表示一旦触发重置机制,会重置至初始阶段,并重置当前总抽数的计数器,默认为false,true时全部重置。

锁定预设用可视作另一种保底形式,可配合当前总抽数分多阶段使用。当一个稀有度对应的结果阶段被激活且锁定预设为true时,会强制稀有度抽取结果为此稀有度,并使用此结果阶段。默认为false。

结果组合始终应该视作一维列表,但其中的元素允许是数字或者列表,每次抽取一个元素。如果取出来为数值,如在[-1,0]中取值,则会去寻找在可获取内容列表的对应下标所表示的元素,取出0即是可获取内容列表中0下标对应元素,特别的是,-1表示全部不在特别内容列表的结果。对于没有JS基础的用户而言,可以理解为下标为n时,指的是列表里第n+1个元素。当取出来为列表形式,如对于[[-1,0]]按一维列表取出元素,必然取到列表元素[-1,0],列表元素会被立即在其范围内判定结果,因此这里表示1/2概率出可获取内容列表中下标0元素,类似的如果是[-1,-1,0]则表示1/3概率出可获取内容列表中下标0元素。特别的是,[[0,1,1,1,1,1],即1/6概率出可获取内容列表中下标0元素,5/6概率出下标1元素,可以简写为[[0,[1,5]]],这里[1,5]表示给下标1对应元素增加5份权重。

结果预设流程说明和案例参考
  • 首先是假设如果结果是up(在特别内容列表里),那么必然重置当前阶段到初始。在这个基础上,如果是出货时全局重置,那么则会重置到初始阶段。
  • 为了方便起见,即使只是重置当前阶段,也会重置当前总抽数的计数器。
  • 关于次数,每次重置会消耗一次次数,消耗完成后进入下一阶段。
  • 此外次数还有种情况是结果组合的长度变成0,这种情形也会消耗次数来重置,视作阶段重置。

  • 由于默认状态下,从结果组合取出一个结果是顺序的,来方便安排结果,有时也会是随机的,因此允许随机取出
  • 在此基础上,就衍生了强制要求清空结果,这个设置会阻止未取完结果时的重置。
  • 额外的是,有些游戏对于结果的出现有最低抽数限制,因此需要设置当前总抽数用来区分在不同阶段的抽卡结果,最后可能还需要使用锁定预设来设定大保底(比如游戏小保底次数不影响大保底)。

比如明日方舟的规则是150抽之前无保底,仅有50%出率,150抽后必然出UP且重置大保底。结果预设这一部分可以写成(假设明日方舟的特别内容在可获取内容列表中下标为0)。

[{"当前总抽数":150,"结果组合": [[-1, 0]]}, {"出货时全局重置":true,"结果组合": [0]}]

复苏的魔女规则是每次最多80抽触发小保底,总计最多160抽大保底,这意味着前159抽无大保底有小保底,160抽将锁定结果,可以写作(假设复苏的魔女的特别内容在可获取内容列表中下标为0)。

[{"次数":-1,"当前总抽数":159,"结果组合":[[0,-1]]},{"次数":1,"当前总抽数":-1,"出货时全局重置":true,"锁定预设":true,"结果组合":[[1]]}]

原神是一次小保底,一次大保底,可以写作(假设原神的特别内容在可获取内容列表中下标为0)。

[{"结果组合": [[-1, 0],0]}]

白夜极光心愿单机制是50%几率出up,50%几率出其他四位角色,两次小保底后触发大保底,可以写作(假设白夜极光的特别内容在可获取内容列表中下标为0)。

[{"结果组合": [[[0,4],1,2,3,4],[[0,4],1,2,3,4],0]}]

卡拉彼丘机制是无普通保底内容,特殊保底有人物皮肤和枪皮,且前两次会不重复,因此,可以写作(假设卡拉彼丘的特别内容在可获取内容列表中下标为0和1)。

[{"次数":1,"随机取出":true,"强制要求清空结果":true,"结果组合":[0,1]},{"结果组合":[[-1,0]]}]

稀有度项

稀有度主要是配置稀有度概率的地方。以下直接以传说这个属性进行说明。

"传说": {
	"权重": 65,
	"保底抽数": 80,
	"保底更高稀有度": true,
	"权重追加": 0
}
权重

权重需要将游戏内概率按比例写成整数,如游戏概率为10%,90%,权重可以分别写作1,9。如卡拉彼丘小数点后位数最多的是0.65%,即0.0065,那么按权重可以写作65,总权重为10000。考虑到精度损失问题,即使游戏概率小数点后位数比较少,也推荐将比例写大一些,比如10%:90%最好写作1000:9000.

保底抽数

如果没有可以不定义。当给予整数时,会将每一次稀有度保底时都以此作为基准。也可以写成列表形式,如[[10,1],[80,-1]],这表示第一次保底是10抽保底,之后每一次都是80抽。

保底更高稀有度

如果没有可以不定义,默认为false。这个意思是保底时是否包括更高稀有度,如有些游戏保底SR出了SSR会重置SR保底。

权重保持

如果没有可以不定义,默认为false。这个意思是如原神触发4星保底时,5星概率不变,4星增加3星的概率,并不等权重提升。

权重追加

如果没有可以不定义,默认不追加,目前仅支持设置在稀有度中最后一项如本案的传说上(模板默认最后一项为最高稀有度,当然如果不设置权重追加无需顾虑)。注意必须同时设置保底抽数。写为整数时会按固定值增加该配置项的权重,减少其他配置项的权重(目前仅支持最稀有的稀有度)。有些游戏在不同阶段对于权重追加的值不同,因此也可以定义列表,如[[0,70],[10,10]]表示前七十抽不追加权重,后10抽每次增加10个权重,也等同于[0,0,0......10,10,10](但是需要注意这里的抽数之和不能小于保底抽数,比如当前保底是80抽,列表所想要表示的长度也不能小于80抽)。

CSS美化

布局说明

本模板会在页面中生成如下布局,如果需要移动位置请使用JS的DOM操作移动以避免监听器失效。

<div class='Gacha'>
<div class='gacha_select_new'></div>
<div class='gacha_select'>选择卡池:<select id='sl_upRole'  ></select></div>
<table id='table_gacha'border='1' width='100%'><tr><th>次数</th><th>获得</th></tr></table>
<div class='result_gacha_new'></div>
<div id='result_gacha'>统计结果:</div>
<div id='bt_again'><button id='bt_1again' type='button' ><div id='bt_1again_text'>单次抽卡</div></button>
<button id='bt_10again' type='button'  ><div id='bt_10again_text'>十连抽卡</div></button></div>
<div class='loading_gacha'></div>
</div>

不允许新增内容的控件

gacha_selectresult_gachatable_gacha这三个控件分别是选择卡池,显示卡池,以及显示结果统计的作用,前两个更推荐使用display来隐藏,table_gacha则显示本轮抽卡结果,本身是一个表格标签。

这一区域原始情形可以参考卡池模拟器测试版(注意该页面除布局外与本模板不同),因此如果仅需要显示本轮抽卡结果就要通过css隐藏部分控件。这一部分请参考后文基础美化部分。

<table id="table" border="1" width="100%">
<tbody><tr><th>次数</th><th>获得</th></tr>
</tbody><tbody><tr><td>10</td><td class="Bigcontainer">......</td></tr></tbody>
</table>

允许新增内容的控件

gacha_select_newresult_gachaloading_gacha完全允许用户自定义新增加子内容,本身作为空元素存在。bt_again可以看需要改动,如果需要更改抽卡的文字更推荐用css进行。

#bt_10again::after {
	content: "10回召唤";
}
#bt_1again::after {
	content: "1回召唤";
}
#bt_1again_text {
	display: none;
}
#bt_10again_text {
	display: none;
}

基础美化

本模板默认输出表格,如有需要可以通过一些选择器隐藏表格元素。 比如

//不显示表格边框
table_gacha, .Bigcontainer {
	border: none;
}
//不显示所有行和第一列
tbody, td:first-child {
	display: none;
}
//显示最后一行,并进行元素内容控制
tbody:last-child {
	margin-top: 10px;
	margin-bottom: 10px;
	display: flex;
	align-items: center;
	flex-direction: column;
	background-size: 100% 100%;
	max-width: 100%;
	height: 600px;
}

//隐藏标题栏
tbody:nth-child(1) {
	display: none;
}

//单抽时居中元素,注意Cellcontainer为你所使用的模板或者html语言的自定义class或者id名字。
.Bigcontainer>.Cellcontainer:first-child.Cellcontainer:last-child {
	margin: 0 auto;
	top: 75px;
}

其他美化

  • 每个卡池的JSON里最外层还可以配置 "抽卡延时": 6000来延时显示结果。
  • 在玩家点击抽卡时,会给table_gacha加上一个active的ClassName,当切换卡池后移除。
  • 在玩家切换卡池或者第一次加载卡池模拟器时,会给table_gacha加上一个卡池名称如海中匿影的ClassName,当切换卡池后更新。
  • 在玩家抽卡结果显示之前时,会给table_gacha加上一个loading的ClassName,当获得稀有度时,会再加上UR或者R,在结果显示之后或者用户定义的抽卡延时过期后移除。

版本更新历史

  • 0.1
    • 初版卡池模拟器
  • 0.2
    • 拆分内容与抽卡机制。
  • 0.3
    • 拆分卡池列表,一个页面一个Json一个卡池。
  • 0.4
    • #table控件id改为#table_gacha。
    • 修复权重追加计算异常的问题。
    • 追加延时显示和预加载元素图片功能。
    • 其他美化支持。
  • 1.0
    • 新增JS接口支持。
  • 1.1
    • 优化了部分日志输出方式
    • 优化Gacha布局
    • #result控件id改为#result_gacha。
    • 新增wiki模板解析处理resourceLoader和JS模板的支持。
    • GachaAPI扩充postMWParse和createNewTry以及renderTemplate的支持,分别用于请求解析wikitext和指定数量抽卡。
    • 新增gachaContentLoaded事件支持。
  • 1.2
    • 正式支持保底更高稀有度设置false,如SR保底允许SSR出现时不重置SR保底。
    • build557 :允许设置非整数float的权重,如0.02
    • build557 :优化了抽卡性能问题和权重追加的精度损失。

1.3

    • build567 :整理和完善了抽卡机制部分的代码。
    • build582 :修复了使用出货时全局重置会产生错误的情况。
    • build584 : 现在使用postMWParse和Wiki模板时会预载图片了,缓解临时加载图片的延迟感。

1.4

    • build590 :结果预设新增“锁定预设”属性。
    • build642 :抽卡结果事件新增“本轮抽数排序”支持。
    • build642 :扩展了table_gacha的className,提供更多扩展,并优化了加载顺序。
    • build701 :GachaAPI现在提供了当前卡池配置文件的副本,通过GachaAPI.upNow访问。

1.5

    • 修复未指定结果预设的使用次数时,出现up角色无法重置权重计数的问题。

1.6

    • 支持使用在GachaConfig中设置引用卡池信息。
    • 1.6.1 : 支持设置卡池启用时间和关闭时间。
    • 1.6.2 : 完善引用卡池列表支持,支持嵌套引用以及更多内容引用。

1.7

    • 支持注册结果修改函数,如gachaAPI.registerPatch('nameresult',(name)=>{return '南奈尔'}),此外也支持rarityresult来调整稀有度设置,使用pool来动态调整卡池内容。

1.8

    • 允许在稀有度设置中增加“权重保持”属性,开启将在其余稀有度保底时不等比增加权重。
    • 允许在可获取内容中使用嵌套列表,这将有助于分类,注意如果使用引用卡池,包含相同内容的不同列表将视为不同的元素。

特别致谢

在本模板的完成中得到了官方和很多大佬的支持。

Bwiki攻略组大佬们的支持,特别是点点、马小萌、拉菲、胶水、云晓、残天、唯独等大佬们。

Bwiki官方人员特别是环理的支持。

扩展内容

JS接口支持

本模板的加载阶段较晚,因此建议通过合理加载方式和手段判断接口是否可用,且皆建议通过直接使用gachaAPI或者document.gachaAPI来使用。当然也可以查看MediaWiki:Gacha2Pro-Release.js参考。

监听模拟器初始化状态

通过监听gachaContentLoaded事件可以判断模拟器是否已经初始化完。

if (document.gachaContentLoaded != true) {
	document.addEventListener("gachaContentLoaded", test);
} else {
	test();
}

自定义卡池切换

如果你不喜欢默认的卡池切换方式,你可以隐藏控件,并用以下代码强制切换卡池,注意卡池名称错误时不会切换。

gachaAPI.emit("poolchange",卡池名称(基于GachaConfig))

请求抽卡

如你想自定义抽卡数量,可用使用这个代码。注意这个API是异步的。

gachaAPI.createNewTry(100);

抽卡结果更新事件

也许你想自定义结果统计,你可以隐藏默认控件,并通过注册gachaAPI来接收事件。示例如下:

gachaAPI.on("update", function(event) {
  console.log(event); 
});

事件的结构是。

{"合计抽数":160,"本轮抽数":10,"本轮抽数排序":10,"稀有度":"UR","结果名称":"皎"}

WikiText解析增强

有可能你会想使用本模板的Wikitext解析程序来做更多的事情,那么你可以使用

gachaAPI.postMWPars("<center>{{CD播放器|时之塔-Main Menu|时之塔-Main Menu|}}</center>")

这段代码中包含引入JS,本模板的postMWPars支持不重复地引入resourceLoader。注意这个API是异步的。

如果你想完成后放入页面中,可以将其放到异步函数中,如下所示:

async function test() {
	let intext = await gachaAPI.postMWParse(`<center>{{CD播放器|时之塔-Main Menu|时之塔-Main Menu|}}</center>`);
	console(intext);
}

辅助格式化字符串解析

renderTemplate可以用于解析以字符串形式存储的格式化字符串,并从一个给定的对象中读取属性信息。

document.gachaAPI.renderTemplate('{{图标|小|${名称}|${数量}}}', {
					'名称': name,
					'数量': amount
				}));

BwikiJSONEditor

适用于Bwiki平台的JSON在线编辑器,基于JSONEditor定制开发,方便BWIKI上安全编辑和提交JSON页面内容,注意引用了外站的JS和CSS,请谨慎使用!

用户可以通过修改MediaWiki:Gadgets-definition,并安装MediaWiki:Gadget-BwikiJSONEditor.jsMediaWiki:BwikiJSONEditor.js到自己的wiki即可安装。

可以访问本站的JSON页面体验功能。