初始化星铁面板属性,尚未完成,请勿更新至Dev

This commit is contained in:
Kokomi 2023-05-17 03:15:00 +08:00
parent fddcfeef60
commit 9ee1aa28a9
11 changed files with 132 additions and 49 deletions

View File

@ -11,6 +11,10 @@ const elemAlias = {
cryo: '冰,至冬' cryo: '冰,至冬'
} }
const elemAliasSR = {
}
// 元素属性映射, 名称=>elem // 元素属性映射, 名称=>elem
let elemMap = {} let elemMap = {}

View File

@ -158,7 +158,7 @@ export default class AvatarArtis extends Base {
level: ds.level || 1, level: ds.level || 1,
star: ds.star || 5 star: ds.star || 5
} }
console.log('tojson', 'isSr')
if (this.isSr) { if (this.isSr) {
tmp.id = ds.id tmp.id = ds.id
tmp.mainId = ds.main?.id tmp.mainId = ds.main?.id

View File

@ -16,7 +16,6 @@ Data.createDir('/data/UserData', 'root')
Data.createDir('/data/PlayerData/gs', 'root') Data.createDir('/data/PlayerData/gs', 'root')
Data.createDir('/data/PlayerData/sr', 'root') Data.createDir('/data/PlayerData/sr', 'root')
export default class Player extends Base { export default class Player extends Base {
constructor (uid, game = 'gs') { constructor (uid, game = 'gs') {
super() super()

View File

@ -94,8 +94,8 @@ export default class ProfileArtis extends AvatarArtis {
_mark: mark, _mark: mark,
mark: Format.comma(mark, 1), mark: Format.comma(mark, 1),
markClass: ArtisMark.getMarkClass(mark), markClass: ArtisMark.getMarkClass(mark),
main: ArtisMark.formatArti(arti.main, charCfg.attrs, true, this.elem || ''), main: ArtisMark.formatArti(arti.main, charCfg.attrs, true, this.game),
attrs: ArtisMark.formatArti(arti.attrs, charCfg.attrs) attrs: ArtisMark.formatArti(arti.attrs, charCfg.attrs, false, this.game)
} }
} }
}) })

View File

@ -1,17 +1,24 @@
import lodash from 'lodash' import lodash from 'lodash'
import Base from './Base.js' import Base from './Base.js'
const baseAttr = 'atk,def,hp,mastery,recharge,cpct,cdmg,dmg,phy,heal,shield'.split(',') const baseAttr = {
let attrReg = new RegExp(`^(${baseAttr.join('|')})(Base|Plus|Pct|Inc)$`) gs: 'atk,def,hp,mastery,recharge,cpct,cdmg,dmg,phy,heal,shield'.split(','),
sr: 'atk,def,hp,speed,recharge,cpct,cdmg,dmg,heal,stance,effPct,effDmg'.split(',')
}
let attrReg = {
gs: new RegExp(`^(${baseAttr.gs.join('|')})(Base|Plus|Pct|Inc)$`),
sr: new RegExp(`^(${baseAttr.sr.join('|')})(Base|Plus|Pct|Inc)$`)
}
class ProfileAttr extends Base { class ProfileAttr extends Base {
constructor (data = null) { constructor (data = null, game = 'gs') {
super() super()
this.game = game
this.init(data) this.init(data)
} }
static create (data = null) { static create (data = null, game = 'gs') {
return new ProfileAttr(data) return new ProfileAttr(data, game)
} }
init (data) { init (data) {
@ -20,7 +27,7 @@ class ProfileAttr extends Base {
this._base = {} this._base = {}
let attr = this._attr let attr = this._attr
let base = this._base let base = this._base
lodash.forEach(baseAttr, (key) => { lodash.forEach(baseAttr[this.game], (key) => {
attr[key] = { attr[key] = {
base: 0, base: 0,
plus: 0, plus: 0,
@ -42,12 +49,12 @@ class ProfileAttr extends Base {
*/ */
_get (key) { _get (key) {
let attr = this._attr let attr = this._attr
if (baseAttr.includes(key)) { if (baseAttr[this.game].includes(key)) {
let a = attr[key] let a = attr[key]
return a.base * (1 + a.pct / 100) + a.plus return a.base * (1 + a.pct / 100) + a.plus
} }
let testRet = attrReg.exec(key) let testRet = attrReg[this.game].exec(key)
if (testRet && testRet[1] && testRet[2]) { if (testRet && testRet[1] && testRet[2]) {
let key = testRet[1] let key = testRet[1]
let key2 = testRet[2].toLowerCase() let key2 = testRet[2].toLowerCase()
@ -59,13 +66,13 @@ class ProfileAttr extends Base {
* 添加或追加Attr数据 * 添加或追加Attr数据
* @param key * @param key
* @param val * @param val
* @param base * @param isBase
* @returns {boolean} * @returns {boolean}
*/ */
addAttr (key, val, isBase = false) { addAttr (key, val, isBase = false) {
let attr = this._attr let attr = this._attr
let base = this._base let base = this._base
if (baseAttr.includes(key)) { if (baseAttr[this.game].includes(key)) {
attr[key].plus += val * 1 attr[key].plus += val * 1
if (isBase) { if (isBase) {
base[key] = (base[key] || 0) + val * 1 base[key] = (base[key] || 0) + val * 1
@ -73,7 +80,7 @@ class ProfileAttr extends Base {
return true return true
} }
let testRet = attrReg.exec(key) let testRet = attrReg[this.game].exec(key)
if (testRet && testRet[1] && testRet[2]) { if (testRet && testRet[1] && testRet[2]) {
let key = testRet[1] let key = testRet[1]
let key2 = testRet[2].toLowerCase() let key2 = testRet[2].toLowerCase()
@ -109,7 +116,7 @@ class ProfileAttr extends Base {
getAttr () { getAttr () {
let ret = {} let ret = {}
lodash.forEach(baseAttr, (key) => { lodash.forEach(baseAttr[this.game], (key) => {
ret[key] = this[key] ret[key] = this[key]
if (['hp', 'atk', 'def'].includes(key)) { if (['hp', 'atk', 'def'].includes(key)) {
ret[`${key}Base`] = this[`${key}Base`] ret[`${key}Base`] = this[`${key}Base`]

View File

@ -76,7 +76,7 @@ export default class ProfileData extends AvatarData {
} }
calcAttr () { calcAttr () {
this._attr = AttrCalc.create(this, this.game) this._attr = AttrCalc.create(this)
this.attr = this._attr.calc() this.attr = this._attr.calc()
this.base = this._attr.getBase() this.base = this._attr.getBase()
} }

View File

@ -1,6 +0,0 @@
import Character from '../Character.js'
class Character extends Character {
}

View File

@ -1,37 +1,30 @@
import lodash from 'lodash' import lodash from 'lodash'
import { Format } from '#miao' import { Format } from '#miao'
import { attrNameMap, mainAttr, subAttr, attrMap, basicNum, attrPct } from '../../resources/meta/artifact/index.js' import { attrNameMap, mainAttr, subAttr, attrMap } from '../../resources/meta/artifact/index.js'
import {
attrMap as attrMapSR
} from '../../resources/meta-sr/artifact/meta.js'
let ArtisMark = { let ArtisMark = {
// 根据Key获取标题 // 根据Key获取标题
getKeyByTitle (title, dmg = false) { getKeyByTitle (title, dmg = false, game = 'gs') {
if (/元素伤害加成/.test(title) || Format.isElem(title)) { if (/元素伤害加成/.test(title) || Format.isElem(title)) {
let elem = Format.matchElem(title) let elem = Format.matchElem(title)
return dmg ? 'dmg' : elem return dmg ? 'dmg' : elem
} else if (title === '物理伤害加成') { } else if (title === '物理伤害加成') {
return 'phy' return 'phy'
} }
return attrNameMap[title] return (game === 'gs' ? attrNameMap : attrNameMapSR)[title]
}, },
// 根据标题获取Key getKeyTitleMap (game = 'gs') {
getTitleByKey (key) {
// 检查是否是伤害字段
let dmg = Format.elemName(key, '')
if (dmg) {
return `${dmg}伤加成`
}
return attrMap[key].title
},
getKeyTitleMap () {
let ret = {} let ret = {}
lodash.forEach(attrMap, (ds, key) => { lodash.forEach(attrMap, (ds, key) => {
ret[key] = ds.title ret[key] = ds.title
}) })
Format.eachElem((key, name) => { Format.eachElem((key, name) => {
ret[key] = `${name}伤加成` ret[key] = `${name}伤加成`
}) }, game)
return ret return ret
}, },
@ -57,11 +50,11 @@ let ArtisMark = {
/** /**
* 格式化圣遗物词条 * 格式化圣遗物词条
* @param ds * @param ds
* @param markCfg * @param charAttrCfg
* @param isMain * @param isMain
* @returns {{title: *, value: string}|*[]} * @returns {{title: *, value: string}|*[]}
*/ */
formatArti (ds, charAttrCfg = false, isMain = false, elem = '') { formatArti (ds, charAttrCfg = false, isMain = false, game = 'gs') {
// 若为attr数组 // 若为attr数组
if (ds[0] && (ds[0].title || ds[0].key)) { if (ds[0] && (ds[0].title || ds[0].key)) {
let ret = [] let ret = []
@ -71,7 +64,7 @@ let ArtisMark = {
lodash.forEach(ds, (d) => { lodash.forEach(ds, (d) => {
isIdAttr = !d.isCalcNum isIdAttr = !d.isCalcNum
let arti = ArtisMark.formatArti(d, charAttrCfg) let arti = ArtisMark.formatArti(d, charAttrCfg, isMain, game)
ret.push(arti) ret.push(arti)
if (isIdAttr) { if (isIdAttr) {
return true return true
@ -101,8 +94,6 @@ let ArtisMark = {
let title = ds.title || ds[0] let title = ds.title || ds[0]
if (!key) { if (!key) {
key = ArtisMark.getKeyByTitle(title) key = ArtisMark.getKeyByTitle(title)
} else if (!title) {
title = ArtisMark.getTitleByKey(key)
} }
let isDmg = Format.isElem(key) let isDmg = Format.isElem(key)
let val = ds.value || ds[1] let val = ds.value || ds[1]
@ -111,22 +102,23 @@ let ArtisMark = {
if (!key || key === 'undefined') { if (!key || key === 'undefined') {
return {} return {}
} }
let arrCfg = attrMap[isDmg ? 'dmg' : key] let arrCfg = (game === 'gs' ? attrMap : attrMapSR)[isDmg ? 'dmg' : key]
val = Format[arrCfg.format](val, 1) console.log(key, arrCfg)
val = Format[arrCfg?.format || 'comma'](val, 1)
let ret = { let ret = {
key, key,
value: val, value: val,
upNum: ds.upNum || 0, upNum: ds.upNum || 0,
eff: ds.eff || 0 eff: ds.eff || 0
} }
if (!isMain && !ret.upNum) { /* if (!isMain && !ret.upNum) {
let incRet = ArtisMark.getIncNum(key, value) let incRet = ArtisMark.getIncNum(key, value)
ret.upNum = incRet.num ret.upNum = incRet.num
ret.eff = incRet.eff ret.eff = incRet.eff
ret.hasGt = incRet.hasGt ret.hasGt = incRet.hasGt
ret.hasLt = incRet.hasLt ret.hasLt = incRet.hasLt
ret.isCalcNum = true ret.isCalcNum = true
} }*/
if (charAttrCfg) { if (charAttrCfg) {
let mark = charAttrCfg[key]?.mark * num || 0 let mark = charAttrCfg[key]?.mark * num || 0

View File

@ -16,6 +16,14 @@ class AttrCalc {
this.game = profile.game this.game = profile.game
} }
get isGs () {
return this.game === 'gs'
}
get isSr () {
return this.game === 'sr'
}
/** /**
* 静态调用入口 * 静态调用入口
* @param profile * @param profile
@ -25,6 +33,7 @@ class AttrCalc {
return new AttrCalc(profile) return new AttrCalc(profile)
} }
// 只有原神才需要
static calcPromote (lv) { static calcPromote (lv) {
if (lv === 20) { if (lv === 20) {
return 1 return 1
@ -48,11 +57,13 @@ class AttrCalc {
* @returns {{}} * @returns {{}}
*/ */
calc () { calc () {
this.attr = ProfileAttr.create({}) this.attr = ProfileAttr.create({}, this.game)
if (this.profile.isGs) { if (this.isGs) {
this.addAttr('recharge', 100, true) this.addAttr('recharge', 100, true)
this.addAttr('cpct', 5, true) this.addAttr('cpct', 5, true)
this.addAttr('cdmg', 50, true) this.addAttr('cdmg', 50, true)
} else {
} }
this.setCharAttr() this.setCharAttr()
this.setWeaponAttr() this.setWeaponAttr()
@ -74,6 +85,9 @@ class AttrCalc {
* @param affix * @param affix
*/ */
setCharAttr (affix = '') { setCharAttr (affix = '') {
if (this.isGs) {
return
}
let { char, level, promote } = this.profile let { char, level, promote } = this.profile
let metaAttr = char.detail?.attr || {} let metaAttr = char.detail?.attr || {}
let { keys = {}, details = {} } = metaAttr let { keys = {}, details = {} } = metaAttr
@ -125,6 +139,9 @@ class AttrCalc {
* 计算武器属性 * 计算武器属性
*/ */
setWeaponAttr () { setWeaponAttr () {
if (this.isGs) {
return
}
let wData = this.profile?.weapon || {} let wData = this.profile?.weapon || {}
let weapon = Weapon.get(wData?.name || wData?.id, this.game) let weapon = Weapon.get(wData?.name || wData?.id, this.game)
let wCalcRet = weapon.calcAttr(wData.level, wData.promote) let wCalcRet = weapon.calcAttr(wData.level, wData.promote)
@ -155,6 +172,9 @@ class AttrCalc {
* 计算圣遗物属性 * 计算圣遗物属性
*/ */
setArtisAttr () { setArtisAttr () {
if (this.isGs) {
return
}
let artis = this.profile?.artis let artis = this.profile?.artis
// 计算圣遗物词条 // 计算圣遗物词条
artis.forEach((arti) => { artis.forEach((arti) => {

View File

@ -0,0 +1,32 @@
/**
* 旧面板数据迁移
* 去除旧格式控制逻辑复杂度
*/
import fs from 'node:fs'
import lodash from 'lodash'
import { Data } from '#miao'
const DataTrans = {
trans () {
const srcPath = './data/UserData'
let uids = fs.readdirSync(srcPath)
uids = uids.filter((uid) => /\.json/i.test(uid))
lodash.forEach(uids, (uid) => {
let data = Data.readJSON(`/data/UserData/${uid}`)
DataTrans.doTrans(data)
})
},
doTrans (data) {
lodash.forEach(data.avatars, (ds, id) => {
data.avatars[id] = DataTrans.getAvatar(ds)
})
},
getAvatar (data) {
let artisSet = {}
lodash.forEach(data.artis, (ds, idx) => {
})
}
}
export default DataTrans

View File

@ -0,0 +1,35 @@
export const mainAttr = {
3: 'atk,def,hp,cpct,cdmg,heal,effPct'.split(','),
4: 'atk,def,hp,speed'.split(','),
5: 'atk,def,hp,dmg'.split(','),
6: 'atk,def,hp,recharge,stance'.split(',')
}
export const subAttr = 'atk,atkPlus,def,defPlus,hp,hpPlus,speed,cpct,cdmg,effPct,effDef,stance'.split(',')
/**
* 圣遗物词条配置
* @[]value 副词条单次提升值最大档位
* @[]valueMin 副词条单次提升最小值
* @[]calc 伤害计算时变更的字段type
* @[]type 词条的类型 normal:普通字段 plus:小词条
* @[]base 词条类型为小词条时对应的大词条
* @[]text 展示文字
*/
export const attrMap = {
atk: { title: '大攻击', format: 'pct', calc: 'pct' },
atkPlus: { title: '小攻击', format: 'comma' },
def: { title: '大防御', format: 'pct', calc: 'pct' },
defPlus: { title: '小防御', format: 'comma' },
hp: { title: '大生命', format: 'pct', calc: 'pct' },
hpPlus: { title: '小生命', format: 'comma' },
speed: { title: '速度', format: 'comma' },
cpct: { title: '暴击率', format: 'pct', calc: 'plus' },
cdmg: { title: '暴击伤害', format: 'pct', calc: 'plus' },
recharge: { title: '充能效率', format: 'pct', calc: 'plus' },
dmg: { title: '伤害加成', format: 'pct' },
heal: { title: '治疗加成', format: 'pct' },
stance: { title: '击破特攻', format: 'pct' },
effPct: { title: '效果命中', format: 'pct' },
effDef: { title: '效果抵抗', format: 'pct' }
}