import { _decorator, Animation, AnimationClip, Component, isValid, IVec2, Sprite, SpriteAtlas, SpriteFrame } from "cc"; import FrameJsonCfg from "./FrameJsonCfg"; import { FrameAnima } from "../const/GameInterface"; import { EResUrls } from "../ResUrl/EResUrls"; import ResLoad from "../ResUrl/ResLoad"; import { Utils } from "../ExUtils/Utils"; const { ccclass, property, menu } = _decorator; @ccclass @menu("战斗场景显示/帧动画控制") export class FrameAniCtrl extends Component { /**CC动画播放器 */ @property(Animation) animation:Animation; /**当前正在播放的动画名称 */ _curAnimName:string; _loadComplete:Function; /**循环中 只执行一次的函数 */ _onceFrameEvent; /**动画数据 */ _animationClipInfoMap:Map = new Map(); /**动画数据 */ _animationClipFarme: Map = new Map(); Clear() { this.animation.stop(); this.animation.clips = []; } loadAnimation(list:FrameAnima[],CallBack?:Function,speed:number = 0.2,animation:string = null,loop:boolean =true){ this.animation.stop(); this.animation.node.getComponent(Sprite).spriteFrame = null; this.Clear(); this._curAnimName = ""; this._animationClipInfoMap.clear(); this._animationClipFarme.clear(); let complete: number = list.length; for (let i = 0; i < list.length; i++) { const tCnfAnima = list[i]; if(tCnfAnima.Atlas && tCnfAnima.Atlas.length){ let urls: string[] = []; for (let j = 0; j < tCnfAnima.frameNum; j++) { let url = tCnfAnima.headUrl + j; //+ "/spriteFrame" urls.push(url); } let key = `${tCnfAnima.bundle}_${tCnfAnima.headUrl}`; ResLoad.Ins.loadBundle(tCnfAnima.bundle,()=>{ ResLoad.Ins.AutoAtlas(EResUrls.Atlas(tCnfAnima.Atlas),tCnfAnima.bundle,(err,atlas:SpriteAtlas)=>{ if(err){ ConsoleEx.Error("怪物图集加载失败",tCnfAnima.Atlas); return; } if(!isValid(this.node)){return}; let res:SpriteFrame[] = []; let scale:IVec2[]= []; for (let i = 0; i < urls.length; i++) { const element = urls[i]; res.push(atlas.getSpriteFrame(element)); let sclae = FrameJsonCfg.getScaleList(tCnfAnima.bundle, tCnfAnima.Atlas, element); if (sclae) { scale.push({ x: sclae.x, y: sclae.y }); } } let tAnimationClip: AnimationClip = Utils.FrameClip.getAnimationClip(key,tCnfAnima.actionName,res,scale,speed); this._animationClipInfoMap.set(tCnfAnima.actionName, tAnimationClip); this.animation.addClip(tAnimationClip, tCnfAnima.actionName); this._animationClipFarme.set(tCnfAnima.actionName, res.length); complete--; if(complete<=0){ this.loadComplete(); if(animation){this.playAnim(animation,loop); } CallBack && CallBack(); } }); }) }else{ let urls: string[] = []; for (let j = 0; j < tCnfAnima.frameNum; j++) { let url = tCnfAnima.path + tCnfAnima.headUrl + j; urls.push(url + "/spriteFrame"); } ResLoad.Ins.Load(urls, tCnfAnima.bundle, SpriteFrame, (err, res: SpriteFrame[]) => { if (!res) { ConsoleEx.Error("怪物序列帧错误", urls) return; } if (!isValid(this.node)) { return }; let tAnimationClip: AnimationClip = AnimationClip.createWithSpriteFrames(res, 60); tAnimationClip.speed = speed; tAnimationClip.name = tCnfAnima.actionName; this._animationClipInfoMap.set(tCnfAnima.actionName, tAnimationClip); this.animation.addClip(tAnimationClip, tCnfAnima.actionName); this._animationClipFarme.set(tCnfAnima.actionName, res.length); complete--; if (complete <= 0) { this.loadComplete(); if (animation) { this.playAnim(animation, loop); } CallBack && CallBack(); } }); } } } loadComplete(){ this._loadComplete && this._loadComplete(); } clearAnimEvent(){ } onFrameEvent(){ } getFarmeTime(tName: string,speed:number = 0.2){ return ((this._animationClipFarme.get(tName) * 0.02) || 0.2)/speed; } playAnim(tName: string, isLoop: boolean = true, callBack: Function = null, loopOneEvent: Function = null, speed: number = 1) { if (this._curAnimName == tName) { return;} if(callBack){ this.animation.once(Animation.EventType.FINISHED,()=>{callBack && callBack(); },this); } let state = this.animation.getState(tName) let tAnimationClip = this.animation.clips.find((t1)=>{ return t1.name == tName; }); if(tAnimationClip){ if(isLoop){ tAnimationClip.wrapMode = AnimationClip.WrapMode.Loop; }else{ tAnimationClip.wrapMode = AnimationClip.WrapMode.Normal; } if(state){ if(isLoop){ state.wrapMode = AnimationClip.WrapMode.Loop; }else{ state.wrapMode = AnimationClip.WrapMode.Normal; } } this.animation.stop(); this.animation.play(tName); this._curAnimName = tName; } } }