96 lines
2.2 KiB
Go
96 lines
2.2 KiB
Go
package gameserver
|
|
|
|
import (
|
|
"fmt"
|
|
"os"
|
|
"reflect"
|
|
|
|
"gac-hkrpg-go/internal/common"
|
|
goproto "gac-hkrpg-go/protocol/proto"
|
|
)
|
|
|
|
func syncPersistedExRanks(s *Session) error {
|
|
// Publish changes after battle settlement; do not replace actor progression
|
|
// while the client's combat scene is using its captured BattleInfo.
|
|
if _, active := CURRENT_BATTLE.Load(s.Token); active {
|
|
return nil
|
|
}
|
|
player := s.JSON()
|
|
if player == nil {
|
|
return nil
|
|
}
|
|
p, err := common.ReadPersistent()
|
|
if os.IsNotExist(err) {
|
|
return nil
|
|
}
|
|
if err != nil {
|
|
return err
|
|
}
|
|
changed := player.RefreshExRanks(p)
|
|
if s.pendingExRankSync == nil {
|
|
s.pendingExRankSync = make(map[uint32]bool)
|
|
}
|
|
for _, id := range changed {
|
|
s.pendingExRankSync[id] = true
|
|
}
|
|
if len(s.pendingExRankSync) == 0 {
|
|
return nil
|
|
}
|
|
changed = changed[:0]
|
|
for id := range s.pendingExRankSync {
|
|
changed = append(changed, id)
|
|
}
|
|
sortU32Slice(changed)
|
|
notify := &goproto.PlayerSyncScNotify{}
|
|
buildSync(player, notify, changed, nil, nil)
|
|
notify.MaterialList, err = eidolonMaterials(player)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
if err := s.Send(notify); err != nil {
|
|
return err
|
|
}
|
|
Log(fmt.Sprintf("[EX-RANK SYNC] updated avatars=%v", changed))
|
|
s.pendingExRankSync = nil
|
|
return nil
|
|
}
|
|
|
|
// A rank-only edit does not require deleting/recreating inventory. Preserve the
|
|
// existing full-import path only when equipment, relics or avatar ownership change.
|
|
func reloadPlayerData(s *Session, next *common.FreesrData) error {
|
|
previous := s.JSON()
|
|
full := previous == nil
|
|
if !full {
|
|
full = !reflect.DeepEqual(previous.Lightcones, next.Lightcones) || !reflect.DeepEqual(previous.Relics, next.Relics) || len(previous.Avatars) != len(next.Avatars)
|
|
}
|
|
var changed []uint32
|
|
if !full {
|
|
for id, avatar := range next.Avatars {
|
|
old, exists := previous.Avatars[id]
|
|
if !exists {
|
|
full = true
|
|
break
|
|
}
|
|
if !reflect.DeepEqual(old, avatar) {
|
|
changed = append(changed, id)
|
|
}
|
|
}
|
|
}
|
|
s.SetJSON(next)
|
|
if full {
|
|
return s.SyncPlayer()
|
|
}
|
|
if len(changed) == 0 {
|
|
return nil
|
|
}
|
|
sortU32Slice(changed)
|
|
notify := &goproto.PlayerSyncScNotify{}
|
|
buildSync(next, notify, changed, nil, nil)
|
|
var err error
|
|
notify.MaterialList, err = eidolonMaterials(next)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
return s.Send(notify)
|
|
}
|