player.go 32 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106
  1. package models
  2. import (
  3. "context"
  4. "fmt"
  5. mhayaString "github.com/mhaya/extend/string"
  6. mhayaTime "github.com/mhaya/extend/time"
  7. "github.com/mhaya/game/game_cluster/internal/constant"
  8. "github.com/mhaya/game/game_cluster/internal/data"
  9. "github.com/mhaya/game/game_cluster/internal/mdb"
  10. "github.com/mhaya/game/game_cluster/internal/param"
  11. "github.com/mhaya/game/game_cluster/internal/third"
  12. "github.com/mhaya/game/game_cluster/internal/token"
  13. mhayaLogger "github.com/mhaya/logger"
  14. "math/rand"
  15. "slices"
  16. "strconv"
  17. "strings"
  18. "time"
  19. )
  20. type Player struct {
  21. UserName string `json:"userName" bson:"userName"` // 用户名
  22. OpenId string `json:"openId" bson:"openId"` // 对应tgid
  23. UserNameMaybe string `json:"userNameMaybe" bson:"userNameMaybe"` // 昵称
  24. NickName string `json:"nickName" bson:"nickName"` // 昵称
  25. Pid string `json:"pid" bson:"pid"` // 上级ID
  26. XID string `json:"xID" bson:"xID"` // 绑定推特ID
  27. TonWall string `json:"tonWall" bson:"tonWall"` // 绑定钱包地址
  28. Email string `json:"email" bson:"email"` // 邮箱
  29. Mobile string `json:"mobile" bson:"mobile"` // 手机号
  30. Avatar string `json:"avatar" bson:"avatar"` // 头像
  31. Password string `json:"-" bson:"password"` //账户密码
  32. Salt string `json:"-" bson:"salt"` //密码盐
  33. IsNew bool `json:"isNew" bson:"isNew"` //是否新用户
  34. PwdErrTimes int `json:"pwdErrTimes" bson:"pwdErrTimes"` //密码错误次数
  35. PwdErrRefreshTime int64 `json:"pwdErrRefreshTime" bson:"pwdErrRefreshTime"` //密码到期时间
  36. IsCashOut int `json:"-" bson:"IsCashOut"` //服务器判断是否有提现的数据 0 否 1是
  37. IsRobot int `json:"isRobot" bson:"isRobot"` // 是否为机器人
  38. IsLeader int `json:"isLeader" bson:"isLeader"` // 是否是社区长
  39. IsVip int `json:"isVip" bson:"isVip"` // 是否为VIP
  40. IsFirstBindingXID int `json:"isFirstBindingXID" bson:"isFirstBindingXID"` // 是否是第一次绑定推特
  41. Level int `json:"level" bson:"level"` // 等级
  42. Exp int `json:"exp" bson:"exp"` // 经验
  43. Gender int `json:"gender" bson:"gender"` // 性别
  44. Birthday string `json:"birthday" bson:"birthday"` // 生日
  45. Successions int `json:"successions" bson:"successions"` // 连续登陆天数
  46. MaxSuccessions int `json:"maxSuccessions" bson:"maxSuccessions"` // 最大连续等级天数
  47. PrevTime int64 `json:"prevTime" bson:"prevTime"` // 上次登陆时间
  48. LoginTime int64 `json:"loginTime" bson:"loginTime"` // 登陆时间
  49. LoginIP string `json:"loginIP" bson:"loginIP"` // 登录IP
  50. LoginFailure int `json:"loginFailure" bson:"loginFailure"` // 登陆失败次数
  51. JoinIP string `json:"joinIP" bson:"joinIP"` // 注册IP
  52. Rank int `json:"rank" bson:"rank"` // 排名
  53. JoinTime int64 `json:"joinTime" bson:"joinTime"` // 注册时间
  54. CreateTime int64 `json:"createTime" bson:"createTime"` // 创建时间
  55. UpdateTime int64 `json:"updateTime" bson:"updateTime"` // 更新时间
  56. DailyRefreshTime int64 `json:"dailyRefreshTime" bson:"dailyRefreshTime"` // 每日刷新时间
  57. HourRefreshTime int64 `json:"hourRefreshTime" bson:"hourRefreshTime"` // 每小时更新
  58. WeeklyRefreshTime int64 `json:"weeklyRefreshTime" bson:"weeklyRefreshTime"` // 每周刷新时间
  59. RollDay int64 `json:"rollDay" bson:"rollDay"` // 抽奖日期
  60. Status int `json:"status" bson:"status"` // 状态
  61. Roll *Roll `json:"roll" bson:"roll"` // 抽奖
  62. Guide int `json:"guide" bson:"guide"` //
  63. Share *Share `json:"share" bson:"share"` // 分享
  64. FirstReward int `json:"firstReward" bson:"firstReward"` // 首次登陆奖励
  65. Index int `json:"-" bson:"index"` // 索引
  66. Item ItemBasePack `json:"item" bson:"item"` // 道具
  67. SinIn SignIn `json:"sinIn" bson:"sinIn"` // 签到
  68. DailyTask DailyTask `json:"dailyTask" bson:"dailyTask"` // 日常任务
  69. AchieveTask AchieveTask `json:"achieveTask" bson:"achieveTask"` // 成就任务
  70. RankReward RankReward `json:"rankReward" bson:"rankReward"` // 排行奖励
  71. Invite Invite `json:"invite" bson:"invite"` // 邀请
  72. PlayerReward map[int]*PlayerRewardBase `json:"-" bson:"-"`
  73. InviteReward *InviteReward `json:"inviteReward" bson:"inviteReward"` // 邀请奖励
  74. InviteNodeReward InviteNodeReward `json:"inviteNodeReward" bson:"inviteNodeReward"` // 邀请节点奖励
  75. ClaimInviteNum int `json:"claimInviteNum" bson:"claimInviteNum"` // 当前周期,已领取的节点邀请奖励基数
  76. FirstClaimReward FirstReward `json:"firstClaimReward" bson:"firstClaimReward"` // 首次奖励
  77. }
  78. func NewPlayer(token *token.Token) *Player {
  79. return &Player{
  80. UserName: token.PlayerID,
  81. OpenId: token.OpenID,
  82. NickName: token.Nickname,
  83. IsRobot: 0,
  84. IsNew: true,
  85. Successions: 1,
  86. MaxSuccessions: 1,
  87. LoginTime: mhayaTime.Now().Unix(),
  88. CreateTime: mhayaTime.Now().Unix(),
  89. UpdateTime: mhayaTime.Now().Unix(),
  90. RollDay: mhayaTime.Now().Unix(),
  91. Exp: 0,
  92. Status: 1,
  93. Rank: 0,
  94. Item: NewItem(),
  95. Guide: 1,
  96. Level: 1,
  97. Index: 1,
  98. FirstReward: 1,
  99. Roll: &Roll{RollNums: 0, RollDays: 0},
  100. DailyTask: NewDailyTask(),
  101. Share: &Share{IsDrawShare: 0},
  102. SinIn: NewSignIn(),
  103. AchieveTask: NewAchieveTask(),
  104. RankReward: NewRankReward(),
  105. Invite: NewInvite(),
  106. InviteNodeReward: NewInviteNodeReward(),
  107. FirstClaimReward: NewFirstReward(),
  108. }
  109. }
  110. func NewBotPlayer(token *token.Token) *Player {
  111. return &Player{
  112. UserName: token.PlayerID,
  113. OpenId: token.OpenID,
  114. NickName: token.Nickname,
  115. IsRobot: 1,
  116. Successions: 1,
  117. MaxSuccessions: 1,
  118. LoginTime: mhayaTime.Now().Unix(),
  119. CreateTime: mhayaTime.Now().Unix(),
  120. UpdateTime: mhayaTime.Now().Unix(),
  121. RollDay: mhayaTime.Now().Unix(),
  122. Exp: 0,
  123. Status: 1,
  124. Rank: 0,
  125. Item: NewItem(),
  126. Guide: 1,
  127. Level: 1,
  128. Index: 1,
  129. FirstReward: 1,
  130. Roll: &Roll{RollNums: 0, RollDays: 0},
  131. DailyTask: NewDailyTask(),
  132. Share: &Share{IsDrawShare: 0},
  133. SinIn: NewSignIn(),
  134. AchieveTask: NewAchieveTask(),
  135. RankReward: NewRankReward(),
  136. Invite: NewInvite(),
  137. }
  138. }
  139. func (p *Player) Init() {
  140. if p.InviteReward == nil {
  141. p.InviteReward = &InviteReward{IsClaim: 0}
  142. }
  143. }
  144. // InitDaily 每日刷新
  145. func (p *Player) InitDaily() {
  146. if !mhayaTime.CreateFromTimestamp(p.DailyRefreshTime).IsToday() {
  147. ////刷新每日任务
  148. //p.DailyTask.RefreshDailyTask()
  149. ////刷新抽奖每日分享
  150. //p.Share.RefreshShare()
  151. //刷新是否有排行榜奖励
  152. p.RankReward.InitRank(p.UserName, 1)
  153. //更新时间到当天
  154. p.DailyRefreshTime = mhayaTime.Now().Unix()
  155. }
  156. }
  157. func (p *Player) InitWeekly() {
  158. if !mhayaTime.CreateFromTimestamp(p.WeeklyRefreshTime).IsThisWeek() {
  159. p.SinIn.RefreshSignIn()
  160. //刷新是否有排行榜奖励
  161. p.RankReward.InitRank(p.UserName, 2)
  162. p.WeeklyRefreshTime = mhayaTime.Now().Unix()
  163. }
  164. }
  165. func (p *Player) InitSignIn() {
  166. ret := data.WeeklySignInConfig.GetAll()
  167. signInNode := []int{1009, 1010, 1011, 1012}
  168. // 最近一次签到
  169. //p.SinIn.RefreshSignIn()
  170. last, exists := p.SinIn.Sign[p.SinIn.Num-1]
  171. if !exists {
  172. // 签到数据初始化
  173. p.SinIn.RefreshSignIn()
  174. p.SinIn.RefreshSignNode(signInNode)
  175. return
  176. }
  177. // todo 测试代码
  178. //p.SinIn.RefreshSignIn()
  179. //p.SinIn.RefreshSignNode(signInNode)
  180. // 将时间戳转换为 time.Time 类型
  181. t := time.Unix(last.SignTime, 0)
  182. fmt.Sprintln(t)
  183. // todo 测试代码
  184. // 减去一天
  185. //t = t.Add(-24 * time.Hour)
  186. // 计算第二天的开始时间(即第二天的零点)
  187. // todo 正式代码
  188. //nextDayStart := t.Add(24 * time.Hour).Truncate(24 * time.Hour)
  189. //if p.SinIn.Num >= len(ret)-1 && time.Now().After(nextDayStart) {
  190. // // 签到周期满的第二天
  191. // p.SinIn.RefreshSignIn()
  192. //}
  193. // todo 测试代码
  194. if p.SinIn.Num >= len(ret) {
  195. p.SinIn.RefreshSignIn()
  196. }
  197. maxNodeId := signInNode[len(signInNode)-1]
  198. maxNode, _ := data.DiscreteRuleConfig.Get(maxNodeId)
  199. maxDay, _ := strconv.Atoi(maxNode.Condition)
  200. //if p.SinIn.NodeProgress.Curr >= maxDay && time.Now().After(nextDayStart) {
  201. // // 签到周期满的第二天
  202. // p.SinIn.RefreshSignNode(signInNode)
  203. //}
  204. // todo 测试代码
  205. if p.SinIn.NodeProgress.Curr >= maxDay {
  206. // 签到周期满的第二天
  207. p.SinIn.RefreshSignNode(signInNode)
  208. }
  209. }
  210. func (p *Player) InitAchieveTask() {
  211. p.AchieveTask.RefreshAchieveTask()
  212. }
  213. func (p *Player) LevelUp() bool {
  214. ret, ok := data.LevelConfig.Get(p.Level + 1)
  215. if !ok {
  216. return false
  217. }
  218. curLevel := p.Level
  219. if p.Item[ItemGold].CurNum >= ret.DiceNum && p.Item[ItemInvite].CurNum >= ret.Invite {
  220. p.Level += 1
  221. if p.Level > curLevel {
  222. p.Item[ItemGold].AddMaxNum(ret.DiceLimit)
  223. p.Item[ItemGold].CurNum -= ret.DiceNum
  224. p.Item[ItemInvite].CurNum -= ret.Invite
  225. go p.SetPassiveInviteReward()
  226. //添加日志
  227. mhayaLogger.Infof("player level up, playerName=%v,level=%v", p.UserName, p.Level)
  228. p.SetPlayerRewardLog(SourceLevelUp, p.Level, []data.ItemReward{{ItemID: ItemAllRoll, ItemBaseType: 2, Amount: ret.DiceLimit}}, []data.ItemReward{}, p.Level)
  229. return true
  230. }
  231. }
  232. return false
  233. }
  234. //func (p *Player) RefreshRoll() bool {
  235. // ret, ok := data.DiscreteRuleConfig.Get(RefreshRoll)
  236. // if !ok {
  237. // return false
  238. // }
  239. // arr := strings.Split(ret.Condition, ",")
  240. // if len(arr) == 0 {
  241. // return false
  242. // }
  243. // h, _ := mhayaString.ToInt64(arr[0])
  244. // //m, _ := mhayaString.ToInt64(arr[1])
  245. // s := mhayaTime.CreateFromTimestamp(p.RollDay).DiffInSeconds(mhayaTime.Now())
  246. // if s >= h {
  247. // p.RollDay = mhayaTime.Now().Unix()
  248. // num := p.Item[ItemRoll].AddAll()
  249. // num := p.Item[ItemGold].AddSameTwo(8)
  250. // if num > 0 {
  251. // p.SetPlayerRewardLog(SourceRefreshRoll, 1, []data.ItemReward{{ItemID: ItemRoll, ItemBaseType: 1, Amount: num}}, []data.ItemReward{}, 0)
  252. // p.SetPlayerRewardLog(SourceRefreshRoll, 2, []data.ItemReward{{ItemID: ItemGold, ItemBaseType: 1, Amount: num}}, []data.ItemReward{}, 0)
  253. // }
  254. // mhayaLogger.Infof("RefreshRoll by condition 1 rollDay:%d,num:%v", s, num)
  255. // return true
  256. // }
  257. // return false
  258. //}
  259. func (p *Player) CheckTaskByType1(openid int64, id int) bool {
  260. ret := data.AchieveTaskConfig.GetAll()
  261. mhayaLogger.Debugf("ret => %v", ret)
  262. for _, v := range ret {
  263. if v.Type == 2 {
  264. continue
  265. }
  266. mhayaLogger.Debugf("execute => GetIfChannel1()")
  267. if v.ID == id {
  268. if v.ID == 2 {
  269. if third.GetIfChannel(openid) == 1 {
  270. mhayaLogger.Debugf("execute => GetIfChannel2()")
  271. return true
  272. } else {
  273. mhayaLogger.Debugf("execute => GetIfChannel3()")
  274. return false
  275. }
  276. } else {
  277. return true
  278. }
  279. }
  280. }
  281. mhayaLogger.Debugf("execute => GetIfChannel4()")
  282. return false
  283. }
  284. func (p *Player) FinishAchieveTaskByType1(id int) bool {
  285. mhayaLogger.Debugf("FinishAchieveTaskByType1 id = %v", id)
  286. //if a, ok := p.AchieveTask[id]; ok {
  287. // mhayaLogger.Debugf("FinishAchieveTaskByType1 num = %v Validate = %v", a.Num, a.Validate)
  288. //if a.Num == 0 && a.Validate == 1 { //待验证
  289. openid, ok1 := mhayaString.ToInt64(p.OpenId)
  290. if !ok1 {
  291. mhayaLogger.Warnf("FinishAchieveTaskByType1 验证失败 username :%v, id : %v", p.UserName, id)
  292. return false
  293. }
  294. if p.CheckTaskByType1(openid, id) {
  295. p.AchieveTask[id].Validate = 2 //验证成功
  296. p.AchieveTask[id].Num = 1
  297. p.AchieveTask[id].Status = 1
  298. p.AchieveTask[id].RewardNum = 1
  299. //处理邀请订阅顺序问题
  300. if id == 2 {
  301. go p.SetPassiveInviteReward()
  302. }
  303. return true
  304. } else {
  305. p.AchieveTask[id].Validate = 0 //验证成功
  306. p.AchieveTask[id].Status = 0
  307. mhayaLogger.Warnf("FinishAchieveTaskByType1 验证失败 username :%v, id : %v", p.UserName, id)
  308. return false
  309. }
  310. //} else {
  311. // if a.Validate == 0 {
  312. // p.AchieveTask[id].Validate = 1
  313. // }
  314. //}
  315. //return true
  316. //}
  317. return false
  318. }
  319. // FinishAchieveTaskByType2 完成成就类型2
  320. func (p *Player) FinishAchieveTaskByType2() bool {
  321. //var range data.RangeInt32{}
  322. for _, v := range p.AchieveTask {
  323. if v.Type == 2 {
  324. ret, ok := data.AchieveTaskConfig.Get(v.ID)
  325. if !ok {
  326. continue
  327. }
  328. if p.Item[ItemInvite].Num <= ret.Condition.Max && p.AchieveTask[v.ID].Num != ret.Condition.Max {
  329. p.AchieveTask[v.ID].Num += 1
  330. if p.AchieveTask[v.ID].Num >= ret.Condition.Min && p.AchieveTask[v.ID].Num <= ret.Condition.Max {
  331. p.AchieveTask[v.ID].Status = 1
  332. p.AchieveTask[v.ID].RewardNum += 1
  333. }
  334. }
  335. }
  336. }
  337. return false
  338. }
  339. func (p *Player) FinishDailyTask(tp, num int) bool {
  340. var f bool
  341. for i := 0; i < num; i++ {
  342. for _, v := range p.DailyTask {
  343. if v.Type == tp && v.Status == 0 {
  344. p.DailyTask[v.ID].Num += 1
  345. if p.DailyTask[v.ID].Num == v.Condition {
  346. p.DailyTask[v.ID].Status = 1
  347. f = true
  348. continue
  349. }
  350. }
  351. }
  352. }
  353. return f
  354. }
  355. func (p *Player) RollOnce(num int) *param.RollOnce {
  356. var roll param.RollOnce
  357. levelConfig, ok := data.LevelConfig.Get(p.Level)
  358. if !ok {
  359. return nil
  360. }
  361. if levelConfig == nil {
  362. return nil
  363. }
  364. r1 := rand.Int31n(6) + 1
  365. r2 := rand.Int31n(6) + 1
  366. r3 := rand.Int31n(6) + 1
  367. //rule 4
  368. if (r1 == 1 && r2 == 1 && r3 == 1) || (r1 == 6 && r2 == 6 && r3 == 6) {
  369. roll.Score = levelConfig.Ratio * levelConfig.Rule4
  370. roll.RollType = constant.RollSpecialTripleBet
  371. } else if r1 == r2 && r2 == r3 {
  372. roll.Score = levelConfig.Ratio * levelConfig.Rule3
  373. roll.RollType = constant.RollTripleBet
  374. } else if r1 == r2 || r1 == r3 || r2 == r3 {
  375. roll.Score = levelConfig.Ratio * levelConfig.Rule2
  376. roll.RollType = constant.RollDoubleBet
  377. } else {
  378. roll.Score = levelConfig.Ratio * levelConfig.Rule1
  379. if r1+r2+r3 > 9 {
  380. roll.RollType = constant.RollBigBet
  381. } else {
  382. roll.RollType = constant.RollSmallBet
  383. }
  384. }
  385. roll.Rand = make(map[int]int32)
  386. roll.Rand[1] = r1
  387. roll.Rand[2] = r2
  388. roll.Rand[3] = r3
  389. p.Item[ItemScore].Add(roll.Score * num)
  390. p.Item[ItemGold].Sub(1 * num)
  391. p.SetPlayerRewardLog(SourceRoll, 0, []data.ItemReward{{ItemID: ItemScore, ItemBaseType: 1, Amount: roll.Score * num}}, []data.ItemReward{{ItemID: ItemGold, ItemBaseType: 1, Amount: 1 * num}}, roll)
  392. p.Roll.RollNums += 1 * num
  393. roll.IsDailyTask = p.FinishDailyTask(1, num)
  394. roll.IsLevelUp = p.LevelUp()
  395. return &roll
  396. }
  397. // Draw 最多尝试重复执行50次
  398. func (p *Player) Draw() *param.Draw {
  399. for i := 0; i < 50; i++ {
  400. draw, ok := p.DrawOnce()
  401. if ok {
  402. return draw
  403. }
  404. }
  405. return nil
  406. }
  407. func (p *Player) NewPlayer10Draw() {
  408. if p.Roll.DrawTotal == 0 {
  409. ret, ok := data.DiscreteRuleConfig.Get(NewPlayer10Draw)
  410. if !ok {
  411. return
  412. }
  413. arr := strings.Split(ret.Condition, ",")
  414. if len(arr) != 2 {
  415. return
  416. }
  417. minC := mhayaString.ToIntD(arr[0], 4)
  418. MaxC := mhayaString.ToIntD(arr[1], 6)
  419. p.Roll.NewDraw = make(map[int]int)
  420. wei := []int{1, 2, 4, 5, 12}
  421. wei2 := []int{1, 2, 4, 12}
  422. var m []int
  423. for i := 0; i < minC; i++ {
  424. r := rand.Intn(2)
  425. if r == 0 {
  426. m = append(m, 5)
  427. } else {
  428. m = append(m, 5)
  429. }
  430. }
  431. var num = len(m)
  432. var num2 = 0
  433. for i := 0; i < 10-minC; i++ {
  434. if num2 == 0 {
  435. if num >= MaxC {
  436. k2 := rand.Intn(len(wei2))
  437. cur := wei2[k2]
  438. if cur == 11 || cur == 5 {
  439. num++
  440. }
  441. if cur == 4 || cur == 12 {
  442. num2++
  443. }
  444. m = append(m, cur)
  445. } else {
  446. k := rand.Intn(len(wei))
  447. cur := wei[k]
  448. if cur == 11 || cur == 5 {
  449. num++
  450. }
  451. if cur == 4 || cur == 12 {
  452. num2++
  453. }
  454. m = append(m, cur)
  455. }
  456. } else {
  457. if num >= MaxC-1 {
  458. k2 := rand.Intn(len(wei2))
  459. cur := wei2[k2]
  460. if cur == 11 || cur == 5 {
  461. num++
  462. }
  463. if cur == 4 || cur == 12 {
  464. num2++
  465. }
  466. m = append(m, cur)
  467. } else {
  468. k := rand.Intn(len(wei))
  469. cur := wei[k]
  470. if cur == 11 || cur == 5 {
  471. num++
  472. }
  473. if cur == 4 || cur == 12 {
  474. num2++
  475. }
  476. m = append(m, cur)
  477. }
  478. }
  479. }
  480. m = Shuffle(m)
  481. for key, v := range m {
  482. p.Roll.NewDraw[key+1] = v
  483. }
  484. }
  485. }
  486. func Shuffle(slice []int) []int {
  487. rand.Seed(time.Now().UnixNano())
  488. for i := len(slice) - 1; i > 0; i-- {
  489. j := rand.Intn(i + 1)
  490. slice[i], slice[j] = slice[j], slice[i]
  491. }
  492. return slice
  493. }
  494. func (p *Player) DrawOnce() (*param.Draw, bool) {
  495. var ret map[int]*data.DrawConfigRow
  496. var draw param.Draw
  497. var wg = 0
  498. p.NewPlayer10Draw()
  499. if p.Roll.DrawTotal < 10 {
  500. ret = data.DrawConfig.GetByType(1)
  501. for _, v := range ret {
  502. wg += v.Weight
  503. }
  504. } else {
  505. ret = data.DrawConfig.GetByType(2)
  506. for _, v := range ret {
  507. wg += v.Weight
  508. }
  509. }
  510. if wg == 0 {
  511. return nil, false
  512. }
  513. var cur int
  514. var curID int
  515. //出去新手10连后规则
  516. if p.Roll.DrawTotal >= 10 {
  517. weight := int(rand.Int31n(int32(wg))) + 1
  518. for _, v := range ret {
  519. if v.Weight == 0 {
  520. continue
  521. }
  522. if weight > cur && weight <= cur+v.Weight {
  523. curID = v.ID
  524. break
  525. }
  526. cur += v.Weight
  527. }
  528. } else {
  529. curID = p.Roll.NewDraw[p.Roll.DrawTotal+1]
  530. //0.1u兼容处理
  531. if curID == 11 {
  532. curID = 5
  533. }
  534. }
  535. if d, ok := ret[curID]; ok {
  536. if d.HourTotalCondition > 0 {
  537. i, err := GetDrawHour(curID)
  538. if err != nil {
  539. return nil, false
  540. }
  541. if int(i) > d.HourTotalCondition {
  542. return nil, false
  543. }
  544. }
  545. if d.DailyTotalCondition > 0 {
  546. i, err := GetDrawDailyKey(curID)
  547. if err != nil {
  548. return nil, false
  549. }
  550. if int(i) > d.DailyTotalCondition {
  551. return nil, false
  552. }
  553. }
  554. if d.WeeklyTotalCondition > 0 {
  555. i, err := GetDrawWeeklyKey(curID)
  556. if err != nil {
  557. return nil, false
  558. }
  559. if int(i) > d.WeeklyTotalCondition {
  560. return nil, false
  561. }
  562. }
  563. p.Item.AddItem(d.Reward)
  564. p.Item[ItemDrawsNumber].Sub(1)
  565. draw.Reward = d.Reward
  566. draw.ID = d.Order
  567. draw.CurID = curID
  568. if len(p.Roll.Draw) == 0 {
  569. p.Roll.Draw = make(map[int]int)
  570. }
  571. if len(p.Roll.DrawRatio) == 0 {
  572. p.Roll.DrawRatio = make(map[int]float64)
  573. }
  574. p.Roll.Draw[curID] += 1
  575. p.Roll.DrawTotal += 1
  576. p.Roll.DrawRatio[curID] = float64(p.Roll.Draw[curID]) / float64(p.Roll.DrawTotal)
  577. p.SetPlayerRewardLog(SourceDraw, 0, draw.Reward, []data.ItemReward{{1, ItemDrawsNumber, 1}}, draw)
  578. } else {
  579. return nil, false
  580. }
  581. return &draw, true
  582. }
  583. func GetDrawHour(id int) (int64, error) {
  584. s := mhayaTime.CreateFromTime(mhayaTime.Now().Hour(), 0, 0).ToDateTimeFormat()
  585. key := fmt.Sprintf("%v:%v:%v", constant.DrawHourKey, id, s)
  586. return mdb.RDB.IncrBy(context.Background(), key, 1).Result()
  587. }
  588. func GetDrawDailyKey(id int) (int64, error) {
  589. key := fmt.Sprintf("%v:%v:%v", constant.DrawDailyKey, id, mhayaTime.Now().Format(mhayaTime.DateFormat))
  590. return mdb.RDB.IncrBy(context.Background(), key, 1).Result()
  591. }
  592. func GetDrawWeeklyKey(id int) (int64, error) {
  593. key := fmt.Sprintf("%v:%v:%v", constant.DrawWeeklyKey, id, mhayaTime.Now().Week())
  594. return mdb.RDB.IncrBy(context.Background(), key, 1).Result()
  595. }
  596. //func (p *Player) SignIn() *param.ChangeData {
  597. // var sign param.ChangeData
  598. // p.SinIn.SignDailyTime = mhayaTime.Now().Unix()
  599. // p.SinIn.Sign[p.SinIn.Num].IsSign = 1
  600. // p.SinIn.Sign[p.SinIn.Num].SignTime = mhayaTime.Now().Unix()
  601. // var addItem AddItem
  602. // at := addItem.Add(p.SinIn.Sign[p.SinIn.Num].Reward)
  603. // sign.AddItem = at
  604. // p.Item.AddItem(p.SinIn.Sign[p.SinIn.Num].Reward)
  605. // p.SinIn.Num += 1
  606. // p.SetPlayerRewardLog(SourceSignIn, p.SinIn.Num, p.SinIn.Sign[p.SinIn.Num].Reward, []data.ItemReward{}, nil)
  607. //
  608. // // 节点奖励进度
  609. // p.SinIn.NodeProgress.Curr += 1
  610. //
  611. // // 领取节点奖励
  612. //
  613. // sign.IsLevelUp = p.LevelUp()
  614. // return &sign
  615. //}
  616. func (p *Player) SetPlayerRewardLog(tp, tid int, addReward, subReward []data.ItemReward, desc interface{}) {
  617. p.Index += 1
  618. if len(p.PlayerReward) == 0 {
  619. p.PlayerReward = make(map[int]*PlayerRewardBase)
  620. }
  621. p.PlayerReward[p.Index] = &PlayerRewardBase{
  622. UserName: p.UserName,
  623. AddReward: addReward,
  624. SubReward: subReward,
  625. Desc: desc,
  626. Source: tp,
  627. SourceId: tid,
  628. CreateTime: mhayaTime.Now().Unix(),
  629. }
  630. }
  631. func (p *Player) SetPassiveInviteReward() {
  632. ret2, ok := data.DiscreteRuleConfig.Get(InvitePlayer)
  633. c, tok := mhayaString.ToInt(ret2.Condition)
  634. if !ok || !tok || c != p.Level {
  635. return
  636. }
  637. ret3, ok := data.DiscreteRuleConfig.Get(InviteVipPlayer)
  638. c, tok = mhayaString.ToInt(ret3.Condition)
  639. if !ok || !tok || c != p.Level {
  640. return
  641. }
  642. var isCheck bool
  643. if ts, ok := p.AchieveTask[2]; ok {
  644. if ts.Num == 1 {
  645. isCheck = true
  646. }
  647. }
  648. if !isCheck {
  649. // 升级邀请奖励
  650. openid, _ := mhayaString.ToInt64(p.OpenId)
  651. if third.GetIfChannel(openid) == 0 {
  652. mhayaLogger.Infof("player SetPassiveInviteReward,Not following the channel playerName=%v,level=%v,pid=%v", p.UserName, p.Level, p.Pid)
  653. return
  654. }
  655. }
  656. //被邀请人
  657. key := fmt.Sprintf("%v:1:%v", constant.InviteKey, p.UserName)
  658. //获取邀请人
  659. pUid := mdb.RDB.Get(context.Background(), key).Val()
  660. /* pbase := mdb.RDB.HGet(context.Background(), constant.PlayerBaseKey, pUid).Val()
  661. mdb.RDB.Del(context.Background(), key)
  662. var base param.PlayerBase
  663. err := jsoniter.Unmarshal([]byte(pbase), &base)
  664. if err != nil {
  665. return
  666. }*/
  667. var addItem []data.ItemReward
  668. if p.IsVip == 0 {
  669. //主动邀请记录, 设置邀请人数量+1
  670. key = fmt.Sprintf("%v:%v:%v", constant.InviteKey, InvitePlayer, pUid)
  671. err := mdb.RDB.IncrBy(context.Background(), key, 1).Err()
  672. if err != nil {
  673. mhayaLogger.Infof("player SetPassiveInviteReward,not vip invite playerName=%v,level=%v,param=%v,err=%v", p.UserName, p.Level, key, err)
  674. }
  675. addItem = append(addItem, ret2.Reward...)
  676. } else {
  677. //主动邀请记录, 设置邀请人数量+1
  678. key = fmt.Sprintf("%v:%v:%v", constant.InviteKey, InviteVipPlayer, pUid)
  679. err := mdb.RDB.IncrBy(context.Background(), key, 1).Err()
  680. if err != nil {
  681. mhayaLogger.Infof("player SetPassiveInviteReward, vip invite playerName=%v,level=%v,param=%v,err=%v", p.UserName, p.Level, key, err)
  682. }
  683. addItem = append(addItem, ret3.Reward...)
  684. }
  685. /* //社区长额外奖励
  686. if base.IsLeader == 1 {
  687. ret, ok := data.DiscreteRuleConfig.Get(InvitePlayerByLeader)
  688. if !ok {
  689. return
  690. }
  691. addItem = append(addItem, ret.Reward...)
  692. }*/
  693. if p.InviteReward.IsClaim == 2 {
  694. p.InviteReward.Reward = []data.ItemReward{}
  695. p.InviteReward.IsClaim = 0
  696. p.InviteReward.RewardTime = 0
  697. }
  698. p.InviteReward.Reward = append(p.InviteReward.Reward, addItem...)
  699. p.InviteReward.Merge()
  700. }
  701. func (p *Player) SetInviteReward() {
  702. ret, ok := data.DiscreteRuleConfig.Get(InvitePlayerByLeader)
  703. if !ok {
  704. return
  705. }
  706. ret2, ok := data.DiscreteRuleConfig.Get(InvitePlayer)
  707. if !ok {
  708. return
  709. }
  710. ret3, ok := data.DiscreteRuleConfig.Get(InviteVipPlayer)
  711. if !ok {
  712. return
  713. }
  714. var addItem []data.ItemReward
  715. key1 := fmt.Sprintf("%v:%v:%v", constant.InviteKey, InvitePlayer, p.UserName)
  716. key2 := fmt.Sprintf("%v:%v:%v", constant.InviteKey, InviteVipPlayer, p.UserName)
  717. //自己作为邀请人判断奖励
  718. freeNum, _ := mdb.RDB.Get(context.Background(), key1).Int()
  719. VipNum, _ := mdb.RDB.Get(context.Background(), key2).Int()
  720. for i := 0; i < freeNum; i++ {
  721. addItem = append(addItem, ret2.Reward...)
  722. p.SetPlayerRewardLog(SourceInvite, InvitePlayer, []data.ItemReward{}, []data.ItemReward{}, 2)
  723. if p.IsLeader == 1 {
  724. addItem = append(addItem, ret.Reward...)
  725. p.SetPlayerRewardLog(SourceInvite, InvitePlayerByLeader, []data.ItemReward{}, []data.ItemReward{}, 2)
  726. }
  727. p.Item[ItemInvite].Num += 1
  728. p.Item[ItemInvite].CurNum += 1
  729. p.Invite.Set(InvitePlayer, ret.Reward)
  730. p.FinishAchieveTaskByType2()
  731. mdb.RDB.DecrBy(context.Background(), key1, 1)
  732. }
  733. for i := 0; i < VipNum; i++ {
  734. addItem = append(addItem, ret3.Reward...)
  735. p.SetPlayerRewardLog(SourceInvite, InviteVipPlayer, []data.ItemReward{}, []data.ItemReward{}, 2)
  736. if p.IsLeader == 1 {
  737. addItem = append(addItem, ret.Reward...)
  738. p.SetPlayerRewardLog(SourceInvite, InvitePlayerByLeader, []data.ItemReward{}, []data.ItemReward{}, 2)
  739. }
  740. p.Item[ItemInvite].Num += 1
  741. p.Item[ItemInvite].CurNum += 1
  742. p.Invite.Set(InviteVipPlayer, ret.Reward)
  743. p.FinishAchieveTaskByType2()
  744. mdb.RDB.DecrBy(context.Background(), key2, 1)
  745. }
  746. if (freeNum + VipNum) > 0 {
  747. SetRank(constant.RankSourceInvite, p.IsRobot, p.UserName, freeNum+VipNum)
  748. }
  749. if p.InviteReward.IsClaim == 2 {
  750. p.InviteReward.Reward = []data.ItemReward{}
  751. p.InviteReward.IsClaim = 0
  752. p.InviteReward.RewardTime = 0
  753. }
  754. p.InviteReward.Reward = append(p.InviteReward.Reward, addItem...)
  755. p.InviteReward.Merge()
  756. }
  757. func (p *Player) SetInvite(pid string) bool {
  758. key := fmt.Sprintf("%v:1:%v", constant.InviteKey, p.UserName)
  759. ret, ok := data.DiscreteRuleConfig.Get(InviteMaxExpireTime)
  760. if !ok {
  761. mhayaLogger.Warn("SetInvite return 1")
  762. return false
  763. }
  764. t, _ := mhayaString.ToInt64(ret.Condition)
  765. err := mdb.RDB.Set(context.Background(), key, pid, time.Duration(t)*24*time.Hour).Err()
  766. if err != nil {
  767. mhayaLogger.Warn("SetInvite return 1")
  768. return false
  769. }
  770. key2 := fmt.Sprintf("%v:%v:%v", constant.InviteKey, InvitePlayer, p.Pid)
  771. lRange, _ := mdb.RDB.LRange(context.Background(), key2, 0, -1).Result()
  772. if slices.Contains(lRange, p.UserName) {
  773. mhayaLogger.Warn("SetInvite return 1")
  774. return false
  775. }
  776. mdb.RDB.LPush(context.Background(), key2, p.UserName)
  777. key3 := fmt.Sprintf("%v:%v:%v", constant.InviteTagKey, InvitePlayer, p.Pid)
  778. pTag := mdb.RDB.Get(context.Background(), key3).Val()
  779. mKey := fmt.Sprintf("%v:%v:%v", constant.InviteTagKey, InvitePlayer, p.UserName)
  780. mhayaLogger.Debugf("SetInvite finish 1")
  781. if pTag != "" {
  782. mdb.RDB.Set(context.Background(), mKey, pTag, 0)
  783. tagKey := fmt.Sprintf("%v:%v:%v", constant.InviteTagKey, 2, pTag)
  784. mdb.RDB.Incr(context.Background(), tagKey)
  785. } else {
  786. kol, _ := data.KolConfig.Get(p.Pid)
  787. if kol != nil {
  788. mdb.RDB.Set(context.Background(), mKey, kol.Mark, 0)
  789. tagKey := fmt.Sprintf("%v:%v:%v", constant.InviteTagKey, 2, kol.Mark)
  790. mdb.RDB.Incr(context.Background(), tagKey)
  791. }
  792. }
  793. mhayaLogger.Debugf("SetInvite finish 2")
  794. return true
  795. }
  796. func (p *Player) ClaimInviteReward(id int) param.ChangeData {
  797. var resp param.ChangeData
  798. if len(p.InviteReward.Reward) > 0 {
  799. var addItem AddItem
  800. resp.AddItem = addItem.Add(p.InviteReward.Reward)
  801. p.Item.AddItem(p.InviteReward.Reward)
  802. p.InviteReward.IsClaim = 2
  803. p.InviteReward.RewardTime = mhayaTime.Now().Unix()
  804. p.InviteReward.Reward = []data.ItemReward{}
  805. p.SetPlayerRewardLog(SourceInvite, id, p.InviteReward.Reward, []data.ItemReward{}, nil)
  806. }
  807. p.LevelUp()
  808. return resp
  809. }
  810. func (p *Player) ClaimAchieveTaskReward(id int) param.ChangeData {
  811. var resp param.ChangeData
  812. if ach, ok := p.AchieveTask[id]; ok {
  813. if ach.Status == 1 && ach.RewardNum > 0 {
  814. var addItem AddItem
  815. resp.AddItem = addItem.Add(ach.Reward)
  816. p.Item.AddItem(ach.Reward)
  817. ach.RewardNum -= 1
  818. p.SetPlayerRewardLog(SourceAchieveTask, id, ach.Reward, []data.ItemReward{}, nil)
  819. }
  820. if ach.RewardNum == 0 {
  821. ret, _ := data.AchieveTaskConfig.Get(ach.ID)
  822. if ret.Condition.Max == ach.Num {
  823. p.AchieveTask[id].Status = 2
  824. } else {
  825. p.AchieveTask[id].Status = 0
  826. }
  827. }
  828. }
  829. p.LevelUp()
  830. return resp
  831. }
  832. func (p *Player) ClaimDailyTaskReward(id int) param.ChangeData {
  833. var resp param.ChangeData
  834. if task, ok := p.DailyTask[id]; ok {
  835. if task.Status == 1 {
  836. var addItem AddItem
  837. resp.AddItem = addItem.Add(task.Reward)
  838. p.Item.AddItem(task.Reward)
  839. task.Status = 2
  840. p.SetPlayerRewardLog(SourceDailyTask, id, task.Reward, []data.ItemReward{}, nil)
  841. }
  842. }
  843. p.LevelUp()
  844. return resp
  845. }
  846. // 初始化邀请节点奖励
  847. func (p *Player) InitInviteNodeReword() {
  848. //key := fmt.Sprintf("%v:%v", constant.InviteNodeHistoryKey, p.UserName)
  849. //mdb.RDB.Del(context.Background(), key)
  850. icfg := data.InviteConfig.GetAll()
  851. var maxCondition int
  852. var isUpdate bool
  853. for _, value := range icfg {
  854. maxCondition += value.Condition
  855. if item, ok := p.InviteNodeReward[value.ID]; ok {
  856. if !slices.Equal(item.Reward, value.Reward) || item.Condition != value.Condition {
  857. isUpdate = true
  858. }
  859. } else {
  860. isUpdate = true
  861. }
  862. }
  863. if (len(p.InviteNodeReward) == 0) || isUpdate {
  864. // 初次邀请和更新奖励配置
  865. p.RefreshInviteNodeReward(icfg)
  866. } else if p.ClaimInviteNum >= maxCondition {
  867. // 奖励周期满,重置奖励
  868. p.RefreshInviteNodeReward(icfg)
  869. // 保留刷新前的奖励历史记录
  870. var beforeNum int64
  871. for _, item := range p.InviteNodeReward {
  872. beforeNum += int64(item.Condition)
  873. }
  874. mhayaLogger.Debugf("刷新邀请奖励周期")
  875. key := fmt.Sprintf("%v:%v", constant.InviteNodeHistoryKey, p.UserName)
  876. mdb.RDB.IncrBy(context.Background(), key, beforeNum)
  877. }
  878. }
  879. // 刷新邀请节点奖励
  880. func (p *Player) RefreshInviteNodeReward(icfg map[int]*data.InviteConfigRow) {
  881. p.InviteNodeReward = make(map[int]*InviteNodeRewardItem)
  882. for _, row := range icfg {
  883. condition := row.Condition
  884. inviteReward := &InviteNodeRewardItem{
  885. ID: row.ID,
  886. IsClaim: 0,
  887. IsUnlock: 1,
  888. Reward: row.Reward,
  889. Condition: condition,
  890. }
  891. p.InviteNodeReward[row.ID] = inviteReward
  892. p.ClaimInviteNum = 0
  893. }
  894. }
  895. // 初始化首次奖励
  896. func (p *Player) InitFirstReward() {
  897. drcAll := data.DiscreteRuleConfig.GetAll()
  898. ids := []int{1002, 1003, 1004, 1005, 1006}
  899. for _, id := range ids {
  900. diConfig, _ := drcAll[id]
  901. // todo 测试代码
  902. _, exists := p.FirstClaimReward[id]
  903. if !exists {
  904. item := &FirstRewardItem{
  905. Reward: diConfig.Reward,
  906. }
  907. p.FirstClaimReward[id] = item
  908. }
  909. }
  910. default_friend := []int{2001, 2002, 2003}
  911. openid, _ := strconv.ParseInt(p.OpenId, 10, 64)
  912. playerLevel, _ := data.PlayerConfig.Get(openid)
  913. // 3级以上的老用户专属奖励
  914. if playerLevel != nil && playerLevel.Level > 2 {
  915. level_reword := []int{10001, 10002, 10003, 10004, 10005, 10006, 10007, 10007, 10008, 10009, 10010}
  916. for _, id := range level_reword {
  917. ID := 1000
  918. if drcAll[id].Condition == (strconv.Itoa(playerLevel.Level)) {
  919. _, exists := p.FirstClaimReward[ID]
  920. if !exists {
  921. item := &FirstRewardItem{
  922. IsClaim: 0,
  923. Reward: drcAll[id].Reward,
  924. }
  925. newItem := &FirstRewardItem{
  926. IsClaim: 0,
  927. Reward: drcAll[10001].Reward,
  928. }
  929. oldAmount := item.Reward[0].Amount - drcAll[10001].Reward[0].Amount
  930. oldReward := data.ItemReward{
  931. ItemBaseType: 1,
  932. ItemID: 1,
  933. Amount: oldAmount,
  934. }
  935. oldItem := &FirstRewardItem{
  936. IsClaim: 0,
  937. Reward: []data.ItemReward{oldReward},
  938. }
  939. // 设置新用户的初始奖励
  940. p.FirstClaimReward[ID] = item
  941. p.FirstClaimReward[1001] = newItem
  942. // 设置老用户多出的奖励
  943. p.FirstClaimReward[10001] = oldItem
  944. }
  945. break
  946. }
  947. }
  948. } else {
  949. ID := 1000
  950. _, exists := p.FirstClaimReward[ID]
  951. if !exists {
  952. item := &FirstRewardItem{
  953. IsClaim: 0,
  954. Reward: drcAll[10001].Reward,
  955. }
  956. p.FirstClaimReward[ID] = item
  957. }
  958. }
  959. for _, id := range default_friend {
  960. row, _ := drcAll[id]
  961. if row == nil {
  962. continue
  963. }
  964. // todo 测试代码
  965. _, exists := p.FirstClaimReward[id]
  966. if !exists {
  967. item := &FirstRewardItem{
  968. IsClaim: 0,
  969. Reward: row.Reward,
  970. }
  971. p.FirstClaimReward[id] = item
  972. }
  973. }
  974. }