service.go 6.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271
  1. package facility
  2. import (
  3. actorRemote "f1-game/internal/actor_remote"
  4. capp "f1-game/internal/cherry_app"
  5. "f1-game/internal/constant"
  6. "f1-game/internal/data"
  7. "f1-game/internal/enum"
  8. "f1-game/internal/event"
  9. facade "f1-game/internal/facade"
  10. nameRoute "f1-game/internal/name/route"
  11. "f1-game/internal/pb"
  12. "f1-game/internal/sessions"
  13. "f1-game/internal/types"
  14. "f1-game/nodes/map/internal/db"
  15. "f1-game/nodes/map/player/player"
  16. "f1-game/nodes/map/player/storage"
  17. "f1-game/nodes/map/player/team"
  18. clog "github.com/cherry-game/cherry/logger"
  19. cproto "github.com/cherry-game/cherry/net/proto"
  20. )
  21. var srv = &service{}
  22. func Service() *service {
  23. return srv
  24. }
  25. type service struct {
  26. facade.PlayerServiceBase[*db.MapPlayerTable]
  27. }
  28. func (p *service) OnLogin(mapPlayerTable *db.MapPlayerTable, session *cproto.Session) {
  29. // 根据常量表配置初始化城建,支持配表增量变化
  30. isFacilityChange := p.initDefaultFacilities(mapPlayerTable)
  31. isQueueChange := p.initDefaultQueues(mapPlayerTable)
  32. if isFacilityChange || isQueueChange {
  33. mapPlayerTable.Save2Queue()
  34. if isFacilityChange {
  35. // 只有属性更新才需要刷新声望值
  36. player.Service().RefreshFacilityPrestige(mapPlayerTable.PlayerID)
  37. }
  38. clog.Infof("map facility init: playerID = %d", mapPlayerTable.PlayerID)
  39. }
  40. }
  41. // func (p *service) OnLogined(playerTable *db.MapPlayerTable, session *cproto.Session) {
  42. // }
  43. // func (p *service) OnLogout(playerTable *db.MapPlayerTable) {
  44. // }
  45. // func (p *service) OnReset(playerTable *db.MapPlayerTable, time *ctime.CherryTime, byLogin bool) {
  46. // }
  47. // 建筑推送
  48. func (p *service) Push(playerTable *db.MapPlayerTable, session *cproto.Session) {
  49. proto := playerTable.Facilities.ToProto()
  50. sessions.PushWithSession(session, nameRoute.PushMapPlayer_FacilityList, &proto)
  51. }
  52. // 创建默认开启的建筑
  53. func (p *service) initDefaultFacilities(playerTable *db.MapPlayerTable) (isChange bool) {
  54. for _, build := range data.Const.BuildDefaultOpen {
  55. facility, found := playerTable.Facilities.Facilitys.Get(build.Key)
  56. if found && facility.Level >= build.Value {
  57. continue
  58. }
  59. if !found {
  60. facility = playerTable.Facilities.CreateFacility(build.Key)
  61. }
  62. facility.Level = build.Value
  63. isChange = true
  64. }
  65. if isChange {
  66. // 更新默认开启的建筑属性
  67. p.UpdateAttrs(playerTable, true)
  68. }
  69. return
  70. }
  71. // 创建默认解锁的建筑队列
  72. func (p *service) initDefaultQueues(playerTable *db.MapPlayerTable) (isChange bool) {
  73. for _, facilityQueue := range data.FacilityQueue.List() {
  74. if facilityQueue.IsUnlock {
  75. if playerTable.Facilities.Queues.Contains(facilityQueue.ID) {
  76. continue
  77. }
  78. playerTable.Facilities.UnlockQueue(facilityQueue.ID)
  79. isChange = true
  80. }
  81. }
  82. return
  83. }
  84. // 推送完成的建筑
  85. func (p *service) FinishPush(playerID int64, facilityIDList ...int32) {
  86. if len(facilityIDList) == 0 {
  87. return
  88. }
  89. var (
  90. playerTable = db.GetMapPlayerTable(playerID)
  91. list []*pb.Facility
  92. )
  93. if playerTable == nil {
  94. return
  95. }
  96. for _, facilityID := range facilityIDList {
  97. if facility, ok := playerTable.Facilities.Facilitys.Get(facilityID); ok {
  98. proto := facility.ToProto()
  99. list = append(list, &proto)
  100. }
  101. }
  102. if len(list) == 0 {
  103. return
  104. }
  105. rsp := pb.FacilityList{List: list}
  106. sessions.PushPlayer(playerID, nameRoute.PushMapPlayer_FacilityFinish, &rsp)
  107. }
  108. // CheckQueue 检查建筑队列
  109. func (p *service) CheckQueue(playerID int64, nowSecond int64) {
  110. var (
  111. playerTable = db.GetMapPlayerTable(playerID)
  112. facilityMap = types.NewMap[int32, int32]()
  113. )
  114. if playerTable == nil {
  115. return
  116. }
  117. for _, queue := range playerTable.Facilities.Queues {
  118. if queue.FinishTime > nowSecond || queue.FacilityID < 1 {
  119. continue
  120. }
  121. build, _ := playerTable.Facilities.Facilitys.Get(queue.FacilityID)
  122. build.Level++
  123. facilityMap.Put(build.FacilityID, build.Level)
  124. queue.Reset()
  125. }
  126. if len(facilityMap) > 0 {
  127. p.UpdateAttrs(playerTable)
  128. playerTable.Save2Queue()
  129. p.FinishPush(playerID, facilityMap.Keys()...)
  130. for facilityID, level := range facilityMap {
  131. capp.PostEvent(event.NewFacilityUp(playerID, facilityID, level))
  132. // 发送系统消息
  133. actorRemote.GamePlayer.GamePlayerCallSystemMsg(playerTable.GameNodeID, playerID, enum.ChatMsgType_buildUp, nil, nil, facilityID, level)
  134. }
  135. }
  136. }
  137. // 更新属性,只在变更的时候推送,登录在领主信息协议里推送
  138. func (p *service) UpdateAttrs(playerTable *db.MapPlayerTable, isLogin ...bool) {
  139. var (
  140. mapPlayerStorageTable = db.GetMapPlayerStorageTable(playerTable.PlayerID)
  141. attrs = newAttrs()
  142. )
  143. for _, fn := range attrFnList {
  144. fn(playerTable.PlayerID, attrs)
  145. }
  146. playerTable.Facilities.Attrs = attrs.result()
  147. // 更新建筑属性,转换为战斗对象属性
  148. p.UpdateFacilityFighterAttrs(playerTable)
  149. if playerTable.IsSelectBornState() {
  150. // 抛事件
  151. capp.PostEvent(event.NewMapWatcherSync(playerTable.PlayerID, &event.MapWatcherData{
  152. PlayerID: playerTable.PlayerID,
  153. IsFacilitySync: true,
  154. FacilityAttrs: playerTable.Facilities.Attrs,
  155. }))
  156. }
  157. // 是否推送,登录不推送
  158. isPush := len(isLogin) == 0 || !isLogin[0]
  159. if isPush {
  160. // 推送属性变更
  161. sessions.PushPlayer(playerTable.PlayerID, nameRoute.PushMapPlayer_FacilityAttrChange, playerTable.Facilities.Attrs.ToProto())
  162. }
  163. // 检查更新资源容量
  164. isChange := mapPlayerStorageTable.Storage.CurrencyMap.Check(playerTable.Facilities.Attrs.GetI64(enum.AttrResCapacity), enum.ItemMaxNumList)
  165. if isChange {
  166. mapPlayerStorageTable.Save2Queue()
  167. if isPush {
  168. // 推送资源容量变更,登录不推送
  169. storage.Service().ChangePush(playerTable.PlayerID, enum.ItemMaxNumList...)
  170. }
  171. }
  172. }
  173. // 建筑升级,城建属性转战斗对象的属性
  174. func (p *service) UpdateFacilityFighterAttrs(playerTable *db.MapPlayerTable) {
  175. attrs := types.NewAttrs()
  176. for _, facility := range playerTable.Facilities.Facilitys {
  177. if levelRow, ok := data.FacilityLevel.GetByFacilityIDLevel(facility.FacilityID, facility.Level); ok {
  178. for k, v := range levelRow.Attrs {
  179. switch k {
  180. case enum.AttrTeamDamageRatio:
  181. attrs.Add(enum.Attr_DamageBonus, v)
  182. case enum.AttrTeamDamageReduceRatio:
  183. attrs.Add(enum.Attr_DamageReduction, v)
  184. case enum.AttrInfantryAllAttrRatio:
  185. attrs.Add(enum.Attr_InfantryAllAttributeBonus, v)
  186. case enum.AttrCavalryAllAttrRatio:
  187. attrs.Add(enum.Attr_CavalryAllAttributeBonus, v)
  188. case enum.AttrArcherAllAttrRatio:
  189. attrs.Add(enum.Attr_ArcherAllAttributeBonus, v)
  190. }
  191. }
  192. }
  193. }
  194. for _, team := range playerTable.Teams {
  195. team.FacilityAttrs = attrs
  196. }
  197. playerTable.Save2Queue()
  198. // 更新所有队伍
  199. team.Service().UpdatePlayerTeams(playerTable.PlayerID, playerTable.Teams...)
  200. }
  201. func (*service) GetBuildCountLimit(playerTable *db.MapPlayerTable, mapBuildRow *data.MapBuildRow) int32 {
  202. attrID := int32(0)
  203. switch mapBuildRow.ConfigID {
  204. // 营帐
  205. case constant.MapBuild_Camp:
  206. attrID = enum.AttrTentLimit
  207. }
  208. if attrID <= 0 {
  209. return mapBuildRow.InitBuildLimit
  210. }
  211. return playerTable.Facilities.GetAttrs(attrID)
  212. }