You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
425 lines
16 KiB
425 lines
16 KiB
import { PREVIEW } from "cc/env";
|
|
import { MainConfig } from "../../Launch/_MainConfig";
|
|
import { Director, director, sys } from "cc";
|
|
import { ESceneName } from "../const/GameEnum";
|
|
import FileManager from "../Framework/FileTools/FileManager";
|
|
import { Utils } from "../ExUtils/Utils";
|
|
import DataInstanceT from "../ExUtils/DataInstanceT";
|
|
import { TDAnalyticsMgr } from "../Mgr_Ge/TDAnalyticsMgr";
|
|
import { GEData } from "../Mgr_Ge/GeDifine";
|
|
import PlatformData from "../Platform/Data/PlatformData";
|
|
import { PlatformCommonDefine } from "../Platform/Common/PlatformCommonDefine";
|
|
|
|
export default class LocalStorage{
|
|
static readonly GAME_DATA_NAME: string = `${MainConfig.Name}-${`CatCat`}`;
|
|
static readonly LoginKey:string = "LoginTime"
|
|
static m_mapLocalData: { [key: string]: any } = {};
|
|
static mMapLocalDataJson: string = ``;
|
|
/**标记更新*/
|
|
static mDirty: boolean = false;
|
|
static mLoadComplete:boolean = false;
|
|
static mReBuilding:boolean = false; //是否正在重新构建数据
|
|
/**是否分离Jsonstringify与localStorage */
|
|
static mStringifySplit: boolean = false;
|
|
/**是否支持监听游戏关闭或者结束 暂未实现请自己在关闭游戏时进行处理 */
|
|
static mSupListen: boolean = false;
|
|
static mDebugTime: boolean = false;
|
|
/**时间记录 */
|
|
static time:number = 0;
|
|
static frame:number = 0;
|
|
static maxFrame:number = 5;
|
|
private static isSaveing:boolean =false;
|
|
private static saveTime: number = 0;
|
|
private static mstime:number = 0;
|
|
private static GameTime = 0;
|
|
private static LastGameTime = 0;
|
|
private static chekcTime = 30*1000;
|
|
private static LoginDay:number = 0;
|
|
|
|
private static mPlatformData:PlatformData;
|
|
private static mLoginState:PlatformCommonDefine.LoginState;
|
|
/**添加事件触发 */
|
|
static addEvent(){
|
|
this.mstime = Date.now();
|
|
this.LastGameTime = this.mstime;
|
|
this.GameTime = this.mstime;
|
|
director.targetOff(this)
|
|
director.on(Director.EVENT_AFTER_DRAW, this.SaveGameData, this);
|
|
}
|
|
|
|
private static isNewUserKey:string = "NewUser";
|
|
private static _isNewUser:boolean = false;
|
|
|
|
static get isNewUser():boolean{
|
|
return this._isNewUser;
|
|
}
|
|
|
|
static set isNewUser(value: boolean) {
|
|
this.setItem(this.isNewUserKey, true, true);
|
|
this._isNewUser = value;
|
|
this.mDirty = true;
|
|
}
|
|
private static ADKey:string = "ADKey";
|
|
private static _ad_cnt: number = 0;
|
|
|
|
static get ad_cnt() {
|
|
return this._ad_cnt;
|
|
}
|
|
|
|
static set ad_cnt(value: number) {
|
|
this._ad_cnt = value;
|
|
this.setItem(this.ADKey, this._ad_cnt);
|
|
}
|
|
|
|
static InitServerGameData(_PlatformData:PlatformData,_loginState:PlatformCommonDefine.LoginState,callBack: Function) {
|
|
this.mPlatformData = _PlatformData;
|
|
this.mLoginState = _loginState;
|
|
this.getServerData((json: string) => {
|
|
this.InitGameData(json, callBack);
|
|
// if (this.m_mapLocalData["_ShopData"] && this.m_mapLocalData["_ShopData"]["times"] < 0) {
|
|
// this.m_mapLocalData["_ShopData"]["times"] = 50;
|
|
// }
|
|
if (this.m_mapLocalData["_TokenData"] && this.m_mapLocalData["_TokenData"]["Token"]["1"] < 0) {
|
|
this.m_mapLocalData["_TokenData"]["Token"]["1"] = 3000000;
|
|
}
|
|
})
|
|
}
|
|
|
|
/**初始化游戏缓存数据 */
|
|
static InitGameData(serverJson:string,callBack:Function) {
|
|
/**获取本地数据 */
|
|
this.mMapLocalDataJson = sys.localStorage.getItem(this.GAME_DATA_NAME);
|
|
if (!this.mMapLocalDataJson) {
|
|
/**如果拥有服务器数据 */
|
|
if (serverJson) {
|
|
let tampData = JSON.parse(serverJson) || {};
|
|
this.m_mapLocalData = tampData;
|
|
this.saveTime = tampData.lastTime || 0;
|
|
} else {
|
|
this.mMapLocalDataJson = "{}";
|
|
this.m_mapLocalData = JSON.parse(this.mMapLocalDataJson) || {};
|
|
}
|
|
} else {
|
|
if (serverJson) {
|
|
let tampData = JSON.parse(serverJson) || {};
|
|
this.saveTime = tampData.lastTime || 0;
|
|
let templocalData = JSON.parse(this.mMapLocalDataJson) || {};
|
|
if(tampData["_GameData"] && tampData["_PassData"] && templocalData["_GameData"] && templocalData["_PassData"]){
|
|
const serverlevelid = tampData["_GameData"]["mLevelData"]["id"] + tampData["_PassData"]["passed_times"] * 21;
|
|
const locallevelid = templocalData["_GameData"]["mLevelData"]["id"] + templocalData["_PassData"]["passed_times"] * 21;
|
|
if(serverlevelid <= locallevelid){
|
|
ConsoleEx.Com("本地数据更新: " + serverlevelid + " <= " + locallevelid)
|
|
this.m_mapLocalData = templocalData;
|
|
}
|
|
}else{
|
|
this.m_mapLocalData = tampData;
|
|
}
|
|
}else{
|
|
this.m_mapLocalData = JSON.parse(this.mMapLocalDataJson) || {};
|
|
}
|
|
}
|
|
|
|
this.time = Date.now();
|
|
let LoginTime = this.getItem(this.LoginKey);
|
|
if (!LoginTime) {
|
|
this.setItem(this.LoginKey, Date.now());
|
|
this.LoginDay = 1;
|
|
} else {
|
|
this.LoginDay = Math.floor((this.time - LoginTime) / 1000 / (24 * 60 * 60)) + 1;
|
|
}
|
|
|
|
let _time = Date.now() - this.time;
|
|
this.time = 0;
|
|
//判断时间差
|
|
if (_time > 50) {
|
|
ConsoleEx.Error('数据读取时间过长', this.GAME_DATA_NAME, _time);
|
|
}
|
|
this._isNewUser = !this.getItem(this.isNewUserKey);
|
|
this._ad_cnt = +this.getItem(this.ADKey) || 0;
|
|
callBack && callBack();
|
|
}
|
|
|
|
private static getServerData( Back: (str:string)=>void) {
|
|
const platformData = this.mPlatformData;
|
|
const loginState = this.mLoginState;
|
|
let base = window["wx"] || window["tt"] || window["ks"];
|
|
if (!base || !platformData.appId || !loginState.openid) {
|
|
!PREVIEW && ConsoleEx.Error("获取存档失败",base,platformData.appId,loginState.openid);
|
|
Back && Back(null);
|
|
return;
|
|
}
|
|
|
|
let data = {
|
|
app_id: platformData.appId,
|
|
open_id: loginState.openid,
|
|
}
|
|
base.request({
|
|
url: `https://game-api.lvzhouyouxi.com/user/game_data`, // 本地服务地址
|
|
method: 'GET',
|
|
data: data,
|
|
header: { 'Content-Type': 'application/json' },
|
|
success: (resp) => {
|
|
console.log('*********************', resp)
|
|
// console.warn("获取的存档数据", resp.data.game_data)
|
|
Back && Back(resp.data.game_data);
|
|
},
|
|
fail: (errString) => {
|
|
console.error(errString);
|
|
Back && Back(null);
|
|
},
|
|
complete: (message) => {
|
|
}
|
|
});
|
|
}
|
|
|
|
static CheckSaveServerData(Back?: (isError: boolean) => void) {
|
|
if (this.saveTime < this.m_mapLocalData["lastTime"]) {
|
|
this.saveServerData(Back);
|
|
} else {
|
|
Back && Back(true);
|
|
}
|
|
}
|
|
|
|
static getCloudDiffTime() {
|
|
return this.m_mapLocalData["lastTime"] - this.saveTime;
|
|
}
|
|
|
|
static saveServerData(Back: (isError:boolean)=>void) {
|
|
if (this.isSaveing) { return; }
|
|
this.isSaveing = true;
|
|
const platformData = this.mPlatformData;
|
|
const loginState = this.mLoginState;
|
|
let base = window["wx"] || window["tt"] || window["ks"];
|
|
if (!base || !platformData.appId || !loginState.openid) {
|
|
!PREVIEW && ConsoleEx.Error("存档失败",base,platformData.appId,loginState.openid);
|
|
Back && Back(false);
|
|
this.isSaveing = false;
|
|
return;
|
|
}
|
|
|
|
if (!this.m_mapLocalData["lastTime"]) {
|
|
this.m_mapLocalData["lastTime"] = Date.now();
|
|
}
|
|
let time = this.m_mapLocalData["lastTime"];
|
|
let data = {
|
|
app_id: platformData.appId,
|
|
open_id: loginState.openid,
|
|
game_data: this.mMapLocalDataJson,
|
|
}
|
|
|
|
let sync_time_start = Date.now();
|
|
|
|
base.request({
|
|
url: `https://game-api.lvzhouyouxi.com/user/game_data`, // 本地服务地址
|
|
method: 'POST',
|
|
data: data,
|
|
header: { 'Content-Type': 'application/json' },
|
|
success: (resp) => {
|
|
console.log('*********************', resp)
|
|
console.warn("保存存档数据", resp.data.game_data)
|
|
this.saveTime = time;
|
|
this.isSaveing = false;
|
|
let sync_time = (Date.now() - sync_time_start) / 1000;
|
|
sync_time = +sync_time.toFixed(2)
|
|
TDAnalyticsMgr.ins.TrySendtrack(GEData.GEeventName.sync_data, {sync_time: sync_time});
|
|
Back && Back(true);
|
|
},
|
|
fail: (errString) => {
|
|
console.error(errString);
|
|
Back && Back(false);
|
|
this.isSaveing = false;
|
|
},
|
|
complete: (message) => {
|
|
|
|
}
|
|
});
|
|
}
|
|
|
|
static setLodingComplete(){
|
|
this.mLoadComplete = true;
|
|
}
|
|
|
|
static tryEventSend(){
|
|
this.mstime = Date.now();
|
|
if ((this.mstime - this.LastGameTime) >= this.chekcTime) {
|
|
this.LastGameTime = this.mstime;
|
|
let time = this.mstime - this.GameTime;
|
|
let length = Math.floor(Utils.MathUtils.MsToFloat(time));
|
|
ConsoleEx.Log(`游玩时长:第${this.LoginDay}天 游玩时长:${length}`);
|
|
// TDAnalyticsMgr.ins.TrySendtrack(GEData.GEeventName.play_time, { day: this.LoginDay, length: length });
|
|
}
|
|
}
|
|
|
|
/**保存游戏数据 */
|
|
static SaveGameData(dt:number) {
|
|
this.tryEventSend();
|
|
if (!this.mLoadComplete) { return; }
|
|
if (!this.mDirty) { return; }
|
|
if (this.mReBuilding) { return; }
|
|
/**处于新用户阶段 不保存数据 */
|
|
//if (this.isNewUser) { return; }
|
|
// this.frame++;
|
|
// if(this.frame<this.maxFrame){return;}
|
|
// this.frame = 0;
|
|
this.mDebugTime && console.time();
|
|
this.time = performance.now();
|
|
if (!this.mStringifySplit) {
|
|
this.m_mapLocalData["lastTime"] = Date.now();
|
|
this.mMapLocalDataJson = JSON.stringify(this.m_mapLocalData,null, 0)
|
|
this.mDebugTime && ConsoleEx.Log("执行了Json时间:",performance.now() - this.time)
|
|
}
|
|
this.saveData();
|
|
this.mDebugTime && console.timeEnd();
|
|
//判断时间
|
|
let _time = performance.now() - this.time;
|
|
this.time = 0;
|
|
this.mDebugTime && ConsoleEx.Log("等待写入测试时间2:",_time)
|
|
//判断时间差
|
|
if (_time > 50) {
|
|
ConsoleEx.Error('数据保存时间过长', this.GAME_DATA_NAME, _time);
|
|
}
|
|
this.mDirty = false;
|
|
this.mDebugTime && ConsoleEx.Log(this.mMapLocalDataJson)
|
|
}
|
|
|
|
/**获取缓存数据 */
|
|
static getItem(key) {
|
|
return this.m_mapLocalData[key]
|
|
}
|
|
|
|
/**设置缓存数据 */
|
|
static setItem(key: string, value: any, isSave: boolean = false) {
|
|
this.m_mapLocalData[`${key}`] = value;
|
|
this.mDirty = true;
|
|
if (this.mStringifySplit || isSave) {
|
|
this.m_mapLocalData["lastTime"] = Date.now();
|
|
this.mMapLocalDataJson = JSON.stringify(this.m_mapLocalData,null, 0)
|
|
}
|
|
isSave && (this.mDirty = false)
|
|
isSave && this.saveData();
|
|
}
|
|
|
|
/**保存数据 */
|
|
static saveData(){
|
|
sys.localStorage.setItem(this.GAME_DATA_NAME, this.mMapLocalDataJson)
|
|
}
|
|
|
|
/**重置所有数据 */
|
|
static reBuildAllData(){
|
|
DataInstanceT.ReBuildData();
|
|
DataInstanceT.initData();
|
|
DataInstanceT.initLogic();
|
|
}
|
|
|
|
/**清除所有 */
|
|
static clearAll() {
|
|
|
|
DataInstanceT.ClearData();
|
|
localStorage.clear();
|
|
this.m_mapLocalData = {};
|
|
this.mMapLocalDataJson = JSON.stringify(this.m_mapLocalData,null, 0)
|
|
this.saveData();
|
|
}
|
|
|
|
/**清除某个key的数据 */
|
|
static clearDataByKey(key: string) {
|
|
delete this.m_mapLocalData[`${key}`];
|
|
this.mMapLocalDataJson = JSON.stringify(this.m_mapLocalData,null, 0)
|
|
this.saveData();
|
|
}
|
|
|
|
static readJsonFile(callback:Function){
|
|
FileManager.ins().mFileTools.openLocalFileCallBack((file) => {
|
|
let data = null;
|
|
if(file?.value){
|
|
data = file?.value;
|
|
}else if(file?.json){
|
|
if(typeof file.json == "string"){
|
|
data = file.json;
|
|
}else{
|
|
data = JSON.stringify(file.json);
|
|
}
|
|
}
|
|
if(!data){ConsoleEx.Error("数据读取失败",file); return;}
|
|
callback && callback();
|
|
let scene = director.getScene();
|
|
for (let i = 0; i < scene.children.length; i++) {
|
|
const tNode = scene.children[i];
|
|
if (director.isPersistRootNode(tNode)) {
|
|
director.removePersistRootNode(tNode)
|
|
ConsoleEx.Log(tNode.name)
|
|
}
|
|
}
|
|
LocalStorage.readJson(data);
|
|
director.loadScene(ESceneName.Launch);
|
|
}, ".json");
|
|
}
|
|
|
|
static readJson(json:string){
|
|
this.clearAll();
|
|
this.mLoadComplete = false;
|
|
this.mDirty = false;
|
|
this.m_mapLocalData = JSON.parse(json) || {};
|
|
this.mMapLocalDataJson = JSON.stringify(this.m_mapLocalData,null, 0)
|
|
this.saveData();
|
|
}
|
|
|
|
static getSaveJson(){
|
|
return JSON.stringify(this.m_mapLocalData,null, 0);
|
|
}
|
|
|
|
static SaveToLocal(){
|
|
FileManager.ins().mFileTools.ProjectWriteStringToFile(LocalStorage.getSaveJson(),`${MainConfig.ZHName}${"存档"}.json`);
|
|
}
|
|
|
|
static getUserInfo(appId:string,openid:string){
|
|
let xhr: XMLHttpRequest = new XMLHttpRequest();
|
|
xhr.open('GET', `https://game-api.lvzhouyouxi.com/user/game_data?app_id=${appId}&open_id=${openid}`, true);
|
|
xhr.onreadystatechange = () => {
|
|
if (xhr.readyState === 4 && (xhr.status >= 200 && xhr.status < 300)) {
|
|
if (xhr.responseText.length > 0) {
|
|
let data = JSON.parse(xhr.responseText);
|
|
let game_data = JSON.stringify(JSON.parse(data.game_data))
|
|
FileManager.ins().mFileTools.ProjectWriteStringToFile(game_data,`${appId}-${openid}.json`);
|
|
} else {
|
|
|
|
}
|
|
}
|
|
}
|
|
xhr.onerror = () => {
|
|
console.error("拉取存档错误");
|
|
}
|
|
xhr.send();
|
|
}
|
|
|
|
static setUserInfo(appId: string, openid: string,json:string) {
|
|
let xhr: XMLHttpRequest = new XMLHttpRequest();
|
|
xhr.open('POST', `https://game-api.lvzhouyouxi.com/user/game_data`, true);
|
|
xhr.setRequestHeader('Content-Type','application/json' );
|
|
xhr.onreadystatechange = () => {
|
|
if (xhr.readyState === 4 && (xhr.status >= 200 && xhr.status < 300)) {
|
|
if (xhr.responseText.length > 0) {
|
|
let data = JSON.parse(xhr.responseText);
|
|
ConsoleEx.Log("存档成功!",xhr.responseText)
|
|
} else {
|
|
|
|
}
|
|
}
|
|
}
|
|
xhr.onerror = () => {
|
|
console.error("存档错误");
|
|
}
|
|
|
|
let data = {
|
|
app_id: appId,
|
|
open_id: openid,
|
|
game_data: json,
|
|
}
|
|
|
|
xhr.send(JSON.stringify(data));
|
|
}
|
|
}
|
|
|
|
if (PREVIEW) {
|
|
window['LocalStorage'] = LocalStorage;
|
|
}
|