feat: configure dual game king rankings
This commit is contained in:
parent
36999097d8
commit
cc455ccfb8
@ -38,7 +38,8 @@
|
|||||||
</el-table-column>
|
</el-table-column>
|
||||||
<el-table-column label="抽奖门槛" min-width="125" align="right">
|
<el-table-column label="抽奖门槛" min-width="125" align="right">
|
||||||
<template slot-scope="scope">
|
<template slot-scope="scope">
|
||||||
每 {{ formatNumber(scope.row.coinPerDraw) }} 金币
|
<div>每 {{ formatNumber(scope.row.coinPerDraw) }} 金币</div>
|
||||||
|
<div class="secondary-text">每日最多 {{ scope.row.dailyChanceLimit }} 次</div>
|
||||||
</template>
|
</template>
|
||||||
</el-table-column>
|
</el-table-column>
|
||||||
<el-table-column label="状态" min-width="130" align="center">
|
<el-table-column label="状态" min-width="130" align="center">
|
||||||
@ -157,6 +158,20 @@
|
|||||||
/>
|
/>
|
||||||
</el-form-item>
|
</el-form-item>
|
||||||
</el-col>
|
</el-col>
|
||||||
|
<el-col :span="12">
|
||||||
|
<el-form-item label="每日最多获次数" prop="dailyChanceLimit">
|
||||||
|
<el-input-number
|
||||||
|
v-model="form.dailyChanceLimit"
|
||||||
|
:min="1"
|
||||||
|
:max="10000"
|
||||||
|
:precision="0"
|
||||||
|
controls-position="right"
|
||||||
|
style="width: 100%"
|
||||||
|
:disabled="startedLocked"
|
||||||
|
/>
|
||||||
|
<div class="form-help">按活动时区自然日封顶;超出部分仍计入两个榜单,但不再增加抽奖次数。</div>
|
||||||
|
</el-form-item>
|
||||||
|
</el-col>
|
||||||
<el-col :span="12">
|
<el-col :span="12">
|
||||||
<el-form-item label="结算等待(分钟)" prop="settlementDelayMinutes">
|
<el-form-item label="结算等待(分钟)" prop="settlementDelayMinutes">
|
||||||
<el-input-number
|
<el-input-number
|
||||||
@ -172,8 +187,8 @@
|
|||||||
</el-form-item>
|
</el-form-item>
|
||||||
</el-col>
|
</el-col>
|
||||||
<el-col :span="12">
|
<el-col :span="12">
|
||||||
<el-form-item label="排行口径">
|
<el-form-item label="榜单配置">
|
||||||
<el-input value="消费金币榜(TYCOON)" disabled />
|
<el-input value="消耗榜(TYCOON)+ 中奖入账榜(VICTORIOUS)" disabled />
|
||||||
</el-form-item>
|
</el-form-item>
|
||||||
</el-col>
|
</el-col>
|
||||||
<el-col :span="12">
|
<el-col :span="12">
|
||||||
@ -245,14 +260,21 @@
|
|||||||
</el-table>
|
</el-table>
|
||||||
<div class="weight-summary">当前总权重:{{ totalPrizeWeight }}</div>
|
<div class="weight-summary">当前总权重:{{ totalPrizeWeight }}</div>
|
||||||
|
|
||||||
<div class="section-title">排行榜结算奖励(固定六档)</div>
|
<div class="section-title">排行榜结算奖励(每个榜单固定六档)</div>
|
||||||
<el-alert
|
<el-alert
|
||||||
type="warning"
|
type="warning"
|
||||||
:closable="false"
|
:closable="false"
|
||||||
show-icon
|
show-icon
|
||||||
title="名次范围不可增删或修改;活动结束后按最终消费榜快照结算,失败记录可在结算记录中单独重试。"
|
title="消费榜和中奖榜分别配置六档奖励;名次范围不可增删或修改,失败记录可在结算记录中单独重试。"
|
||||||
/>
|
/>
|
||||||
<el-table :data="form.rankRewards" border class="config-table">
|
<el-table :data="form.rankRewards" border class="config-table">
|
||||||
|
<el-table-column label="榜单" width="110" align="center">
|
||||||
|
<template slot-scope="scope">
|
||||||
|
<el-tag :type="scope.row.rankingType === 'VICTORIOUS' ? 'warning' : 'primary'">
|
||||||
|
{{ rankingTypeText(scope.row.rankingType) }}
|
||||||
|
</el-tag>
|
||||||
|
</template>
|
||||||
|
</el-table-column>
|
||||||
<el-table-column label="名次范围" width="130" align="center">
|
<el-table-column label="名次范围" width="130" align="center">
|
||||||
<template slot-scope="scope">
|
<template slot-scope="scope">
|
||||||
<el-tag type="success">{{ rankRangeText(scope.row) }}</el-tag>
|
<el-tag type="success">{{ rankRangeText(scope.row) }}</el-tag>
|
||||||
@ -346,10 +368,17 @@
|
|||||||
</el-table>
|
</el-table>
|
||||||
</template>
|
</template>
|
||||||
</el-table-column>
|
</el-table-column>
|
||||||
|
<el-table-column label="榜单" width="110" align="center">
|
||||||
|
<template slot-scope="scope">
|
||||||
|
<el-tag :type="scope.row.rankingType === 'VICTORIOUS' ? 'warning' : 'primary'">
|
||||||
|
{{ rankingTypeText(scope.row.rankingType) }}
|
||||||
|
</el-tag>
|
||||||
|
</template>
|
||||||
|
</el-table-column>
|
||||||
<el-table-column label="名次" width="70" align="center" prop="rank" />
|
<el-table-column label="名次" width="70" align="center" prop="rank" />
|
||||||
<el-table-column label="用户 ID" min-width="160" prop="userId" />
|
<el-table-column label="用户 ID" min-width="160" prop="userId" />
|
||||||
<el-table-column label="消费金币" min-width="120" align="right">
|
<el-table-column label="榜单数值" min-width="120" align="right">
|
||||||
<template slot-scope="scope">{{ formatNumber(scope.row.totalConsumed) }}</template>
|
<template slot-scope="scope">{{ formatNumber(scope.row.score === undefined ? scope.row.totalConsumed : scope.row.score) }}</template>
|
||||||
</el-table-column>
|
</el-table-column>
|
||||||
<el-table-column label="资源组" min-width="145" prop="resourceGroupId" />
|
<el-table-column label="资源组" min-width="145" prop="resourceGroupId" />
|
||||||
<el-table-column label="发放状态" width="110" align="center">
|
<el-table-column label="发放状态" width="110" align="center">
|
||||||
@ -543,6 +572,7 @@ const REQUIRED_RANK_RANGES = [
|
|||||||
[8, 10],
|
[8, 10],
|
||||||
[11, 30]
|
[11, 30]
|
||||||
]
|
]
|
||||||
|
const RANKING_TYPES = ['TYCOON', 'VICTORIOUS']
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
name: 'ActivityGameKing',
|
name: 'ActivityGameKing',
|
||||||
@ -619,6 +649,7 @@ export default {
|
|||||||
timeZone: 'Asia/Riyadh',
|
timeZone: 'Asia/Riyadh',
|
||||||
timeRange: [],
|
timeRange: [],
|
||||||
coinPerDraw: 1,
|
coinPerDraw: 1,
|
||||||
|
dailyChanceLimit: 10,
|
||||||
settlementDelayMinutes: 30,
|
settlementDelayMinutes: 30,
|
||||||
rankingType: 'TYCOON',
|
rankingType: 'TYCOON',
|
||||||
rankingPeriod: 'OVERALL',
|
rankingPeriod: 'OVERALL',
|
||||||
@ -642,15 +673,18 @@ export default {
|
|||||||
}))
|
}))
|
||||||
},
|
},
|
||||||
emptyRankRewards() {
|
emptyRankRewards() {
|
||||||
return REQUIRED_RANK_RANGES.map((range, index) => ({
|
return RANKING_TYPES.reduce((result, rankingType) => result.concat(
|
||||||
|
REQUIRED_RANK_RANGES.map((range, index) => ({
|
||||||
id: '',
|
id: '',
|
||||||
activityId: '',
|
activityId: '',
|
||||||
|
rankingType,
|
||||||
startRank: range[0],
|
startRank: range[0],
|
||||||
endRank: range[1],
|
endRank: range[1],
|
||||||
resourceGroupId: '',
|
resourceGroupId: '',
|
||||||
rewardName: index < 3 ? `Top ${index + 1} 奖励` : `Top ${range[0]}-${range[1]} 奖励`,
|
rewardName: index < 3 ? `Top ${index + 1} 奖励` : `Top ${range[0]}-${range[1]} 奖励`,
|
||||||
rewards: []
|
rewards: []
|
||||||
}))
|
}))
|
||||||
|
), [])
|
||||||
},
|
},
|
||||||
loadActivities() {
|
loadActivities() {
|
||||||
this.listLoading = true
|
this.listLoading = true
|
||||||
@ -681,6 +715,8 @@ export default {
|
|||||||
timeZone: activity.timeZone || 'Asia/Riyadh',
|
timeZone: activity.timeZone || 'Asia/Riyadh',
|
||||||
settlementDelayMinutes: activity.settlementDelayMinutes === null || activity.settlementDelayMinutes === undefined
|
settlementDelayMinutes: activity.settlementDelayMinutes === null || activity.settlementDelayMinutes === undefined
|
||||||
? 30 : Number(activity.settlementDelayMinutes),
|
? 30 : Number(activity.settlementDelayMinutes),
|
||||||
|
dailyChanceLimit: activity.dailyChanceLimit === null || activity.dailyChanceLimit === undefined
|
||||||
|
? 10 : Number(activity.dailyChanceLimit),
|
||||||
timeRange: [activity.startTime, activity.endTime],
|
timeRange: [activity.startTime, activity.endTime],
|
||||||
prizes,
|
prizes,
|
||||||
rankRewards
|
rankRewards
|
||||||
@ -708,7 +744,13 @@ export default {
|
|||||||
mergeRankRewards(rankRewards) {
|
mergeRankRewards(rankRewards) {
|
||||||
const result = this.emptyRankRewards()
|
const result = this.emptyRankRewards()
|
||||||
rankRewards.forEach(item => {
|
rankRewards.forEach(item => {
|
||||||
const index = REQUIRED_RANK_RANGES.findIndex(range => range[0] === Number(item.startRank) && range[1] === Number(item.endRank))
|
// 榜单类型和名次区间共同定位配置,避免两个榜单的同一名次奖励相互覆盖。
|
||||||
|
const rankingType = item.rankingType || 'TYCOON'
|
||||||
|
const index = result.findIndex(target =>
|
||||||
|
target.rankingType === rankingType &&
|
||||||
|
target.startRank === Number(item.startRank) &&
|
||||||
|
target.endRank === Number(item.endRank)
|
||||||
|
)
|
||||||
if (index >= 0) {
|
if (index >= 0) {
|
||||||
result.splice(index, 1, Object.assign({}, result[index], item, {
|
result.splice(index, 1, Object.assign({}, result[index], item, {
|
||||||
rewards: item.rewardItems || item.rewards || []
|
rewards: item.rewardItems || item.rewards || []
|
||||||
@ -735,7 +777,7 @@ export default {
|
|||||||
}
|
}
|
||||||
const payload = this.buildSavePayload()
|
const payload = this.buildSavePayload()
|
||||||
this.saveLoading = true
|
this.saveLoading = true
|
||||||
// 基础配置、七个奖项与六档排行奖励一次提交,由后端事务保证不会保存出半套配置。
|
// 基础配置、七个奖项与两个榜单各六档奖励一次提交,由后端事务保证不会保存出半套配置。
|
||||||
saveAslanGameKingActivity(payload).then(() => {
|
saveAslanGameKingActivity(payload).then(() => {
|
||||||
this.$message.success('活动配置已保存')
|
this.$message.success('活动配置已保存')
|
||||||
this.editorVisible = false
|
this.editorVisible = false
|
||||||
@ -755,6 +797,10 @@ export default {
|
|||||||
this.$message.error('每次抽奖金币数必须是大于 0 的安全整数')
|
this.$message.error('每次抽奖金币数必须是大于 0 的安全整数')
|
||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
|
if (!Number.isSafeInteger(Number(this.form.dailyChanceLimit)) || Number(this.form.dailyChanceLimit) < 1 || Number(this.form.dailyChanceLimit) > 10000) {
|
||||||
|
this.$message.error('每日最多获得次数必须是 1 到 10000 的整数')
|
||||||
|
return false
|
||||||
|
}
|
||||||
if (!Number.isInteger(Number(this.form.settlementDelayMinutes)) ||
|
if (!Number.isInteger(Number(this.form.settlementDelayMinutes)) ||
|
||||||
Number(this.form.settlementDelayMinutes) < 0 || Number(this.form.settlementDelayMinutes) > 1440) {
|
Number(this.form.settlementDelayMinutes) < 0 || Number(this.form.settlementDelayMinutes) > 1440) {
|
||||||
this.$message.error('结算等待必须是 0 到 1440 的整数分钟')
|
this.$message.error('结算等待必须是 0 到 1440 的整数分钟')
|
||||||
@ -777,14 +823,15 @@ export default {
|
|||||||
this.$message.error('请补全 7 个奖项的名称、图片、正整数权重、合法库存和奖励资源组')
|
this.$message.error('请补全 7 个奖项的名称、图片、正整数权重、合法库存和奖励资源组')
|
||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
const rangesValid = this.form.rankRewards.length === REQUIRED_RANK_RANGES.length &&
|
const rangesValid = this.form.rankRewards.length === REQUIRED_RANK_RANGES.length * RANKING_TYPES.length &&
|
||||||
this.form.rankRewards.every((item, index) =>
|
this.form.rankRewards.every((item, index) =>
|
||||||
Number(item.startRank) === REQUIRED_RANK_RANGES[index][0] &&
|
item.rankingType === RANKING_TYPES[Math.floor(index / REQUIRED_RANK_RANGES.length)] &&
|
||||||
Number(item.endRank) === REQUIRED_RANK_RANGES[index][1] &&
|
Number(item.startRank) === REQUIRED_RANK_RANGES[index % REQUIRED_RANK_RANGES.length][0] &&
|
||||||
|
Number(item.endRank) === REQUIRED_RANK_RANGES[index % REQUIRED_RANK_RANGES.length][1] &&
|
||||||
Boolean(item.resourceGroupId)
|
Boolean(item.resourceGroupId)
|
||||||
)
|
)
|
||||||
if (!rangesValid) {
|
if (!rangesValid) {
|
||||||
this.$message.error('六档名次范围必须保持固定,并为每档选择奖励资源组')
|
this.$message.error('两个榜单的六档名次范围必须保持固定,并为每档选择奖励资源组')
|
||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
return true
|
return true
|
||||||
@ -802,6 +849,7 @@ export default {
|
|||||||
endTime: Number(this.form.timeRange[1]),
|
endTime: Number(this.form.timeRange[1]),
|
||||||
settlementDelayMinutes: Number(this.form.settlementDelayMinutes),
|
settlementDelayMinutes: Number(this.form.settlementDelayMinutes),
|
||||||
coinPerDraw: Number(this.form.coinPerDraw),
|
coinPerDraw: Number(this.form.coinPerDraw),
|
||||||
|
dailyChanceLimit: Number(this.form.dailyChanceLimit),
|
||||||
rankingType: 'TYCOON',
|
rankingType: 'TYCOON',
|
||||||
rankingPeriod: 'OVERALL',
|
rankingPeriod: 'OVERALL',
|
||||||
enabled: Boolean(this.form.enabled)
|
enabled: Boolean(this.form.enabled)
|
||||||
@ -821,6 +869,7 @@ export default {
|
|||||||
payload.rankRewards = this.form.rankRewards.map(item => ({
|
payload.rankRewards = this.form.rankRewards.map(item => ({
|
||||||
id: item.id || null,
|
id: item.id || null,
|
||||||
activityId: this.form.id || null,
|
activityId: this.form.id || null,
|
||||||
|
rankingType: item.rankingType,
|
||||||
startRank: Number(item.startRank),
|
startRank: Number(item.startRank),
|
||||||
endRank: Number(item.endRank),
|
endRank: Number(item.endRank),
|
||||||
resourceGroupId: String(item.resourceGroupId),
|
resourceGroupId: String(item.resourceGroupId),
|
||||||
@ -1051,6 +1100,9 @@ export default {
|
|||||||
rankRangeText(row) {
|
rankRangeText(row) {
|
||||||
return row.startRank === row.endRank ? `Top ${row.startRank}` : `Top ${row.startRank}-${row.endRank}`
|
return row.startRank === row.endRank ? `Top ${row.startRank}` : `Top ${row.startRank}-${row.endRank}`
|
||||||
},
|
},
|
||||||
|
rankingTypeText(rankingType) {
|
||||||
|
return rankingType === 'VICTORIOUS' ? '中奖榜' : '消耗榜'
|
||||||
|
},
|
||||||
formatTime(value) {
|
formatTime(value) {
|
||||||
if (!value) {
|
if (!value) {
|
||||||
return '-'
|
return '-'
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user