package bacwaterpool import ( "context" "math/rand" "sort" "time" "bet24.com/log" pb "bet24.com/servers/micros/waterpool/proto" ) var control_type = []string{"normal", "lose", "win"} func getControlType(t int) string { if t < 0 || t >= len(control_type) { t = 0 } return control_type[t] } func newPoolInfo(config poolConfig) *poolInfo { ret := new(poolInfo) ret.poolConfig = config ret.PoolValue = config.InitPool ret.sortLevels() go ret.updateValue() return ret } type poolLevel struct { Value int Chance int // 调控百分比 Type int // 调控模式 } type poolConfig struct { PoolId int ReturnRate int // 返奖率百分比 InitPool int // 初始金额 UserMin int // 玩家最小 0 不限 UserMax int // 玩家最大 0 不限 IsSlots bool // 是否针对slots游戏 GameId int // 游戏ID PoolName string // 奖池名字 PoolType int // 奖池对应的房间类型 Levels []poolLevel } type poolInfo struct { poolConfig PoolValue int lastValue int } func (p *poolInfo) dump() { t, c := p.getEffectiveLevel() //log.Release("poolInfo.dump,getEffectiveLevel = %d,%d", t, c) log.Release(" Pool[%d] Value[%d] MinMax[%d-%d] [%d%% of %s]", p.PoolId, p.PoolValue, p.UserMin, p.UserMax, c, getControlType(t)) for i := 0; i < len(p.Levels); i++ { log.Release(" [%d][%d%% of %s]", p.Levels[i].Value, p.Levels[i].Chance, getControlType(p.Levels[i].Type)) } } func (p *poolInfo) updateValue() { for { c, cancel := context.WithTimeout(context.Background(), sync_sec*time.Second) select { case <-c.Done(): if p.PoolValue != p.lastValue { p.lastValue = p.PoolValue trans_updateWaterPoolList(p.GameId, p.PoolName, p.PoolType, p.PoolValue) } cancel() } } } func (p *poolInfo) sortLevels() { sort.Slice(p.Levels, func(i, j int) bool { return p.Levels[i].Value > p.Levels[j].Value }) } func (p *poolInfo) addBet(betAmount int, userGold int, isSlots bool, gameId int, poolName string) bool { if !p.isConcerned(userGold, isSlots, gameId) || (poolName != "" && poolName == p.PoolName) { return false } reduceValue := (betAmount / 100 * p.ReturnRate) sysRecover := betAmount - reduceValue p.PoolValue += reduceValue go trans_waterPoolChangeRecord(gameId, p.PoolName, reduceValue, p.PoolType, sysRecover) return true } func (p *poolInfo) reducePool(value int, userGold int, isSlots bool, gameId int, poolName string) bool { if !p.isConcerned(userGold, isSlots, gameId) || (poolName != "" && poolName == p.PoolName) { return false } p.PoolValue -= value go trans_waterPoolChangeRecord(gameId, p.PoolName, -value, p.PoolType, 0) return true } func (p *poolInfo) isConcerned(gold int, isSlots bool, gameId int) bool { if isSlots != p.IsSlots { return false } if p.UserMin != 0 && gold < p.UserMin { return false } if p.UserMax != 0 && gold > p.UserMax { return false } if gameId != 0 && p.GameId != 0 && gameId != p.GameId { return false } return true } func (p *poolInfo) getControlType(userGold int, isSlots bool, gameId int) int { if !p.isConcerned(userGold, isSlots, gameId) { return pb.PoolControl_Invalid } r := rand.Intn(100) t, c := p.getEffectiveLevel() if r < c { return t } return pb.PoolControl_Normal } func (p *poolInfo) getControlProb(userGold int, isSlots bool, gameId int, poolName string) (int, int) { if !p.isConcerned(userGold, isSlots, gameId) { return 0, 0 } t, value := p.getEffectiveLevel() value = value * 100 if t == pb.PoolControl_Lose { value = -value } return t, value } func (p *poolInfo) getEffectiveLevel() (int, int) { // 先看放水的 for i := 0; i < len(p.Levels); i++ { if p.PoolValue >= p.Levels[i].Value && p.Levels[i].Type == pb.PoolControl_Win { //log.Release("poolInfo.getEffectiveLevel poolValue = %d", p.PoolValue) //log.Release(" [%d][%d%% of %s]", p.Levels[i].Value, p.Levels[i].Chance, getControlType(p.Levels[i].Type)) return pb.PoolControl_Win, p.Levels[i].Chance } } for i := len(p.Levels) - 1; i >= 0; i-- { if p.PoolValue <= p.Levels[i].Value && p.Levels[i].Type == pb.PoolControl_Lose { //log.Release("poolInfo.getEffectiveLevel2 poolValue = %d", p.PoolValue) //log.Release(" [%d][%d%% of %s]", p.Levels[i].Value, p.Levels[i].Chance, getControlType(p.Levels[i].Type)) return pb.PoolControl_Lose, p.Levels[i].Chance } } return pb.PoolControl_Normal, 0 }