Files
ZYZ/game-server/app/services/rewardService.ts
2020-12-16 16:16:20 +08:00

315 lines
12 KiB
TypeScript
Raw Blame History

This file contains invisible Unicode characters
This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
import { GOOD_TYPE, ITID, CURRENCY, CURRENCY_TYPE, COUNTER, CONSUME_TYPE } from './../consts/consts';
import { EquipModel } from './../db/Equip';
import { CounterModel } from './../db/Counter';
import { decodeStr, resResult } from '../pubUtils/util';
import { getGoodById, getFashionsById } from '../pubUtils/gamedata';
import { RoleModel } from '../db/Role';
import { setAp } from './actionPointService';
import { ItemModel } from '../db/Item';
import { STATUS } from '../consts/statusCode';
import { pinus } from 'pinus';
import { HeroModel } from '../db/Hero';
import { treatTask } from './battleService';
const _ = require('underscore');
export async function handleFixedReward(roleId: string, roleName: string, rewardStr: string, multi: number) {
let reward = decodeStr('fixReward', rewardStr);
let rewards = [];
for(let obj of reward)
rewards.push({ ...obj, count: Math.ceil(obj.count * multi)});
const result = await handleReward(roleId, roleName, reward);
return result;
}
export async function handleReward(roleId: string, roleName: string, rewards: Array<{type?: number, gid: number, count: number, times?: number}>) {
let returnGoods = new Array(), getGold = 0, getCoin = 0, getAp = 0;
for(let goods of rewards) {
let goodInfo = getGoodById(goods.gid);
let result = new Array<any>()
if(goodInfo.goodType == GOOD_TYPE.EQUIP) { // 装备
result = await rewardWeapons(roleId, roleName, goodInfo, {id: goods.gid, cnt: goods.count });
} else if(goodInfo.goodType == GOOD_TYPE.CONSUMES|| goodInfo.goodType == GOOD_TYPE.SCRIPT) { // 消耗品
let {type, isCurrency} = ITID.get(goodInfo.itid);
if(isCurrency) { // 货币
result = await rewardCurrency(roleId, goodInfo, {id: goods.gid, cnt: goods.count });
} else {
result = await rewardItems(roleId, roleName, goodInfo, type, {id: goods.gid, cnt: goods.count });
}
}
for(let obj of result) {
returnGoods.push({dropType: goods.type, times: goods.times, ...obj});
if(obj.isCurrency) {
if(obj.currencyType == CURRENCY_TYPE.GOLD) {
getGold += obj.count;
} else if (obj.currencyType == CURRENCY_TYPE.COIN) {
getCoin += obj.count;
} else if (obj.currencyType == CURRENCY_TYPE.ACTION_POINT) {
getAp += obj.count;
}
}
}
}
return {
goods: returnGoods,
getGold,
getCoin,
getAp
};
}
async function rewardWeapons (roleId: string, roleName: string, dicGood: any, weapon: {id:number,cnt:number }) {
let weaponsData = [];
let cnt = weapon.cnt;
while (cnt > 0) {
const seqId = await CounterModel.getNewCounter(COUNTER.EID);
const equipInfo = {
roleId,
roleName,
id: weapon.id,
name: dicGood.name,
seqId,
quality: dicGood.lv,
type: dicGood.goodType
}
const equip = await EquipModel.createEquip(equipInfo);
cnt -= 1;
weaponsData.push(equip);
}
return weaponsData;
}
// 消耗品
async function rewardItems (roleId: string, roleName: string, dicGood: any, type: number, data: {id:number,cnt:number }) {
let goods = new Array();
let {id, cnt} = data;
let result = await ItemModel.increaseItem(roleId, id, cnt, {roleId, roleName, itemName: dicGood.name, id, type, hid: dicGood.hid||0});
if(result) {
goods.push({
id: id,
name: dicGood.name,
count: cnt,
type: dicGood.goodType,
isCurrency: false
});
}
return goods;
}
// 消耗品
async function rewardCurrency (roleId: string, dicGood: any, data: {id:number,cnt:number }) {
let goods = new Array();
let {id, cnt} = data;
let dicCurrency = CURRENCY.get(id);
if(dicCurrency.type == CURRENCY_TYPE.GOLD) { // 处理元宝
await RoleModel.addGoldFree(roleId, cnt);
} else if(dicCurrency.type == CURRENCY_TYPE.COIN) { // 处理铜币
await RoleModel.addCoin(roleId, cnt);
} else if(dicCurrency.type == CURRENCY_TYPE.ACTION_POINT) { // 处理体力
await setAp(Date.now(), roleId, cnt);
}
goods.push({
id: id,
name: dicGood.name,
count: cnt,
type: dicGood.goodType,
isCurrency: true,
currencyType: dicCurrency.type
});
return goods;
}
export async function handleCost(roleId: string, sid: string, goods: Array<{id: number, count: number}>) {
// 检查道具数量
let role, costGold = 0, costCoin = 0, items = new Array<{id: number, count: number}>(), ids = new Array<number>() ;
for(let {id, count} of goods) {
let goodInfo = getGoodById(id);
if(goodInfo.goodType == GOOD_TYPE.CONSUMES|| goodInfo.goodType == GOOD_TYPE.SCRIPT) { // 消耗品
let {isCurrency} = ITID.get(goodInfo.itid);
if(isCurrency) { // 货币
if(!role) role = await RoleModel.findByRoleId(roleId);
let dicCurrency = CURRENCY.get(id);
if(dicCurrency.type == CURRENCY_TYPE.GOLD) { // 处理元宝
if(role.gold < count + costGold) return false;
costGold += count;
} else if(dicCurrency.type == CURRENCY_TYPE.COIN) { // 处理铜币
if(role.coin < count + costCoin) return false;
costCoin += count;
}
} else {
let findItem = items.find(cur => cur.id == id);
if(findItem) {
findItem.count += count;
} else {
items.push({id, count}); ids.push(id);
}
}
}
}
for(let {id, count} of items) {
let item = await ItemModel.findbyRoleAndGidAndCount(roleId, id, count);
if(!item) return false
}
// 推送参数
let gold = 0, coin = 0, resultGoods = [];
if(costGold > 0) {
role = await RoleModel.costGold(roleId, costGold);
if(role) gold = role.gold;
}
if(costCoin > 0) {
role = await RoleModel.costCoin(roleId, costCoin);
if(role) coin = role.coin;
}
if(items.length > 0) {
let {hasError, result} = await ItemModel.decreaseItems(roleId, items);
if(hasError) return;
resultGoods = result;
}
let uids = [{uid: roleId, sid}];
pinus.app.get('channelService').pushMessageByUids('onItemUpdate', resResult(STATUS.SUCCESS, {goods: resultGoods, gold, coin} ), uids);
return true;
}
interface Item {id: number, count: number};
interface Equip {id: number, name: string, quality: number, type: number};
interface Bag {id: number, itemName: string, count: number, type: number, hid:number};
export async function addItems(roleId: string, roleName: string, sid: string, goods: Array<Item>) {
let showItems: Array<Item> = [];
let currencys: Array<Item> = [];
let equips: Array<Equip> = [];
let bags: Array<Bag> = [];
let skins: Array<number> = [];
let uids = [{uid: roleId, sid}];
sortItems(goods, bags, skins, currencys, equips);
let equipInfos = [];
for (let equip of equips) {
let equipInfo = await addEquips(roleId, roleName, equip);
showItems.push({id: equip.id, count: 1});
equipInfos.push(equipInfo);
}
//装备推送
if (!!equipInfos.length) {
pinus.app.get('channelService').pushMessageByUids('onEquipAdd', resResult(STATUS.SUCCESS, {equipInfos}), uids);
}
let data = {};
for (let currency of currencys) {
await addCurrency(roleId, currency, data);
showItems.push(currency);
}
//货币推送
if (!!Object.keys(data).length) {
pinus.app.get('channelService').pushMessageByUids('onPlayerDataChange', resResult(STATUS.SUCCESS, data), uids);
}
let bagInfos = [];
for (let item of bags) {
let bagInfo = await addBags(roleId, roleName, item);
showItems.push({id: item.id, count: item.count});
bagInfos.push(bagInfo);
}
//背包除去装备推送
if (!!bagInfos.length) {
pinus.app.get('channelService').pushMessageByUids('onItemUpdate', resResult(STATUS.SUCCESS, {goods: bagInfos}), uids);
}
let skinInfos = [];
for (let skinId of skins) {//皮肤推送
let result = await addSkins(roleId, skinId);
if (!!result) {
showItems.push({id: skinId, count: 1});
skinInfos.push(result);
}
pinus.app.get('channelService').pushMessageByUids('onHeroSkinChange', resResult(STATUS.SUCCESS, {skinInfos}), uids);
}
return showItems;
}
function sortItems (goods: Array<Item>, bags: Array<Bag>, skins: Array<number>, currencys: Array<Item>, equips: Array<Equip>) {
for (let good of goods) {
let goodInfo = getGoodById(good.id);
if (goodInfo.goodType == GOOD_TYPE.EQUIP) { // 装备
for (let i = 0; i < good.count; i++) {
equips.push({id: good.id, name: goodInfo.name, quality: goodInfo.lv, type: goodInfo.goodType});
}
} else {
let {type, isCurrency} = ITID.get(goodInfo.itid);
if (!!isCurrency) {
let index = _.indexOf(currencys, {id: good.id});
if (index > 0) {
currencys[index].count = currencys[index].count + good.count;
} else {
currencys.push(good);
}
} else if (goodInfo.itid == CONSUME_TYPE.SKIN) {
let index = _.indexOf(skins, good.id);
if (index == -1) {
skins.push(good.id);
}
} else {
let index = _.indexOf(skins, {id: good.id});
if (index > 0) {
bags[index].count = bags[index].count + good.count;
} else {
bags.push({id: good.id, count: good.count, itemName: goodInfo.name, hid: goodInfo.hid||0, type});
}
}
}
}
}
async function addSkins(roleId: string, id: number) {
let skinInfo = getFashionsById(id);
if (!skinInfo)
return false;
let hero = await HeroModel.findByHidAndRole(skinInfo.actorId, roleId, false);
if (!hero)
return false;
if (!!_.findWhere(hero.skins, {id}))
return false;
hero.skins.push({id: id, enable: false});
await HeroModel.updateHeroInfo(roleId, hero.hid, hero);
return {skins: hero.skins, hid: hero.hid};
}
async function addBags(roleId: string, roleName: string, data:Bag) {
let {id, count, itemName, type, hid} = data;
let item = await ItemModel.increaseItem(roleId, id, count, {roleId, roleName, itemName, id, type, hid});
return item;
}
async function addEquips (roleId: string, roleName: string, weapon: Equip) {
const seqId = await CounterModel.getNewCounter(COUNTER.EID);
let equip = Object.assign({seqId, roleId, roleName}, weapon);
return await EquipModel.createEquip(equip);
}
async function addCurrency(roleId: string, currency: {id: number, count: number }, data: any) {
let {id, count} = currency;
let dicCurrency = CURRENCY.get(id);
let result;
if(dicCurrency.type == CURRENCY_TYPE.GOLD) { // 处理元宝
result = await RoleModel.addGoldFree(roleId, count);
data.giftGold = result.giftGold;
data.gold = result.gold;
} else if(dicCurrency.type == CURRENCY_TYPE.COIN) { // 处理铜币
result = await RoleModel.addCoin(roleId, count);
data.coin = result.coin;
} else if(dicCurrency.type == CURRENCY_TYPE.ACTION_POINT) { // 处理体力
result = await setAp(Date.now(), roleId, count);
data.ap = result.ap;
}
}