单人游戏结束时, 返回排行榜

This commit is contained in:
zhl 2021-05-11 16:03:06 +08:00
parent 5596f1d2f5
commit c6932fb7eb
5 changed files with 69 additions and 14 deletions

View File

@ -80,7 +80,8 @@
```js ```js
{ {
result: 1 //答题结果 1: 正确, 0 : 错误 result: 1, //答题结果 1: 正确, 0 : 错误
gameResult: 0, // 当前局游戏结果 0: 未完成, -1: 失败, 1: 胜利
"stats": { // 当局的状态 "stats": { // 当局的状态
"1111": { "1111": {
"answer": [ // 每一题的结果 "answer": [ // 每一题的结果
@ -90,7 +91,9 @@
"rightCount": 1, // 答对的数量 "rightCount": 1, // 答对的数量
"errorCount": 1, // 答错的数量 "errorCount": 1, // 答错的数量
"comboCount": 0, // 当前连续答对的数量 "comboCount": 0, // 当前连续答对的数量
"maxCombo": 1 // 当局连续答对的最大数量 "maxCombo": 1, // 当局连续答对的最大数量
"score": 10, // 当局胜利后的得分
"gameResult": 0 // 当局的游戏结果, 单人的话和上一层gameResult相同
} }
} }
} }

View File

@ -21,16 +21,28 @@ import { Schedule } from '../../clock/Schedule'
import { import {
calcPvpScore, calcPvpScore,
calcSingleScore, calcSingleScore,
checkSingleFinish, fetchLevelCfg, fetchSinglePuzzleType, checkSingleFinish, fetchLevelCfg, fetchSinglePuzzleType, getRank,
startGame, startGame,
transformRecord, updateSingleRank transformRecord, updateSingleRank
} from '../../services/GameLogic' } from '../../services/GameLogic'
import { ObjectId } from 'bson' import { ObjectId } from 'bson'
import { Shop } from '../../models/shop/Shop' import { Shop } from '../../models/shop/Shop'
import { isObjectId } from '../../utils/string.util' import { isObjectId } from '../../utils/string.util'
import {
getAccountRank,
getAccountScore,
getRankList
} from '../../services/Rank'
class PuzzleController extends BaseController { class PuzzleController extends BaseController {
@role('anon')
@router('get /api/test')
async test(req) {
let vl =await getAccountScore('11', '22')
return {vl}
}
@role('anon') @role('anon')
@router('post /api/:accountid/puzzle/list') @router('post /api/:accountid/puzzle/list')
async list(req, res) { async list(req, res) {
@ -112,6 +124,7 @@ class PuzzleController extends BaseController {
history.markModified('members') history.markModified('members')
let gameResult = 0 let gameResult = 0
await history.save() await history.save()
let rspData: any = { result, answer: record.a1, stats: history.members }
if (mode == 1) { if (mode == 1) {
let score = result ? calcPvpScore(history.scheduleKey, statMap.comboCount) : 0 let score = result ? calcPvpScore(history.scheduleKey, statMap.comboCount) : 0
await broadcast(history.room, 'answer', {accountid, result, score}) await broadcast(history.room, 'answer', {accountid, result, score})
@ -138,9 +151,13 @@ class PuzzleController extends BaseController {
} }
history.markModified('members') history.markModified('members')
await history.save() await history.save()
let {rankList, userRank } = await getRank({shop: history.shop, level: history.level, accountId: accountid, mode: 0, skip: 0, limit: 20})
rspData.rankList = rankList
rspData.userRank = userRank
} }
} }
return { result, answer: record.a1, stats: history.members, gameResult } rspData.gameResult = gameResult
return rspData
} }
@role('anon') @role('anon')

View File

@ -1,7 +1,7 @@
export class BaseConst{ export class BaseConst{
public static readonly COMPOUND = 'compound' public static readonly COMPOUND = 'compound'
public static readonly MISSION = 'mission' public static readonly MISSION = 'mission'
public static readonly RANK_SCORE = 'rank_score' public static readonly RANK_SCORE = 'r'
// 多人答题时间 // 多人答题时间
public static readonly MATCH_ANSWER_TIME = 10000 public static readonly MATCH_ANSWER_TIME = 10000
// 游戏结束后房间自动解散时间 // 游戏结束后房间自动解散时间

View File

@ -15,6 +15,12 @@ import { PuzzleRank } from '../models/match/PuzzleRank'
import { Shop } from '../models/shop/Shop' import { Shop } from '../models/shop/Shop'
import { mission_vo } from '../config/parsers/mission_vo' import { mission_vo } from '../config/parsers/mission_vo'
import { ShopActivity } from '../models/shop/ShopActivity' import { ShopActivity } from '../models/shop/ShopActivity'
import {
getAccountRank,
getAccountScore,
getRankList,
updateRank
} from './Rank'
export function transformRecord(records: any[]) { export function transformRecord(records: any[]) {
@ -116,7 +122,9 @@ export function calcPvpScore(timeKey: string, combo: number) {
const cfg = new GameEnv() const cfg = new GameEnv()
return cfg.pvpBaseScore + time / 100 * cfg.pvpTimeRate + combo * cfg.pvpComboRate return cfg.pvpBaseScore + time / 100 * cfg.pvpTimeRate + combo * cfg.pvpComboRate
} }
export function rankKey(shop: string, level: number, mode: number) {
return `${shop}_${mode}_${level}`
}
/** /**
* *
* @param {string} shop id * @param {string} shop id
@ -132,15 +140,34 @@ export async function updateSingleRank({shop, level, accountId, score, session,
level: number, level: number,
accountId: string, accountId: string,
score: number, score: number,
mode: number mode: number,
session: string}) { session: string}) {
const key = rankKey(shop, level, mode)
await updateRank(accountId, score, key)
// let record = (await PuzzleRank.findOrCreate({shop, level, accountId, mode})).doc
// if (record.score < score) {
// record.score = score
// record.session = session
// await record.save()
// }
}
let record = (await PuzzleRank.findOrCreate({shop, level, accountId, mode})).doc export async function getRank({shop, level, accountId, mode, skip, limit }
if (record.score < score) { : {shop: string,
record.score = score level: number,
record.session = session accountId: string,
await record.save() mode: number, skip: number, limit: number}) {
// let records = await PuzzleRank.find({shop, level, mode}).limit(limit).skip(skip).sort({'score': -1})
const key = rankKey(shop, level, mode)
let datas: any = await getRankList(skip, limit, key)
// let scoreMap: Map<any, number> = new Map()
let rankList: [any[]] = [[]]
for (let i = 0, l = datas.length; i < l; i += 2) {
// scoreMap.set(datas[i], datas[i + 1] << 0)
rankList.push([datas[i], datas[i + 1] << 0])
} }
let userRank = (await getAccountRank(accountId, key)) || 999
return {rankList, userRank}
} }
/** /**

View File

@ -19,7 +19,10 @@ function generateRankKey(subKey?: string) {
*/ */
export async function updateRank(accountId: string, score: number, subKey?: string) { export async function updateRank(accountId: string, score: number, subKey?: string) {
let scoreL = parseFloat(`${score | 0}.${MAX_TIME - Date.now()}`) let scoreL = parseFloat(`${score | 0}.${MAX_TIME - Date.now()}`)
let scoreOld = await getAccountScore(accountId, subKey)
if (score > scoreOld) {
await new RedisClient().zadd(generateRankKey(subKey), scoreL, accountId) await new RedisClient().zadd(generateRankKey(subKey), scoreL, accountId)
}
} }
/** /**
@ -49,7 +52,12 @@ export async function getAccountRank(accountId: string, subKey?: string) {
* @return {Promise<unknown>} * @return {Promise<unknown>}
*/ */
export async function getAccountScore(accountId: string, subKey?: string) { export async function getAccountScore(accountId: string, subKey?: string) {
return await new RedisClient().zscore(generateRankKey(subKey), accountId) let score = await new RedisClient().zscore(generateRankKey(subKey), accountId)
if (score) {
return (+score)<<0
} else {
return 0
}
} }
/** /**