import { _decorator, AssetManager, AudioClip, BufferAsset, Button, Component, ImageAsset, instantiate, JsonAsset, Label, Material, Node, Prefab, ProgressBar, Sprite, SpriteFrame, Vec3, VideoPlayer, } from "cc"; import { GButton } from "../../Main/Common/GButton"; import ResManager from "../../Main/Manager/ResManager"; import { SDKManager } from "../../Main/Channel/SDKManager"; import HttpUnit from "../../Main/Common/HttpUnit"; import GlobalValue from "../../Main/Common/GlobalValue"; import Utils from "../../Main/Common/Utils"; import { InnerMsgCode } from "../../Main/Config/InnerMsgCode"; import { promptItem } from "../Item/promptItem"; import LanguageUtils, { LanguageType } from "../../Main/Common/LanguageUtils"; import { DataId, DataManager } from "../../chat18x/data/DataManager"; import { ConfigManager } from "../../chat18x/manager/ConfigManager"; import { AppConfig } from "db://assets/Scripts/chat18x/config/env/appConfig"; import DeviceIdService from "db://assets/Scripts/chat18x/foundation/identity/DeviceIdService"; import { AccountData } from "../../chat18x/data/AccountData"; import { EnvData } from "../../chat18x/data/EnvData"; import { GlobalData } from "../../chat18x/data/GlobalData"; import { AiCharacterData } from "../../chat18x/data/AiCharacterData"; import { LoginData } from "../../chat18x/data/LoginData"; import { PlayerData } from "../../chat18x/data/PlayerData"; import { WalletData } from "../../chat18x/data/WalletData"; import MachineInfoService from "../../chat18x/foundation/identity/MachineInfoService"; import { AuthService } from "../../chat18x/network/services/AuthService"; import { CommonService } from "../../chat18x/network/services/CommonService"; import { PlayerDataService } from "../../chat18x/network/services/PlayerDataService"; import proto from "db://assets/Scripts/proto/proto.pb.js"; import { ViewManager } from "../../Main/Manager/ViewManager"; import { MainScene } from "../MainScene"; import { prodConfig } from "../../chat18x/config/env/prod"; import { logger } from "db://assets/Scripts/Main/Common/Logger"; import AudioManager from "../../Main/Manager/AudioManager"; import { Config18x } from "../../Main/Config/Config18x"; import { MainController } from "../../chat18x/core/MainController"; import GameRootUI from "../../Main/Common/GameRootUI"; import { TipsPanel } from "../../chat18x/ui/panels/TipsPanel"; const { ccclass, property } = _decorator; @ccclass("PreloadUI") export class PreloadUI extends Component { @property(MainScene) mainScene: MainScene = null; private _nodeTab: any = {}; private preloadFinish = false; //资源加载完成 private loginFinish = false; //登录完成 loginBtn: Node; private jinduBar: Node = null; private jinduFilled: Sprite = null; private VideoPlayer: VideoPlayer; private appVersion: Label; private progressNode: Node; private loginLabel: Label; private desc: Label; // 视频播放状态跟踪 private videoPlayed: boolean = false; private videoPlayRetryCount: number = 0; private maxVideoPlayRetry: number = 3; start() { //Utils.addInnerEL(InnerMsgCode.UI_ShowPrompt, this, this.resiveShowPrompt) Utils.parseNode(this.node, this._nodeTab); // 添加新的事件监听 this.progressNode = this._nodeTab.progress; this.appVersion = this._nodeTab.appVersion.getComponent(Label); this.loginBtn = this._nodeTab.btnLogin; this.loginBtn.active = false; this.appVersion.string = `app version: ${prodConfig.appVersion}`; this.VideoPlayer = this._nodeTab.VideoPlayer.getComponent(VideoPlayer); this.loginLabel = this._nodeTab.loginLabel.getComponent(Label); this.desc = this._nodeTab.Desc.getComponent(Label); // 设置视频为静音,提高移动端自动播放成功率 this.VideoPlayer.mute = true; this.VideoPlayer.loop = true; this.VideoPlayer.stayOnBottom = true; this.VideoPlayer.node.on( VideoPlayer.EventType.META_LOADED, this.onVideoReadyToPlay, this ); // 监听播放失败事件 this.VideoPlayer.node.on( VideoPlayer.EventType.PLAYING, this.onVideoPlaying, this ); GButton.BandClick(this.loginBtn, this.onLogin, this); this.jinduBar = this.node.getChildByName("jinduBar"); this.jinduFilled = this.jinduBar .getChildByName("jinduFilled") .getComponent(Sprite); //适配背景图 //let BG = this.node.getChildByName("BG"); //Utils.adjustBgPixelRatio(BG, 1); this.jinduFilled.fillRange = 0; // 移除直接播放调用,等待 META_LOADED 事件后再播放 // if (!this.VideoPlayer.isPlaying) this.VideoPlayer.play(); //初始化显示 switch (LanguageUtils.CurrentLanguage) { case LanguageType.CN: this.loginLabel.string = "登录"; this.desc.string = "释放你的所有欲望"; break; case LanguageType.EN: this.loginLabel.string = "LOG IN"; this.desc.string = "Unleash All Your Desires"; break; case LanguageType.HI: this.loginLabel.string = "लॉग इन"; this.desc.string = "अपनी सारी इच्छाओं को मुक्त करें"; break; default: break; } // 初始化配置 ConfigManager.I.init(); //logger.log(ConfigManager.tables.TbGlobalConfig.GameName); // 初始化环境配置 AppConfig.I; // 初始化数据层 DataManager.I.init(); // 设备号 DeviceIdService.I.init(); AudioManager.I.PlayMusic(Config18x.AudioConfig.MainBGM); SDKManager.I.init(); this.preloadFiles(); this.mainScene.init(); } protected onDestroy(): void { // 清理视频事件监听器 if (this.VideoPlayer && this.VideoPlayer.node) { this.VideoPlayer.node.off( VideoPlayer.EventType.META_LOADED, this.onVideoReadyToPlay, this ); this.VideoPlayer.node.off( VideoPlayer.EventType.PLAYING, this.onVideoPlaying, this ); this.VideoPlayer.stop(); } } onVideoReadyToPlay() { logger.log("PreloadUI: Video metadata loaded, attempting to play"); this.tryPlayVideo(); } /** * 尝试播放视频,带重试机制和错误处理 */ private tryPlayVideo() { if (this.videoPlayed) { logger.log("PreloadUI: Video already playing, skip"); return; } if (!this.VideoPlayer) { logger.error("PreloadUI: VideoPlayer not initialized"); return; } // 尝试播放视频 try { this.VideoPlayer.play(); logger.log( `PreloadUI: Video play attempted (retry: ${this.videoPlayRetryCount}/${this.maxVideoPlayRetry})` ); // 延迟检查播放状态,如果失败则重试 this.scheduleOnce(() => { if ( !this.VideoPlayer.isPlaying && this.videoPlayRetryCount < this.maxVideoPlayRetry ) { this.videoPlayRetryCount++; logger.warn( `PreloadUI: Video play failed, retrying... (${this.videoPlayRetryCount}/${this.maxVideoPlayRetry})` ); this.tryPlayVideo(); } else if (!this.VideoPlayer.isPlaying) { logger.warn( "PreloadUI: Video autoplay failed after max retries. Will retry on user interaction." ); } }, 0.5); } catch (error) { logger.error("PreloadUI: Video play error:", error); if (this.videoPlayRetryCount < this.maxVideoPlayRetry) { this.videoPlayRetryCount++; this.scheduleOnce(() => { this.tryPlayVideo(); }, 1.0); } } } /** * 视频开始播放回调 */ private onVideoPlaying() { logger.log("PreloadUI: Video is now playing"); this.videoPlayed = true; } update(deltaTime: number) { if (!this.preloadFinish) { return; //this.goToLoginScene(); } if (this.loginFinish) { this.loginFinish = false; this.preloadFinish = false; this.enterGame(); } } //预加载文件 preloadFiles() { let preloadTab = [ { path: "ChatPanel", bundleName: "Chat18x", ftype: Prefab }, { path: "GirlDetailPanel", bundleName: "Chat18x", ftype: Prefab }, { path: "GirlListPanel", bundleName: "Chat18x", ftype: Prefab }, { path: "tblanguage", bundleName: "DataTable", ftype: BufferAsset }, ]; let num_prefab = 0; //已加载数量 let num_succeed = 0; //加载成功数量 let preloadFunc = () => { if (num_prefab < preloadTab.length) { let cfg = preloadTab[num_prefab]; ResManager.I.preLoadSubpackageFile( cfg.path, cfg.bundleName, cfg.ftype, (ret) => { num_prefab++; num_succeed++; let percent = 0.45 * (num_prefab / preloadTab.length); this.showLoadProgress(0.55 + percent); logger.log("加载成功:", cfg.path); preloadFunc(); }, (err) => { num_prefab++; logger.log("加载失败:", err); } ); } else { if (num_succeed >= num_prefab) { this.startloginProcess(); } } }; preloadFunc(); } //加载配置表 startloginProcess() { this.jinduBar.active = false; this.preloadFinish = true; this.loginBtn.active = true; } //显示加载进度 showLoadProgress(percent) { this.jinduFilled.fillRange = percent; this.progressNode.setPosition(new Vec3(percent * 546, 0, 0)); } // 跳转到登录场景 // private goToLoginScene() { // this.jinduBar.active = false; // ResManager.I.goCustomScene("LoginScene"); // } async onLogin() { // 用户交互时尝试播放视频(如果自动播放失败) if (!this.videoPlayed && this.VideoPlayer) { logger.log("PreloadUI: User interaction detected, trying to play video"); this.videoPlayRetryCount = 0; // 重置重试计数 this.tryPlayVideo(); } const deviceId = DeviceIdService.I.id; const os = MachineInfoService.I.getMachineOs(); const qs = new URLSearchParams(window.location.search); const fbCode = qs.get("fbCode"); const reqData = { platType: "guest", userId: fbCode ? fbCode : deviceId, device: deviceId, os, }; logger.log("登录请求数据:", reqData); let res = await AuthService.I.login(reqData); logger.log("登录响应数据:", res); if (res && res.code === proto.cs.EnmRetCode.SUCCESS) { const resData = res.data; const loginData = DataManager.I.getDataById(DataId.Login); loginData.token = resData.token; loginData.refreshToken = resData.refreshToken; loginData.expire = Number(resData.expire); const playerData = DataManager.I.getDataById(DataId.Player); playerData.name = resData.name; const accountData = DataManager.I.getDataById( DataId.Account ); accountData.accId = resData.accId; const envData = DataManager.I.getDataById(DataId.Env); envData.cdn = resData.cdn; this.loginFinish = true; this.reqMyInfo(); this.reqGlobalData(); this.reqAiCharacterData(); } else { TipsPanel.show(LanguageUtils.getText("error_code_" + res.code)); } } // 请求个人数据 private async reqMyInfo() { const reqData = {}; let res = await PlayerDataService.I.reqMyInfo(reqData); logger.log("个人信息响应数据:", res); if (res && res.code === proto.cs.EnmRetCode.SUCCESS) { const resData = res.data; const walletData = DataManager.I.getDataById(DataId.Wallet); walletData.balance = Number(resData.balance); walletData.vipExpire = Number(resData.vipExpire); } else { TipsPanel.show(LanguageUtils.getText("error_code_" + res.code)); } } // 请求全局数据 private async reqGlobalData() { const reqData = { resName: "TbGlobalConfig", }; let res = await CommonService.I.reqResConfig(reqData); if (res && res.code === proto.cs.EnmRetCode.SUCCESS) { // 保存数据 const globalData = DataManager.I.getDataById(DataId.Global); globalData.globals = res.data; } else { TipsPanel.show(LanguageUtils.getText("error_code_" + res.code)); } } // 请求Ai角色配置 private async reqAiCharacterData() { const reqData = { resName: "TbAiCharacters", }; let res = await CommonService.I.reqResConfig(reqData); if (res && res.code === proto.cs.EnmRetCode.SUCCESS) { // 保存数据 const aiCharacterData = DataManager.I.getDataById( DataId.AiCharacter ); aiCharacterData.aiCharacter = res.data; } else { TipsPanel.show(LanguageUtils.getText("error_code_" + res.code)); } } private async enterGame() { await MainController.I.init(); this.node.destroy(); GameRootUI.I.showDefault(); //ResManager.I.goMainScene(); } }