[add] Engine
This commit is contained in:
153
assets/Script/Engine/Component/Animation/AnimationRandomPlay.ts
Normal file
153
assets/Script/Engine/Component/Animation/AnimationRandomPlay.ts
Normal file
@@ -0,0 +1,153 @@
|
||||
const { ccclass, property, requireComponent, menu } = cc._decorator;
|
||||
|
||||
@ccclass("State_AnimationRandomPlay")
|
||||
export class State_AnimationRandomPlay {
|
||||
@property({ displayName: "最少時間", type: cc.Float })
|
||||
public mintime: number = 0;
|
||||
@property({ displayName: "最多時間", type: cc.Float })
|
||||
public maxtime: number = 0;
|
||||
@property({ displayName: "權重", type: cc.Integer })
|
||||
public weight: number = 0;
|
||||
@property({ displayName: "動畫", type: cc.AnimationClip })
|
||||
public clip: cc.AnimationClip = null;
|
||||
}
|
||||
|
||||
@ccclass
|
||||
@menu("Plug-in/Animation/AnimationRandomPlay")
|
||||
@requireComponent(cc.Animation)
|
||||
/** 可以根據權重決定多久後隨機播放甚麼動畫 */
|
||||
export class AnimationRandomPlay extends cc.Component {
|
||||
//#region public 外調參數
|
||||
|
||||
@property({ type: State_AnimationRandomPlay })
|
||||
public states: State_AnimationRandomPlay[] = [];
|
||||
|
||||
//#endregion
|
||||
|
||||
//#region public 屬性
|
||||
|
||||
public nowPlayName: string = "";
|
||||
public nextPlayName: string = "";
|
||||
public nextPlayTime: number = null;
|
||||
|
||||
//#endregion
|
||||
|
||||
//#region private 屬性
|
||||
|
||||
private _animation: cc.Animation = null;
|
||||
private _weightAll: number[] = [];
|
||||
private _weightAllNum: number = 0;
|
||||
|
||||
//#endregion
|
||||
|
||||
//#region get set
|
||||
|
||||
get animation(): cc.Animation {
|
||||
if (this._animation == null) {
|
||||
this._animation = this.node.getComponent(cc.Animation);
|
||||
}
|
||||
return this._animation;
|
||||
}
|
||||
|
||||
//#endregion
|
||||
|
||||
//#region Lifecycle
|
||||
|
||||
onLoad(): void {
|
||||
let self: this = this;
|
||||
let weight: number = 0;
|
||||
for (let i: number = 0; i < this.states.length; i++) {
|
||||
weight += this.states[i].weight;
|
||||
this._weightAll.push(weight);
|
||||
this._weightAllNum += this.states[i].weight;
|
||||
}
|
||||
|
||||
// 一般動畫
|
||||
this.animation.on("finished", () => {
|
||||
self.GetNextAnim();
|
||||
}, this);
|
||||
|
||||
// 不一般動畫 (X
|
||||
// Loop動畫
|
||||
this.animation.on("lastframe", () => {
|
||||
self.animation.setCurrentTime(0);
|
||||
self.animation.stop();
|
||||
self.GetNextAnim();
|
||||
}, this);
|
||||
}
|
||||
|
||||
onEnable(): void {
|
||||
this.GetNextAnim();
|
||||
}
|
||||
|
||||
onDisable(): void {
|
||||
this.nextPlayName = "";
|
||||
this.nextPlayTime = null;
|
||||
this.animation.setCurrentTime(0);
|
||||
this.animation.stop();
|
||||
}
|
||||
|
||||
onDestroy(): void {
|
||||
this.animation.targetOff(this);
|
||||
// let self: this = this;
|
||||
// this.animation.off("finished", () => {
|
||||
// self.GetNextAnim();
|
||||
// }, this);
|
||||
// this.animation.off("lastframe", () => {
|
||||
// self.animation.setCurrentTime(0);
|
||||
// self.animation.stop();
|
||||
// self.GetNextAnim();
|
||||
// }, this);
|
||||
}
|
||||
|
||||
update(dt: number): void {
|
||||
let time: number = Date.now();
|
||||
if (this.nextPlayTime && time >= this.nextPlayTime) {
|
||||
this.nowPlayName = this.nextPlayName;
|
||||
if (this.animation.getAnimationState(this.nextPlayName)) {
|
||||
this.animation.play(this.nextPlayName);
|
||||
} else {
|
||||
console.error(`this node(${this.node.name}) not has animation(${this.nextPlayName})`);
|
||||
this.animation.addClip(this.GetClip_From_states(this.nextPlayName));
|
||||
if (this.animation.getAnimationState(this.nextPlayName)) {
|
||||
console.warn(`this node(${this.node.name}) add animation(${this.nextPlayName})`);
|
||||
this.animation.play(this.nextPlayName);
|
||||
}
|
||||
}
|
||||
this.nextPlayName = "";
|
||||
this.nextPlayTime = null;
|
||||
}
|
||||
}
|
||||
|
||||
//#endregion
|
||||
|
||||
//#region Custom Function
|
||||
|
||||
/** 取得下一隻動畫的時間&名稱 */
|
||||
GetNextAnim(): void {
|
||||
let random: number = Math.floor(Math.random() * this._weightAllNum) + 1;
|
||||
for (let i: number = 0; i < this._weightAll.length; i++) {
|
||||
if (random <= this._weightAll[i]) {
|
||||
let time: number = Math.floor(Math.random() * (this.states[i].maxtime - this.states[i].mintime + 1)) + this.states[i].mintime;
|
||||
this.nextPlayTime = Date.now() + (time * 1000);
|
||||
this.nextPlayName = this.states[i].clip.name;
|
||||
// if (CC_DEBUG) {
|
||||
// let date: Date = new Date(this.nextPlayTime);
|
||||
// console.log(`nextWaitTime: ${time}, nextPlayTime: ${date.getHours()}:${date.getMinutes()}:${date.getSeconds()}, nextPlayName: ${this.nextPlayName}`);
|
||||
// }
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/** 取得下一隻動畫的時間&名稱 */
|
||||
GetClip_From_states(name: string): cc.AnimationClip {
|
||||
for (let i: number = 0; i < this.states.length; i++) {
|
||||
if (this.states[i].clip.name === name) {
|
||||
return this.states[i].clip;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//#endregion
|
||||
}
|
||||
Reference in New Issue
Block a user