新增#天赋统计#周三天赋命令,查看角色天赋及技能书

新增`#五星练度统计`、`#四星天赋`命令,指定查看五星或四星角色数据
新增`#刷新天赋`命令,用于在有CK情况下强制刷新本地天赋缓存数据
This commit is contained in:
Kokomi 2023-11-06 03:18:49 +08:00
parent 46af80f874
commit 15f43dce9f
30 changed files with 238 additions and 43 deletions

View File

@ -1,3 +1,9 @@
# 2.5.2
* 新增`#天赋统计`、`#周三天赋`命令,查看角色天赋及技能书
* 新增`#五星练度统计`、`#四星天赋`命令,指定查看五星或四星角色数据
* 新增`#刷新天赋`命令用于在有CK情况下强制刷新本地天赋缓存数据
# 2.5.1
* 面板功能升级

View File

@ -73,18 +73,30 @@ app.reg({
name: '面板练度统计',
fn: ProfileStat.stat,
rule: /^#(面板|喵喵)练度统计$/,
yzRule: /^#*(我的)*(技能|天赋|武器|角色|练度|五|四|5|4|星)+(汇总|统计|列表)(force|五|四|5|4|星)*[ |0-9]*$/,
yzRule: /^#*(我的)*(武器|角色|练度|五|四|5|4|星)+(汇总|统计|列表)(force|五|四|5|4|星)*[ |0-9]*$/,
yzCheck: () => Cfg.get('profileStat', false)
},
talentStat: {
name: '天赋统计',
fn: ProfileStat.stat,
rule: /^#*(我的)*(今日|今天|明日|明天|周.*)?(五|四|5|4|星)?(技能|天赋)+(汇总|统计|列表)?[ |0-9]*$/,
},
avatarList: {
name: '角色查询',
fn: ProfileStat.avatarList,
rule: /^#喵喵(角色|查询)[ |0-9]*$/,
yzRule: /^(#(角色|查询|查询角色|角色查询|人物)[ |0-9]*$)|(^(#*uid|#*UID)\+*[1|2|5-9][0-9]{8}$)|(^#[\+|]*[1|2|5-9][0-9]{8})/,
yzRule: /^(#(五|四|5|4|星)*(角色|查询|查询角色|角色查询|人物)[ |0-9]*$)|(^(#*uid|#*UID)\+*[1|2|5-9][0-9]{8}$)|(^#[\+|]*[1|2|5-9][0-9]{8})/,
yzCheck: () => Cfg.get('avatarList', false)
},
refreshTalent: {
name: '强制刷新天赋',
fn: ProfileStat.refreshTalent,
rule: /^#(强制)?(刷新|更新)(所有|角色)*(天赋|技能)$/
},
profileHelp: {
name: '角色面板帮助',
fn: profileHelp,
@ -133,9 +145,9 @@ app.reg({
rule: /^#(删除全部面板|删除面板|删除面板数据)\s*(\d{9})?$/
},
profileReload:{
profileReload: {
name: '重新加载面板',
fn:ProfileList.reload,
fn: ProfileList.reload,
rule: /^#(星铁|原神)?(加载|重新加载|重载)面板\s*(\d{9})?$/
}
})

View File

@ -1,18 +1,33 @@
import { Common } from '#miao'
import { MysApi, Player, Character } from '#miao.models'
import moment from 'moment'
import lodash from 'lodash'
const ProfileStat = {
async stat (e) {
return ProfileStat.render(e, false)
return ProfileStat.render(e, 'stat')
},
async avatarList (e) {
return ProfileStat.render(e, true)
return ProfileStat.render(e, 'avatar')
},
async refreshTalent (e) {
let mys = await MysApi.init(e)
if (!mys || !mys.uid) return false
let player = Player.create(e)
let refreshCount = await player.refreshTalent('', 2)
if (refreshCount) {
e.reply(`角色天赋更新成功,共${refreshCount}个角色\n你现在可以通过【#练度统计】【#天赋统计】来查看角色信息了...`)
} else {
e.reply('角色天赋未能更新...')
}
},
// 渲染
// isAvatarList true:角色列表 false练度统计
async render (e, isAvatarList = false) {
async render (e, mode = 'stat') {
// 缓存时间,单位小时
let msg = e.msg.replace('#', '').trim()
if (msg === '角色统计' || msg === '武器统计') {
@ -20,7 +35,10 @@ const ProfileStat = {
return false
}
let isTalent = !isAvatarList && /天赋|技能/.test(msg)
if (/天赋|技能/.test(msg)) {
mode = 'talent'
}
let mys = await MysApi.init(e)
if (!mys || !mys.uid) return false
@ -32,9 +50,9 @@ const ProfileStat = {
let avatarRet = await player.refreshAndGetAvatarData({
index: 2,
detail: 1,
talent: isAvatarList ? 0 : 1,
talent: mode === 'avatar' ? 0 : 1,
rank: true,
materials: isTalent,
materials: mode === 'talent',
retType: 'array',
sort: true
})
@ -44,7 +62,36 @@ const ProfileStat = {
return true
}
let faceChar = Character.get(player.face || avatarRet[0]?.id)
let starFilter = 0
if (/(五|四|5|4|)+星/.test(msg)) {
starFilter = /(五|5)+星/.test(msg) ? 5 : 4
}
if (starFilter) {
avatarRet = lodash.filter(avatarRet, ds => ds.star === starFilter)
}
let now = moment(new Date())
if (now.hour() < 4) {
now = now.add(-1, 'days')
}
let week = now.weekday()
if (mode === 'talent') {
let weekRet = /周([1-6]|一|二|三|四|五|六)/.exec(msg)
let weekSel = weekRet?.[1]
if (/(今日|今天)/.test(msg)) {
weekSel = week + 1
} else if (/(明天|明日)/.test(msg)) {
now = now.add(1, 'days')
weekSel = now.weekday() + 1
}
let weekFilter = (weekSel * 1) || ('一二三四五六'.split('').indexOf(weekSel) + 1)
if (weekFilter && weekFilter !== 7) {
avatarRet = lodash.filter(avatarRet, ds => ds?.materials?.talent?.num === ['周一/周四', '周二/周五', '周三/周六'][(weekFilter - 1) % 3])
}
}
let faceChar = Character.get(player.face) || Character.get(avatarRet[0]?.id)
let imgs = faceChar.imgs
let face = {
banner: imgs?.banner,
@ -65,13 +112,17 @@ const ProfileStat = {
goldCount: '金卡总数'
}
return await Common.render(isAvatarList ? 'character/avatar-list' : 'character/profile-stat', {
let tpl = mode === 'avatar' ? 'character/avatar-list' : 'character/profile-stat'
return await Common.render(tpl, {
save_id: uid,
uid,
info,
updateTime: player.getUpdateTime(),
isSelfCookie: e.isSelfCookie,
face,
mode,
week,
avatars: avatarRet
}, { e, scale: 1.4 })
}

View File

@ -105,7 +105,7 @@ let Data = {
return {}
},
async setCacheJSON (key, data, EX = 3600 * 24 * 90) {
async setCacheJSON (key, data, EX = 3600 * 24 * 365) {
await redis.set(key, JSON.stringify(data), { EX })
},

View File

@ -194,7 +194,7 @@ const MysAvatar = {
* @param player
* @param ids
* @param force
* @returns {Promise<boolean>}
* @returns {Promise<number|boolean>}
*/
async refreshTalent (player, ids, force = 0) {
let e = player?.e
@ -204,15 +204,16 @@ const MysAvatar = {
}
force = MysAvatar.checkForce(player, force)
let needReqIds = MysAvatar.getNeedRefreshIds(player, ids, force)
let refreshCount = 0
let failCount = 0
if (needReqIds.length > 0) {
if (needReqIds.length > 8) {
e && e.reply('正在获取角色信息,请稍候...')
}
let failCount = 0
// 并发5请求天赋数据
await Data.asyncPool(5, needReqIds, async (id) => {
let avatar = player.getAvatar(id)
if (avatar) {
if (!avatar) {
return false
}
if (avatar.isMaxTalent || failCount > 5) {
@ -222,11 +223,13 @@ const MysAvatar = {
let ret = await MysAvatar.refreshAvatarTalent(avatar, mys)
if (ret === false) {
failCount++
} else {
refreshCount++
}
})
}
player.save()
return true
return refreshCount
},
async refreshAvatarTalent (avatar, mys) {

View File

@ -9,6 +9,11 @@ body {
.head-box {
margin-top: 0;
}
.item-icon {
width: 30px;
height: 30px;
display: inline-block;
}
#profile-stat {
display: table;
border-collapse: collapse;
@ -357,16 +362,33 @@ body {
font-size: 12px;
margin-right: -60px;
}
.cont .td-material {
padding-left: 5px;
text-align: left !important;
}
.cont .td-weekly.today,
.cont .td-material.today {
background: rgba(255, 212, 132, 0.35);
color: #6f4b00;
}
.cont .td-weekly.not-today,
.cont .td-material.not-today {
opacity: 0.7;
background: rgba(50, 50, 50, 0.2);
}
.cont-notice {
background: rgba(0, 0, 0, 0.7);
font-size: 13px;
text-align: right;
padding: 8px 12px 8px 8px;
text-align: center;
padding: 10px;
}
.cont-notice strong {
color: #d3bc8e;
font-weight: normal;
}
.cont-notice div {
margin: 8px 0 0;
}
.cont-notice span {
margin-left: 5px;
}

View File

@ -22,8 +22,13 @@
<div class="td-talent">A</div>
<div class="td-talent">E</div>
<div class="td-talent">Q</div>
{{if mode === 'talent'}}
<div class="td">周本</div>
<div class="td">天赋书</div>
{{else}}
<div class="td-weapon">武器</div>
<div class="td-artis">圣遗物</div>
{{/if}}
</div>
{{each avatars avatar idx}}
{{set talent = avatar.talent}}
@ -34,8 +39,7 @@
<div class="td td-name star{{avatar.star}}">
<div class="item-banner">
<div class="item-icon char-icon star{{avatar.star}}">
<span class="img"
style="background-image:url({{_res_path}}{{avatar.face}})"></span>
<span class="img" style="background-image:url({{_res_path}}{{avatar.face}})"></span>
</div>
<span class="item-name">{{avatar.abbr||avatar.name}}</span>
@ -48,7 +52,6 @@
<div class="td td-fetter">
<span class="fetter fetter{{['空','荧','旅行者'].includes(avatar.name)?10:avatar.fetter}}"></span>
</div>
{{set talentLvMap = [0,1,1,1,2,2,3,3,3,4,5] }}
{{each tk talentKey}}
{{set curr = (avatar.talent||{})[talentKey] || {original:1,level:'-'} }}
@ -56,15 +59,29 @@
{{curr.level}}
</div>
{{/each}}
{{if mode === 'talent'}}
{{set m = avatar.materials || {} }}
{{set w = {'周一/周四':1,'周二/周五':2, '周三/周六':3}[m.talent?.num] }}
{{set isToday = (week === 6) || (week % 3 + 1 === w)}}
<div class="td td-weekly {{isToday?'today':'not-today'}}">
<div class="item-icon">
<span class="img" style="background-image:url({{_res_path}}{{m.weekly?.icon}})"></span>
</div>
</div>
<div class="td {{isToday?'today':'not-today'}} td-material">
<div class="item-icon">
<span class="img" style="background-image:url({{_res_path}}{{m.talent?.icon}})"></span>
</div>
{{m.talent?.label || '-'}} (周{{['1/4','2/5','3/6'][w-1] || '-'}})
</div>
{{else}}
<div class="td td-weapon star{{weapon.star}}">
{{if weapon?.name}}
<div class="item-banner star{{weapon.star}}">
<span class="level">{{weapon.level}}</span>
<div class="item-icon weapon-icon">
<span class="img"
style="background-image:url({{_res_path}}{{weapon.img}})"></span>
<span class="img" style="background-image:url({{_res_path}}{{weapon.img}})"></span>
</div>
<span class="cons weapon cons-{{weapon.affix+1}} star{{weapon.star}}">{{weapon.affix}}</span>
<span class="item-name">{{weapon.abbr}}</span>
@ -90,8 +107,8 @@
<span class="artis-na">暂无面板数据</span>
{{/if}}
</div>
</div>
{{/if}}
</div>
{{/each}}
</div>
@ -105,6 +122,9 @@
{{/if}}
{{if ut.mys}}
<span>米游社: {{ut.mys}}</span>
<div>
天赋数据每2小时最多更新一次可通过<strong>#刷新天赋</strong>来强制刷新天赋数据需具备有效CK
</div>
{{/if}}
{{else}}
未绑定CK或CK失效信息可能不完全。发送<strong>#体力帮助</strong>查看CK绑定方法发送<strong>#更新面板</strong>更新游戏内角色展柜信息
@ -113,6 +133,4 @@
</div>
</div>
{{/block}}
{{/block}}

View File

@ -12,6 +12,12 @@ body {
margin-top: 0;
}
.item-icon {
width: 30px;
height: 30px;
display: inline-block;
}
#profile-stat {
display: table;
border-collapse: collapse;
@ -89,7 +95,6 @@ body {
}
.td-talent {
color: #d3bc8e;
}
}
@ -399,19 +404,41 @@ body {
font-size: 12px;
margin-right: -60px;
}
.td-material {
padding-left: 5px;
text-align: left !important;
}
.td-weekly, .td-material {
&.today {
background: rgba(255, 212, 132, 0.35);
color: #6f4b00;
}
&.not-today {
opacity: .7;
background: rgba(50, 50, 50, .2);
}
}
}
.cont-notice {
background: rgba(0, 0, 0, .7);
font-size: 13px;
text-align: right;
padding: 8px 12px 8px 8px;
text-align: center;
padding: 10px;
strong {
color: #d3bc8e;
font-weight: normal;
}
div {
margin: 8px 0 0;
}
span {
margin-left: 5px;
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 45 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 85 KiB

After

Width:  |  Height:  |  Size: 109 KiB

View File

@ -41,7 +41,6 @@
"talent": "「公平」的哲学",
"weekly": "原初绿洲之初绽"
},
"eta": 1692151200000,
"talent": {
"a": {
"id": 8431,

Binary file not shown.

After

Width:  |  Height:  |  Size: 43 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 477 KiB

After

Width:  |  Height:  |  Size: 70 KiB

View File

@ -41,7 +41,6 @@
"talent": "「秩序」的哲学",
"weekly": "亘古树海之一瞬"
},
"eta": 1692151200000,
"talent": {
"a": {
"id": 8331,

Binary file not shown.

After

Width:  |  Height:  |  Size: 44 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 392 KiB

After

Width:  |  Height:  |  Size: 64 KiB

View File

@ -0,0 +1,58 @@
export const details = [{
title: 'E众水歌者治疗',
dmg: ({ talent, attr, calc }, { heal }) =>
heal(talent.e['众水的歌者治疗量2'][0] * calc(attr.hp) / 100 + talent.e['众水的歌者治疗量2'][1] * 1)
}, {
title: 'E海薇玛夫人(海马)·伤害',
dmg: ({ talent, attr, calc }, { basic }) => basic(calc(attr.hp) * talent.e['海薇玛夫人伤害'] / 100 * 1.4, 'e')
}, {
title: 'E乌瑟勋爵(章鱼)·伤害',
dmg: ({ talent, attr, calc }, { basic }) => basic(calc(attr.hp) * talent.e['乌瑟勋爵伤害'] / 100 * 1.4, 'e')
}, {
title: 'E谢贝蕾妲小姐(螃蟹)·伤害',
dmgKey: 'e',
dmg: ({ talent, attr, calc }, { basic }) => basic(calc(attr.hp) * talent.e['谢贝蕾妲小姐伤害'] / 100 * 1.4, 'e')
}, {
title: 'E谢贝蕾妲小姐(螃蟹)·蒸发',
dmgKey: 'e',
dmg: ({ talent, attr, calc }, { basic }) => basic(calc(attr.hp) * talent.e['谢贝蕾妲小姐伤害'] / 100 * 1.4, 'e')
}, {
title: 'Q万众狂欢·伤害',
params: { talentQ: true },
dmg: ({ talent, attr, calc, cons }, { basic }) => basic(calc(attr.hp) * (talent.q['技能伤害'] / 100), 'q')
}, {
title: 'Q万众狂欢伤害·蒸发',
params: { talentQ: true },
dmg: ({ talent, attr, calc, cons }, { basic }) => basic(calc(attr.hp) * (talent.q['技能伤害'] / 100), 'q', '蒸发')
}]
export const mainAttr = 'hp,mastery,cpct,cdmg'
export const defDmgIdx = 4
export const buffs = [{
title: '芙宁娜天赋消耗4队友生命值E伤害提升140%'
}, {
title: '天赋E·万众狂欢300层气氛值提升[dmg]%伤害,[heal]%治疗加成',
data: {
dmg: ({ talent }) => talent.q['气氛值转化提升伤害比例'] * 300,
heal: ({ talent }) => talent.q['气氛值转化治疗加成比例'] * 300
}
}, {
title: '芙宁娜被动:基于生命值,提升召唤物伤害[eDmg]%',
data: {
eDmg: ({ calc, attr }) => Math.min(28, (calc(attr.hp)) / 1000 * 0.7)
}
}, {
title: '芙宁娜1命气氛值层数上限提升100',
cons: 1,
data: {
dmg: ({ talent }) => talent.q['气氛值转化提升伤害比例'] * 100,
heal: ({ talent }) => talent.q['气氛值转化治疗加成比例'] * 100
}
}, {
title: '芙宁娜2命万众狂欢持续期间满气氛值提升芙宁娜140%生命值',
cons: 2,
data: {
hpPct: ({ params }) => params.talentQ ? 140 : 0,
}
}, 'vaporize']

Binary file not shown.

After

Width:  |  Height:  |  Size: 43 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 82 KiB

After

Width:  |  Height:  |  Size: 99 KiB

View File

@ -265,8 +265,8 @@
"·提高莱欧斯利的抗打断能力;",
"·生命值高于50%时强化「普通攻击·迅烈倾霜拳」的斥逐拳使其造成的伤害提升命中时莱欧斯利将损失一定的生命值每0.1秒至多因此损失一次生命值;",
"效果将在莱欧斯利退场时解除。",
"<i>「过去的裁罚已成定局,未来的选择犹在掌握。」</i>",
"<i>「若是不愿命运被一时的罪恶吞尽,还请珍重此刻的光阴。」</i>"
"<i>「过去的裁罚已成定局,未来的选择犹在掌握。」",
"「若是不愿命运被一时的罪恶吞尽,还请珍重此刻的光阴。」</i>"
],
"tables": [
{

Binary file not shown.

After

Width:  |  Height:  |  Size: 33 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 54 KiB

View File

@ -41,7 +41,6 @@
"talent": "「正义」的哲学",
"weekly": "生长天地之蕨草"
},
"eta": 1692151200000,
"talent": {
"a": {
"id": 8531,
@ -528,7 +527,7 @@
"处于潜猎模式状态下时,菲米尼的抗打断能力提升,元素战技「浮冰增压」获得如下强化:",
"·冷却时间缩短70%",
"·进行普通攻击时额外提升一阶佩伊刻计的压力阶级并使普通攻击释放的霜寒造成的伤害为原本的200%。",
"效果将在菲米尼退场时解除。",
"<h3>效果将在菲米尼退场时解除。</h3>",
"<i>「现在…不需要什么多余的杂音了。」</i>"
],
"tables": [

Binary file not shown.

After

Width:  |  Height:  |  Size: 48 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 458 KiB

After

Width:  |  Height:  |  Size: 66 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 40 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 74 KiB

View File

@ -2228,25 +2228,25 @@
"star": 1
},
"异色结晶石": {
"id": 112082,
"id": "n112082",
"name": "异色结晶石",
"type": "normal",
"star": 3,
"items": {
"异海凝珠": {
"id": 112080,
"id": "n112080",
"name": "异海凝珠",
"type": "normal",
"star": 1
},
"异海之块": {
"id": 112081,
"id": "n112081",
"name": "异海之块",
"type": "normal",
"star": 2
},
"异色结晶石": {
"id": 112082,
"id": "n112082",
"name": "异色结晶石",
"type": "normal",
"star": 3

Binary file not shown.

Before

Width:  |  Height:  |  Size: 28 KiB

After

Width:  |  Height:  |  Size: 22 KiB

View File

@ -25,5 +25,6 @@ export const alias = {
青雀: '赌神,赌圣,青鹊,摸鱼',
黑塔: '转圈圈',
'丹恒•饮月': '丹恒·饮月,饮月君,饮月,丹恒饮月,龙尊',
'托帕&账账': '托帕,账账'
'托帕&账账': '托帕,账账,总监',
桂乃芬: '小桂子,桂师傅,网红,格尼薇儿'
}