[add] Engine

This commit is contained in:
2022-08-26 16:48:17 +08:00
parent f67e566f2a
commit d9c19f096c
197 changed files with 10626 additions and 0 deletions

View File

@@ -0,0 +1,13 @@
{
"ver": "1.1.3",
"uuid": "96902cc4-f71a-4909-b87d-f709fd0d5681",
"importer": "folder",
"isBundle": false,
"bundleName": "",
"priority": 1,
"compressionType": {},
"optimizeHotUpdate": {},
"inlineSpriteFrames": {},
"isRemoteBundle": {},
"subMetas": {}
}

View File

@@ -0,0 +1,16 @@
const { ccclass, requireComponent, menu } = cc._decorator;
@ccclass
@menu("Plug-in/Animation/AnimationAutoPlay")
@requireComponent(cc.Animation)
export default class AnimationAutoPlay extends cc.Component {
onEnable() {
let anim = this.getComponent(cc.Animation);
if (anim != null) {
let animationState = anim.play();
anim.sample(animationState.name);
}
}
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "c51bb156-b283-4e24-a738-317650150b9d",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View 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
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "66e6675c-c922-4952-9eb1-dc55aece8dc3",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,163 @@
import { CoroutineV2 } from "../../CatanEngine/CoroutineV2/CoroutineV2";
import { RandomEx } from "../../Utils/Number/RandomEx";
const { ccclass, property, requireComponent, menu } = cc._decorator;
@ccclass("State")
export class State {
@property()
public name: string = "";
@property({ type: cc.AnimationClip })
public clip: cc.AnimationClip = null;
@property()
public transitionTo: string = "";
}
@ccclass
@menu("Plug-in/Animation/Animator")
@requireComponent(cc.Animation)
export class Animator extends cc.Component {
@property({ displayName: "Default State" })
public defaultState: string = "";
@property({ type: State })
public states: State[] = [];
public nowPlayName: string = "";
_animation: cc.Animation = null;
/** 動畫速度 */
private _speed: number = 1;
get animation(): cc.Animation {
if (this._animation == null) {
this._animation = this.node.getComponent(cc.Animation);
}
return this._animation;
}
onLoad(): void {
if (CC_DEV) {
let animationClip: cc.AnimationClip[] = this.animation.getClips();
for (let s of this.states) {
let state: State = null;
for (let i: number = 0; i < animationClip.length; i++) {
const clip: cc.AnimationClip = animationClip[i];
if (s.clip != null && s.clip.name === clip.name) {
state = s;
break;
}
}
if (state === null) {
console.error(`node: ${this.node.name}, anim: ${s.clip?.name}, 動畫沒有掛在Animation上面`);
}
}
}
}
onEnable(): void {
this.stopState();
if (this.defaultState !== "") {
this.playState(this.defaultState);
}
}
onDisable(): void {
this.stopState();
}
/**
* runStateAndWait(動作機只會接一次動畫)
* @param name 動畫State的名稱
* @param callback callback 沒有transitionTo才會觸發
*/
public *runStateAndWait(name: string, callback: Function = null): any {
if (name === "") {
return;
}
this.animation.stop();
this.nowPlayName = name;
let state: State = null;
for (let s of this.states) {
if (s.name === name && s.clip != null && s.clip.isValid) {
state = s;
break;
}
}
if (state == null) {
return;
}
let animationState: cc.AnimationState = this.animation.play(state.clip.name);
animationState.speed = this.animation.currentClip.speed * this._speed;
this.animation.sample(animationState.name);
if (animationState.duration) {
yield CoroutineV2.WaitTime(animationState.duration);
}
if (callback && !state.transitionTo) {
callback();
}
yield* this.runStateAndWait(state.transitionTo, callback);
}
/** playState(動作機只會接一次動畫) */
public playState(name: string, callback: Function = null): void {
if (!this.node?.activeInHierarchy) {
cc.warn(`Animator error name: ${this.node.name}, activeInHierarchy: ${this.node.activeInHierarchy}`);
}
CoroutineV2.Single(this.runStateAndWait(name, callback)).Start(this);
}
/** playState(隨機) */
public playRandomState(callback: Function = null): void {
let random: number = RandomEx.GetInt(0, this.states.length);
let state: State = this.states[random];
this.playState(state.name, callback);
}
public stopState(): void {
CoroutineV2.StopCoroutinesBy(this);
this.nowPlayName = "";
}
/**
* 設定動畫速率(原有動畫的Speed在乘上倍率)
* @param speed 速率
*/
public SetSpeed(speed: number): void {
this._speed = speed;
}
public getAnimTime(name: string, isGetNext: boolean = false): number {
for (let s of this.states) {
if (s.name === name && s.clip != null) {
let time: number = s.clip.duration / this._speed;
if (isGetNext && s.transitionTo !== "") {
time += this.getAnimTime(s.transitionTo, true);
}
return time;
}
}
return null;
}
/**
* 暫停在某時間
* @param name Animator設定的動畫名稱
* @param time 要停的時間點
* @example
* this._anim.GotoTimeAndPause(name, 0);
*/
public GotoTimeAndPause(name: string, time: number = 0): void {
let clipName: string = null;
for (let s of this.states) {
if (s.name === name && s.clip != null) {
clipName = s.clip.name;
}
}
if (!clipName) {
cc.error(`GotoFrameAndPause get clip error: ${name}`);
return;
}
this.animation.play(clipName);
this.animation.stop(clipName);
this.animation.setCurrentTime(time);
this.animation.sample(clipName);
}
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "e0690d25-55e6-4fb2-9932-2231d0125e60",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,184 @@
import { CoroutineV2 } from "../../CatanEngine/CoroutineV2/CoroutineV2";
const { ccclass, property, requireComponent, menu, executeInEditMode } = cc._decorator;
// /** Clipname */
// export enum Clipname {
// None,
// }
@ccclass("SPState")
export class SPState {
@property()
public name: string = "";
public clip: cc.AnimationClip = null;
@property({ displayName: "Spine動畫名稱", tooltip: "Spine動畫名稱" })
public clipname: string = "";
// @property({ displayName: "clipname1", type: cc.Enum(Clipname) })
// public clipname1: Clipname = Clipname.None;
@property()
public isloop: boolean = false;
@property()
public transitionTo: string = "";
}
@ccclass
// @executeInEditMode
@menu("Plug-in/Animation/SPAnimator")
@requireComponent(sp.Skeleton)
export class SPAnimator extends cc.Component {
@property({ displayName: "Default State" })
public defaultState: string = "";
@property({ type: SPState })
public states: SPState[] = [];
public nowPlayName: string = "";
private _isInit: boolean = false;
_animation: sp.Skeleton = null;
/** 動畫速度 */
private _speed: number = 1;
get animation(): sp.Skeleton {
if (this._animation == null) {
this._animation = this.node.getComponent(sp.Skeleton);
}
return this._animation;
}
protected onLoad(): void {
if (this._isInit) {
return;
}
if (!this.node.activeInHierarchy) {
cc.error(`node: ${this.node.name}, activeInHierarchy: ${this.node.activeInHierarchy}, 動畫沒有打開無法初始化`);
return;
}
let animationClip: cc.AnimationClip[] = this.animation["skeletonData"]["_skeletonCache"].animations;
// if (CC_EDITOR) {
// for (let i: number = 0; i < animationClip.length; i++) {
// const clip: cc.AnimationClip = animationClip[i];
// Clipname[clip.name] = i;
// Clipname[i.toString()] = clip.name;
// cc.log(`[${i}] ${clip.name}`);
// }
// return;
// }
for (let s of this.states) {
let state: SPState = null;
for (let i: number = 0; i < animationClip.length; i++) {
const clip: cc.AnimationClip = animationClip[i];
if (s.clipname === clip.name && s.clipname != null) {
s.clip = clip;
state = s;
break;
}
}
if (CC_DEV) {
if (state === null) {
console.error(`node: ${this.node.name}, anim: ${s.clipname}, 動畫沒有掛在Animation上面`);
}
}
}
this._isInit = true;
}
protected onEnable(): void {
this.stopState();
if (this.defaultState !== "") {
this.playState(this.defaultState);
}
}
protected onDisable(): void {
this.stopState();
}
/**
* runStateAndWait(動作機只會接一次動畫)
* @param name 動畫State的名稱
* @param callback callback 沒有transitionTo才會觸發
*/
public *runStateAndWait(name: string, callback: Function = null): any {
if (!this._isInit) {
this.onLoad();
}
if (name === "") {
return;
}
this.animation.setToSetupPose();
let lastPlayName: string = "";
for (let s of this.states) {
if (s.name === this.nowPlayName && s.clipname != null) {
lastPlayName = s.clipname;
break;
}
}
this.nowPlayName = name;
let state: SPState = null;
for (let s of this.states) {
if (s.name === name && s.clipname != null) {
state = s;
break;
}
}
if (state == null) {
return;
}
// let animationState: cc.AnimationState = this.animation.play(state.clipname);
if (lastPlayName) {
this.animation.setMix(lastPlayName, state.clipname, 0.5);
}
this.animation.setAnimation(0, state.clipname, state.isloop);
// let animationState: sp.spine.TrackEntry = this.animation.setAnimation(0, state.clipname, state.isloop);
// animationState.speed = this.animation.currentClip.speed * this._speed;
// this.animation.sample(animationState.name);
if (state.clip.duration) {
yield CoroutineV2.WaitTime(state.clip.duration);
}
if (callback && !state.transitionTo) {
callback();
}
yield* this.runStateAndWait(state.transitionTo, callback);
}
/** playState(動作機只會接一次動畫) */
public playState(name: string, callback: Function = null): void {
if (!this.node.activeInHierarchy) {
cc.warn(`SPAnimator error name: ${this.node.name}, activeInHierarchy: ${this.node.activeInHierarchy}`);
}
CoroutineV2.Single(this.runStateAndWait(name, callback)).Start(this);
}
// /** playState(隨機) */
// public playRandomState(callback: Function = null): void {
// let random: number = RandomEx.GetInt(0, this.states.length);
// let state: SPState = this.states[random];
// this.playState(state.name, callback);
// }
public stopState(): void {
CoroutineV2.StopCoroutinesBy(this);
this.nowPlayName = "";
this.animation.clearTracks();
}
// /**
// * 設定動畫速率(原有動畫的Speed在乘上倍率)
// * @param speed 速率
// */
// public SetSpeed(speed: number): void {
// this._speed = speed;
// }
public getAnimTime(name: string, isGetNext: boolean = false): number {
for (let s of this.states) {
if (s.name === name && s.clipname != null) {
let time: number = s.clip.duration / this._speed;
if (isGetNext && s.transitionTo !== "") {
time += this.getAnimTime(s.transitionTo, true);
}
return time;
}
}
return null;
}
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "636825f6-4e9a-4b5b-991d-8bc1afd3a1ca",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,48 @@
cc.game.once(cc.game.EVENT_ENGINE_INITED, function () {
cc.js.mixin(sp.Skeleton.prototype, {
update(dt) {
// if (CC_EDITOR) return;
if (CC_EDITOR) {
cc.engine._animatingInEditMode = 1;
cc.engine.animatingInEditMode = 1;
}
if (this.paused) return;
dt *= this.timeScale * sp.timeScale;
if (this.isAnimationCached()) {
// Cache mode and has animation queue.
if (this._isAniComplete) {
if (this._animationQueue.length === 0 && !this._headAniInfo) {
let frameCache = this._frameCache;
if (frameCache && frameCache.isInvalid()) {
frameCache.updateToFrame();
let frames = frameCache.frames;
this._curFrame = frames[frames.length - 1];
}
return;
}
if (!this._headAniInfo) {
this._headAniInfo = this._animationQueue.shift();
}
this._accTime += dt;
if (this._accTime > this._headAniInfo.delay) {
let aniInfo = this._headAniInfo;
this._headAniInfo = null;
this.setAnimation(0, aniInfo.animationName, aniInfo.loop);
}
return;
}
this._updateCache(dt);
} else {
this._updateRealtime(dt);
}
}
});
});

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "9d832050-308c-4cd9-87c6-d8542ea9c3f3",
"importer": "javascript",
"isPlugin": true,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": true,
"subMetas": {}
}

View File

@@ -0,0 +1,13 @@
{
"ver": "1.1.3",
"uuid": "f5250e44-01c0-4660-8c8c-ca3e9d5c9def",
"importer": "folder",
"isBundle": false,
"bundleName": "",
"priority": 1,
"compressionType": {},
"optimizeHotUpdate": {},
"inlineSpriteFrames": {},
"isRemoteBundle": {},
"subMetas": {}
}

View File

@@ -0,0 +1,27 @@
const { ccclass, requireComponent, menu, property } = cc._decorator;
@ccclass
@menu("Plug-in/Button/BlockDoubleClickButton")
@requireComponent(cc.Button)
export default class BlockDoubleClickButton extends cc.Component {
//#region Lifecycle
protected onEnable(): void {
this.node.on("click", this.OnClickNode, this);
}
protected onDisable(): void {
this.node.off("click", this.OnClickNode, this);
}
//#endregion
//#region Event
public OnClickNode(event: cc.Button, customEventData: any): void {
this.getComponent(cc.Button).interactable = false;
}
//#endregion
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "b9536e4d-70cc-4d90-ac7d-4af5134f9cc7",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,81 @@
// import CSSettingsV3 from "../../../FormTable/CSSettingsV3";
const { ccclass, requireComponent, menu, property } = cc._decorator;
/** 有冷卻功能的按鈕 */
@ccclass
@menu("Plug-in/Button/ButtonClickCD")
@requireComponent(cc.Button)
export default class ButtonClickCD extends cc.Component {
//#region property
@property()
public CDTime: number = 3;
//#endregion
//#region public
public Msg: string;
//#endregion
//#region private
private _nowCDTime: number = 0;
//#endregion
//#region Lifecycle
protected onLoad(): void {
this.loadMsg();
}
private async loadMsg(): Promise<void> {
let CSSettingsV3: any = (await (import("../../../FormTable/CSSettingsV3"))).default;
this.Msg = CSSettingsV3.prototype.CommonString(1514);
}
protected update(dt: number): void {
if (this._nowCDTime > 0) {
this._nowCDTime -= dt;
if (this._nowCDTime <= 0) {
this._nowCDTime = 0;
this.getComponent(cc.Button).interactable = true;
}
}
}
protected onEnable(): void {
this.node.on("click", this._onClick, this);
this.node.on(cc.Node.EventType.TOUCH_START, this._onTouchStart, this);
}
protected onDisable(): void {
this.node.off("click", this._onClick, this);
this.node.off(cc.Node.EventType.TOUCH_START, this._onTouchStart, this);
}
//#endregion
//#region Custom
private _onClick(event: cc.Button, customEventData: any): void {
// if (this._nowCDTime > 0) {
// CSMessage.CreateYesMsg(String.Format(this.Msg, this._nowCDTime.toFixed(0)));
// return;
// }
this.getComponent(cc.Button).interactable = false;
this._nowCDTime = this.CDTime;
}
private async _onTouchStart(event: cc.Event.EventTouch): Promise<void> {
if (this._nowCDTime > 0) {
let CSMessage: any = (await (import("../../../Common/Message/CSMessage"))).default;
CSMessage.CreateYesMsg(String.Format(this.Msg, this._nowCDTime.toFixed(0)));
}
}
//#endregion
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "c9dc0a70-6d91-4d02-8ceb-8be96cc33225",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,143 @@
const { ccclass, requireComponent, menu, property } = cc._decorator;
@ccclass
@menu("Plug-in/Button/HoldButton")
@requireComponent(cc.Button)
export default class HoldButton extends cc.Component {
//#region public
@property()
public MaxTime: number = 2;
/** 是否HoldLine */
@property({ displayName: "是否有HoldLine", tooltip: "是否HoldLine" })
public IsHaveHoldLine: boolean = false;
@property({ type: cc.Node, visible(): boolean { return this.IsHaveHoldLine; } })
public HoldLine: cc.Node = null;
@property({ type: cc.Sprite, visible(): boolean { return this.IsHaveHoldLine; } })
public ProgressBG: cc.Sprite = null;
@property({ type: cc.Sprite, visible(): boolean { return this.IsHaveHoldLine; } })
public ProgressLine: cc.Sprite = null;
@property({ type: [cc.Component.EventHandler] })
public OnInvoke: cc.Component.EventHandler[] = [];
//#endregion
//#region private
private _isOnInvoke: boolean = false;
private _m_isMouseDown: boolean = false;
private _m_pressDeltaTime: number = 0;
//#endregion
//#region Lifecycle
protected start(): void {
if (this.HoldLine != null) {
this.HoldLine.active = false;
}
}
protected update(dt: number): void {
if (this._m_isMouseDown) {
this._checkHoldAutoStart(dt);
} else {
if (this.IsHaveHoldLine) {
this.HoldLine.active = false;
}
}
}
protected onEnable(): void {
this.node.on(cc.Node.EventType.TOUCH_START, this._onTouchStart, this);
this.node.on(cc.Node.EventType.TOUCH_END, this._onTouchEnd, this);
this.node.on(cc.Node.EventType.TOUCH_CANCEL, this._onTouchCancel, this);
}
protected onDisable(): void {
this.node.off(cc.Node.EventType.TOUCH_START, this._onTouchStart, this);
this.node.off(cc.Node.EventType.TOUCH_END, this._onTouchEnd, this);
this.node.off(cc.Node.EventType.TOUCH_CANCEL, this._onTouchCancel, this);
}
//#endregion
//#region Custom
private _checkHoldAutoStart(deltaTime: number): void {
this._m_pressDeltaTime += deltaTime;
if (this.IsHaveHoldLine) {
// 蓄能條顯示特效
this.ProgressLine.fillRange = this._m_pressDeltaTime;
}
if (this._m_pressDeltaTime > this.MaxTime) {
this.node.pauseSystemEvents(true);
this._isOnInvoke = true;
this._m_isMouseDown = false;
if (this.IsHaveHoldLine) {
this.HoldLine.active = false;
}
this._m_pressDeltaTime = 0;
if (this.OnInvoke != null) {
this.OnInvoke.forEach((eventHandler: cc.Component.EventHandler) => {
if (eventHandler) {
if (eventHandler.target === <any>"Callback" && eventHandler.component === "Callback" && eventHandler.handler) {
(<Function><unknown>eventHandler.handler)();
} else {
eventHandler.emit([this.node.getComponent(cc.Button)]);
}
}
});
}
}
}
//#endregion
//#region EventT
private _onTouchStart(event: cc.Event.EventTouch): void {
if (this._m_isMouseDown) {
return;
}
this._m_isMouseDown = true;
if (this.IsHaveHoldLine) {
this.HoldLine.active = true;
}
}
private _onTouchEnd(event: cc.Event.EventTouch): void {
this.node.resumeSystemEvents(true);
this._m_isMouseDown = false;
this._m_pressDeltaTime = 0;
if (this.IsHaveHoldLine) {
this.HoldLine.active = false;
}
this._isOnInvoke = false;
this._checkHoldAutoStart(0);
}
private _onTouchCancel(event: cc.Event.EventTouch): void {
this.node.resumeSystemEvents(true);
this._m_isMouseDown = false;
this._m_pressDeltaTime = 0;
if (this.IsHaveHoldLine) {
this.HoldLine.active = false;
}
this._isOnInvoke = false;
this._checkHoldAutoStart(0);
}
//#endregion
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "1472bab3-e5de-4d9a-a761-ccf2787ad36f",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,90 @@
const { ccclass, property } = cc._decorator;
@ccclass
export default class LongTouchComponent extends cc.Component {
@property({
tooltip: "触摸回调间隔。假如为0.1那么1秒内会回调10次 ${longTouchEvents} 事件数组"
})
touchInterval: number = 0.1;
@property({
type: [cc.Component.EventHandler],
tooltip: "回调事件数组,每间隔 ${toucheInterval}s 回调一次"
})
longTouchEvents: cc.Component.EventHandler[] = [];
/**
* 触摸计数器,用于统计本次长按的回调次数
*/
private _touchCounter: number = 0;
/**
* 标记当前是否在触摸这个节点
*/
private _isTouching: boolean = false;
onEnable() {
this.node.on(cc.Node.EventType.TOUCH_START, this._onTouchStart, this);
this.node.on(cc.Node.EventType.TOUCH_END, this._onTouchEnd, this);
this.node.on(cc.Node.EventType.TOUCH_CANCEL, this._onTouchCancel, this);
}
onDisable() {
this.node.off(cc.Node.EventType.TOUCH_START, this._onTouchStart, this);
this.node.off(cc.Node.EventType.TOUCH_END, this._onTouchEnd, this);
this.node.off(cc.Node.EventType.TOUCH_CANCEL, this._onTouchCancel, this);
}
private _onTouchStart(event: cc.Event.EventTouch) {
if (this._isTouching) {
return;
}
if (this.node.getBoundingBoxToWorld().contains(event.getLocation())) {
this._isTouching = true;
} else {
this._isTouching = false;
}
if (this._isTouching) {
// 第一次触摸立即回调一次
this.publishOneTouch();
// 然后开启计时器,计算后续的长按相当于触摸了多少次
this.schedule(this._touchCounterCallback, this.touchInterval);
}
}
private _onTouchEnd(event: cc.Event.EventTouch) {
this._isTouching = false;
this._touchCounter = 0;
this.unschedule(this._touchCounterCallback);
}
private _onTouchCancel(event: cc.Event.EventTouch) {
this._isTouching = false;
this._touchCounter = 0;
this.unschedule(this._touchCounterCallback);
}
private _touchCounterCallback() {
if (this._isTouching) {
this.publishOneTouch();
} else {
this.unschedule(this._touchCounterCallback);
}
}
/**
* 通知出去:被点击/触摸了一次,长按时,会连续多次回调这个方法
*/
private publishOneTouch() {
if (!this._isTouching) {
return;
}
this._touchCounter++;
this.longTouchEvents.forEach((eventHandler: cc.Component.EventHandler) => {
eventHandler.emit([this._touchCounter]);
});
}
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "29b183d5-ec75-4a1b-b99e-88b2c99f796f",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,13 @@
{
"ver": "1.1.3",
"uuid": "53ba29d0-c2b9-43bc-9098-4c49e095da34",
"importer": "folder",
"isBundle": false,
"bundleName": "",
"priority": 1,
"compressionType": {},
"optimizeHotUpdate": {},
"inlineSpriteFrames": {},
"isRemoteBundle": {},
"subMetas": {}
}

View File

@@ -0,0 +1,44 @@
const { ccclass, menu, requireComponent } = cc._decorator;
@ccclass
// @menu("Plug-in/EditBox/EditboxEx")
@requireComponent(cc.EditBox)
export default class EditboxEx extends cc.Component {
//#region private
private _worldPos: cc.Vec2 = null;
//#endregion
//#region Lifecycle
protected onLoad(): void {
if (CC_DEV || cc.sys.isNative) {
let editbox: cc.EditBox = this.node.getComponent(cc.EditBox);
this._worldPos = this.node.GetWorldPosition();
editbox.node.on("editing-did-began", this._onEditDidBegan, this);
editbox.node.on("editing-did-ended", this._onEditDidEnded, this);
}
}
//#endregion
//#region EventListener
private _onEditDidBegan(editbox: cc.EditBox, customEventData: string): void {
let winSizeHeight: number = cc.winSize.height;
let nodeSizeHeight: number = this.node.height / 2;
let targetHeight: number = winSizeHeight - nodeSizeHeight;
let worldPos: cc.Vec2 = cc.v2(this.node.GetWorldPosition().x, targetHeight);
this.node.SetWorldPosition(worldPos);
}
// 假设这个回调是给 editingDidEnded 事件的
private _onEditDidEnded(editbox: cc.EditBox, customEventData: string): void {
this.node.SetWorldPosition(this._worldPos);
}
//#endregion
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "1e6b0467-4516-4f10-a876-473c8894ff17",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,13 @@
{
"ver": "1.1.3",
"uuid": "dff82bd3-7f62-4573-9fe7-02f301602ae9",
"importer": "folder",
"isBundle": false,
"bundleName": "",
"priority": 1,
"compressionType": {},
"optimizeHotUpdate": {},
"inlineSpriteFrames": {},
"isRemoteBundle": {},
"subMetas": {}
}

View File

@@ -0,0 +1,14 @@
const {ccclass, property} = cc._decorator;
@ccclass
export class LabelOtherSetting extends cc.Component {
@property
public bold:boolean = false;
@property
public underline:boolean = false;
onEnable(){
(<any>this.getComponent(cc.Label))._enableBold(this.bold);
(<any>this.getComponent(cc.Label))._enableUnderline(this.underline);
}
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "8444b16e-19e2-45f3-b155-0bbde521118f",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,13 @@
{
"ver": "1.1.3",
"uuid": "8ddc4917-8b1c-4b4e-abfe-9a7b37d363dc",
"importer": "folder",
"isBundle": false,
"bundleName": "",
"priority": 1,
"compressionType": {},
"optimizeHotUpdate": {},
"inlineSpriteFrames": {},
"isRemoteBundle": {},
"subMetas": {}
}

View File

@@ -0,0 +1,58 @@
const { ccclass, property } = cc._decorator;
/** 物品拖動 */
@ccclass
export default class DragItem extends cc.Component {
//#region Lifecycle
protected onLoad(): void {
// 獲取小節點
let carNode: cc.Node = this.node;
// 新增變數判斷使用者當前滑鼠是不是處於按下狀態
let mouseDown: boolean = false;
// 當使用者點選的時候記錄滑鼠點選狀態
carNode.on(cc.Node.EventType.MOUSE_DOWN, (event) => {
mouseDown = true;
});
// 只有當使用者滑鼠按下才能拖拽
carNode.on(cc.Node.EventType.MOUSE_MOVE, (event) => {
if (!mouseDown) { return; }
// 獲取滑鼠距離上一次點的資訊
let delta: any = event.getDelta();
let canvasNode: cc.Node = cc.Canvas.instance.node;
// 增加限定條件
let minX: number = -canvasNode.width / 2 + carNode.width / 2;
let maxX: number = canvasNode.width / 2 - carNode.width / 2;
let minY: number = -canvasNode.height / 2 + carNode.height / 2;
let maxY: number = canvasNode.height / 2 - carNode.height / 2;
let moveX: number = carNode.x + delta.x;
let moveY: number = carNode.y + delta.y;
// 控制移動範圍
if (moveX < minX) {
moveX = minX;
} else if (moveX > maxX) {
moveX = maxX;
}
if (moveY < minY) {
moveY = minY;
} else if (moveY > maxY) {
moveY = maxY;
}
// 移動小車節點
carNode.x = moveX;
carNode.y = moveY;
});
// 當滑鼠抬起的時候恢復狀態
carNode.on(cc.Node.EventType.MOUSE_UP, (event) => {
mouseDown = false;
});
carNode.on(cc.Node.EventType.TOUCH_END, (event) => {
mouseDown = false;
});
carNode.on(cc.Node.EventType.TOUCH_CANCEL, (event) => {
mouseDown = false;
});
}
//#endregion
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "af74a109-396e-4192-bcac-70e8b050f9e6",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,13 @@
{
"ver": "1.1.3",
"uuid": "5e5b6a48-a903-46ac-8feb-4f515f6171fa",
"importer": "folder",
"isBundle": false,
"bundleName": "",
"priority": 1,
"compressionType": {},
"optimizeHotUpdate": {},
"inlineSpriteFrames": {},
"isRemoteBundle": {},
"subMetas": {}
}

View File

@@ -0,0 +1,14 @@
const { ccclass } = cc._decorator;
@ccclass
export default class ParticleSystemAutoPlay extends cc.Component {
onEnable() {
let sys = this.getComponent(cc.ParticleSystem);
if (sys != null) {
sys.stopSystem();
sys.resetSystem();
}
}
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "69f69903-43ad-484d-b1ae-1055b246ad61",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,13 @@
{
"ver": "1.1.3",
"uuid": "37e07a73-638f-4f2f-918a-b70472d54085",
"importer": "folder",
"isBundle": false,
"bundleName": "",
"priority": 1,
"compressionType": {},
"optimizeHotUpdate": {},
"inlineSpriteFrames": {},
"isRemoteBundle": {},
"subMetas": {}
}

View File

@@ -0,0 +1,9 @@
const { ccclass, requireComponent } = cc._decorator;
@ccclass
@requireComponent(cc.Sprite)
export default class ShaderGray extends cc.Component {
onLoad() {
this.getComponent(cc.Sprite).setMaterial(0, cc.Material.getBuiltinMaterial('2d-gray-sprite'));
}
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "3167aa46-5e25-4c15-ae71-d566568d72ad",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,13 @@
{
"ver": "1.1.3",
"uuid": "36c89e1d-52ff-4f8c-9063-40f3c5500591",
"importer": "folder",
"isBundle": false,
"bundleName": "",
"priority": 1,
"compressionType": {},
"optimizeHotUpdate": {},
"inlineSpriteFrames": {},
"isRemoteBundle": {},
"subMetas": {}
}

View File

@@ -0,0 +1,188 @@
import { CoroutineV2 } from "../../CatanEngine/CoroutineV2/CoroutineV2";
import { UIManager } from "./UIManager";
/**畫面自適應(換場景手動呼叫) */
export default class ScreenResize {
private static _instance: ScreenResize = null;
public static get Instance(): ScreenResize { return this._instance; }
/**直橫式的製作尺寸 */
public static readonly CanvasSize: cc.Vec2[] = [cc.v2(1422, 800), cc.v2(800, 1422)];
/**是否直式機台 */
public static IsPortrait: number = 0;
/**固定橫直判斷(null=通用.0=固定橫.1=固定直) */
public static PL: number = null;
constructor() {
cc.log("creat ScreenResize");
ScreenResize._instance = this;
ScreenResize._instance.CallManual();
}
public AddEven(): void {
ScreenResize._instance.AddResizeEvent();
}
/**手動呼叫 */
public CallManual(): void {
ScreenResize.Instance.GameResize("inGameResize");
}
public AddResizeEvent() {
this.GameResize("inGameResize");
window.onresize = () => {
this.GameResize("window.onresize");
};
cc.view.setResizeCallback(() => {
this.GameResize("cc.view.setResizeCallback");
});
}
public GameResize(resizeType: string) {
if (ScreenResize.PL == null) {
//自適應
ScreenResize.IsPortrait = this._isPortraitMode();
} else {
//固定直橫
ScreenResize.IsPortrait = ScreenResize.PL;
}
cc.log("resizeType:" + resizeType);
cc.log("ScreenResize.IsPortrait:" + ScreenResize.IsPortrait);
if (cc.sys.isBrowser) {
//網頁版的修正顯示範圍判斷
this._browserAutoScreenSetting(resizeType);
} else {
this._appAutoScreenSetting();
}
this._alignWithScreen();
CoroutineV2.Single(this._delayChangeDir()).Start();
this._alignWithGameUI();
}
private _browserAutoScreenSetting(resizeType: string) {
let frameSize = cc.view.getFrameSize();
if (ScreenResize.IsPortrait) {
cc.view.setOrientation(cc.macro.ORIENTATION_PORTRAIT);
if (resizeType === "inGameResize") {
//只需要進遊戲設定一次,避免第一次進入場景時萬一跟設計分辨率不同會導致世界座標跑掉(cocos engine底層沒處理好)
if (frameSize.width > frameSize.height) {
cc.view.setFrameSize(frameSize.height, frameSize.width)
} else {
cc.view.setFrameSize(frameSize.width, frameSize.height)
}
}
} else {
cc.view.setOrientation(cc.macro.ORIENTATION_LANDSCAPE);
if (resizeType === "inGameResize") {
//只需要進遊戲設定一次,避免第一次進入場景時萬一跟設計分辨率不同會導致世界座標跑掉(cocos engine底層沒處理好)
if (frameSize.height > frameSize.width) {
cc.view.setFrameSize(frameSize.height, frameSize.width)
} else {
cc.view.setFrameSize(frameSize.width, frameSize.height)
}
}
}
cc.view.setDesignResolutionSize(ScreenResize.CanvasSize[ScreenResize.IsPortrait].x, ScreenResize.CanvasSize[ScreenResize.IsPortrait].y, new cc.ResolutionPolicy(cc.ContainerStrategy["PROPORTION_TO_FRAME"], cc.ContentStrategy["NO_BORDER"]));
if (document.getElementById("GameCanvas")["width"] % 2 != 0) {
document.getElementById("GameCanvas")["width"] -= 1;
}
if (document.getElementById("GameCanvas")["height"] % 2 != 0) {
document.getElementById("GameCanvas")["height"] -= 1;
}
document.body.style.width = "100%";
document.body.style.height = "100%";
}
private _appAutoScreenSetting() {
cc.view.setDesignResolutionSize(ScreenResize.CanvasSize[ScreenResize.IsPortrait].x, ScreenResize.CanvasSize[ScreenResize.IsPortrait].y, cc.ResolutionPolicy.SHOW_ALL);
}
/**舊版COCOS引擎內的座標對齊 */
private _alignWithScreen(): void {
var designSize, nodeSize;
if (CC_EDITOR) {
nodeSize = designSize = cc["engine"]["getDesignResolutionSize"]();
cc.Canvas.instance.node.setPosition(designSize.width * 0.5, designSize.height * 0.5);
}
else {
var canvasSize = nodeSize = cc.visibleRect;
designSize = cc.view.getDesignResolutionSize();
var clipTopRight = !cc.Canvas.instance.fitHeight && !cc.Canvas.instance.fitWidth;
var offsetX = 0;
var offsetY = 0;
if (clipTopRight) {
// offset the canvas to make it in the center of screen
offsetX = (designSize.width - canvasSize.width) * 0.5;
offsetY = (designSize.height - canvasSize.height) * 0.5;
}
cc.Canvas.instance.node.setPosition(canvasSize.width * 0.5 + offsetX, canvasSize.height * 0.5 + offsetY);
}
cc.Canvas.instance.node.width = nodeSize.width;
cc.Canvas.instance.node.height = nodeSize.height;
}
private *_delayChangeDir() {
yield CoroutineV2.WaitTime(0.2);
this._alignWithScreen();
this._alignWithGameUI();
}
private _alignWithGameUI() {
UIManager.DireEvent.DispatchCallback([]);
}
private _isPortraitMode(): number {
let sw = window.screen.width;
let sh = window.screen.height;
let _Width = sw < sh ? sw : sh;
let _Height = sw >= sh ? sw : sh;
if (cc.sys.isBrowser) {
//網頁版的顯示範圍判斷
let w = document.documentElement.clientWidth;
let h = document.documentElement.clientHeight;
let w2 = window.innerWidth;
let h2 = window.innerHeight;
let containerW = Number.parseInt(document.getElementById("Cocos2dGameContainer").style.width) + Number.parseInt(document.getElementById("Cocos2dGameContainer").style.paddingRight) + Number.parseInt(document.getElementById("Cocos2dGameContainer").style.paddingLeft);
let containerH = Number.parseInt(document.getElementById("Cocos2dGameContainer").style.height) + Number.parseInt(document.getElementById("Cocos2dGameContainer").style.paddingTop) + Number.parseInt(document.getElementById("Cocos2dGameContainer").style.paddingBottom);
let rotate = Number.parseInt(document.getElementById("Cocos2dGameContainer").style.transform.replace("rotate(", "").replace("deg)", ""));
/*cc.log(
"w:" + w + ",h:" + h +
"\n,w2:" + w2 + ",h2:" + h2 +
"\n,sw:" + sw + ",sh:" + sh +
"\n,_Width:" + _Width + ",_Height:" + _Height +
"\n,frameW:" + cc.view.getFrameSize().width + ",frameH:" + cc.view.getFrameSize().height +
"\n,containerW:" + containerW + ",containerH:" + containerH + ",rotate:" + rotate +
"\n,canvasW:" + cc.game.canvas.width + ",canvasrH:" + cc.game.canvas.height
);*/
if (w == _Width) {
return 1;
} else if (w == _Height) {
if (!CC_DEV) {
return 0;
} else {
if (containerW >= containerH) {
return rotate == 0 ? 0 : 1;
} else {
return rotate == 0 ? 1 : 0;
}
}
} else if (w == w2) {
if (containerW >= containerH) {
return rotate == 0 ? 0 : 1;
} else {
return rotate == 0 ? 1 : 0;
}
} else {
if (containerW >= containerH) {
return rotate == 0 ? 0 : 1;
} else {
return rotate == 0 ? 1 : 0;
}
}
} else {
if (sw == _Width) {
return 1;
} else if (sw == _Height) {
return 0;
} else {
cc.log("XXXXXXXXXXXXXXXXXX");
return 1;
}
}
}
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "187716a0-d35c-4b06-80fb-48b799e7fe9e",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,13 @@
{
"ver": "1.1.3",
"uuid": "f63b1b10-07ba-49bc-aa9f-a0ea4c652076",
"importer": "folder",
"isBundle": false,
"bundleName": "",
"priority": 1,
"compressionType": {},
"optimizeHotUpdate": {},
"inlineSpriteFrames": {},
"isRemoteBundle": {},
"subMetas": {}
}

View File

@@ -0,0 +1,27 @@
import ScreenResize from "../ScreenResize";
const { ccclass, property } = cc._decorator;
@ccclass("SwitchActive")
export class SwitchActive {
@property({ type: cc.Node })
public UI: cc.Node = null;
@property({ type: cc.Boolean/*, visible: function (this: ImageGroup) { return this.Reset; } */ })
public show: boolean[] = [];
public SetObjActive(obj: cc.Node, show: boolean): void {
obj.active = show;
}
}
@ccclass
export default class SwitchActiveGroup extends cc.Component {
@property({ displayName: "縮放scale群組", type: SwitchActive })
public ScaleGroups: SwitchActive[] = [];
public Run(): void {
if (this.ScaleGroups != null && this.ScaleGroups.length) {
for (let group of this.ScaleGroups) {
group.SetObjActive(group.UI, group.show[ScreenResize.IsPortrait]);
}
}
}
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "a96cf057-9e35-4146-89df-5f0f4819fb6c",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,32 @@
import ScreenResize from "../ScreenResize";
import { UIManager } from "../UIManager";
const { ccclass, property } = cc._decorator;
@ccclass("SwitchActiveObj")
export class SwitchActiveObj {
@property({ type: cc.Node })
public UI: cc.Node = null;
@property({ type: cc.Boolean/*, visible: function (this: ImageGroup) { return this.Reset; } */ })
public show: boolean[] = [];
public SetObjActive(obj: cc.Node, show: boolean): void {
obj.active = show;
}
}
@ccclass
export default class SwitchActiveGroupExtra extends cc.Component {
@property({ displayName: "縮放scale群組", type: SwitchActiveObj })
public ScaleGroups: SwitchActiveObj[] = [];
public Run(): void {
if (this.ScaleGroups != null && this.ScaleGroups.length) {
for (let group of this.ScaleGroups) {
group.SetObjActive(group.UI, group.show[ScreenResize.IsPortrait]);
}
}
}
onLoad() {
UIManager.DireEvent.AddCallback(this.Run, this);
this.Run();
}
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "9d9e9007-973c-4926-b5cf-aacceae74665",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,30 @@
import ScreenResize from "../ScreenResize";
const { ccclass, property } = cc._decorator;
@ccclass("SwitchImgSourceGroup")
export class SwitchImgSourceGroup {
@property({ type: cc.Node })
public Sprite: cc.Sprite = null;
@property({ type: cc.SpriteFrame/*, visible: function (this: ImageGroup) { return this.Reset; } */ })
public SourceImg: cc.SpriteFrame[] = [];
public SetImg(obj: cc.Sprite, switchObj: cc.SpriteFrame): void {
if (obj == null || switchObj == null) {
return;
}
obj.getComponent(cc.Sprite).spriteFrame = switchObj;
}
}
@ccclass
export default class SwitchImgGroup extends cc.Component {
@property({ displayName: "換UI群組", type: SwitchImgSourceGroup })
public ImgGroups: SwitchImgSourceGroup[] = [];
public Run(): void {
if (this.ImgGroups != null && this.ImgGroups.length) {
for (let group of this.ImgGroups) {
group.SetImg(group.Sprite, group.SourceImg[ScreenResize.IsPortrait]);
}
}
}
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "56151188-edd5-4384-8a84-50a84456a6c3",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,35 @@
import ScreenResize from "../ScreenResize";
import { UIManager } from "../UIManager";
const { ccclass, property } = cc._decorator;
@ccclass("SwitchImgSource")
export class SwitchImgSource {
@property({ type: cc.Node })
public Sprite: cc.Sprite = null;
@property({ type: cc.SpriteFrame/*, visible: function (this: ImageGroup) { return this.Reset; } */ })
public SourceImg: cc.SpriteFrame[] = [];
public SetImg(obj: cc.Sprite, switchObj: cc.SpriteFrame): void {
if (obj == null || switchObj == null) {
return;
}
obj.getComponent(cc.Sprite).spriteFrame = switchObj;
}
}
@ccclass
export default class SwitchImgGroupExtra extends cc.Component {
@property({ displayName: "換UI群組", type: SwitchImgSource })
public ImgGroups: SwitchImgSource[] = [];
public Run(): void {
if (this.ImgGroups != null && this.ImgGroups.length) {
for (let group of this.ImgGroups) {
group.SetImg(group.Sprite, group.SourceImg[ScreenResize.IsPortrait]);
}
}
}
onLoad() {
UIManager.DireEvent.AddCallback(this.Run, this);
this.Run();
}
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "208b15b7-a199-4b86-a538-3d1d18695552",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,31 @@
import ScreenResize from "../ScreenResize";
const { ccclass, property } = cc._decorator;
@ccclass("SwitchPosition")
export class SwitchPosition {
@property({ type: cc.Node })
public UI: cc.Node = null;
@property({ type: cc.Vec2/*, visible: function (this: ImageGroup) { return this.Reset; } */ })
public Pos: cc.Vec2[] = [];
public SetPos(obj: cc.Node, posNum: cc.Vec2): void {
obj.setPosition(posNum);
}
}
@ccclass
export default class SwitchPositionGroup extends cc.Component {
@property({ displayName: "改變座標群組", type: SwitchPosition })
public PosGroups: SwitchPosition[] = [];
public Run(): void {
if (this.PosGroups != null && this.PosGroups.length) {
for (let group of this.PosGroups) {
if (!group.UI || !group.Pos[ScreenResize.IsPortrait]) {
cc.error("沒有設定節點或座標.name=" + this.node.name);
continue;
}
group.SetPos(group.UI, group.Pos[ScreenResize.IsPortrait]);
}
}
}
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "2083e1d2-be99-4173-b425-cdc9da21cbb3",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,33 @@
import ScreenResize from "../ScreenResize";
import { UIManager } from "../UIManager";
const { ccclass, property } = cc._decorator;
@ccclass("SwitchPositionObj")
export class SwitchPositionObj {
@property({ type: cc.Node })
public UI: cc.Node = null;
@property({ type: cc.Vec2/*, visible: function (this: ImageGroup) { return this.Reset; } */ })
public Pos: cc.Vec2[] = [];
public SetPos(obj: cc.Node, posNum: cc.Vec2): void {
obj.setPosition(posNum);
}
}
@ccclass
export default class SwitchPositionGroupExtra extends cc.Component {
@property({ displayName: "改變座標群組", type: SwitchPositionObj })
public PosGroups: SwitchPositionObj[] = [];
public Run(param: any[] = null): void {
if (this.PosGroups != null && this.PosGroups.length) {
for (let group of this.PosGroups) {
cc.log("橫直轉換:" + group.UI.name + ":" + group.Pos[ScreenResize.IsPortrait]);
group.SetPos(group.UI, group.Pos[ScreenResize.IsPortrait]);
}
}
}
onLoad() {
UIManager.DireEvent.AddCallback(this.Run, this);
this.Run();
}
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "512c7a23-3a86-4d84-abc6-9553be08da10",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,27 @@
import ScreenResize from "../ScreenResize";
const { ccclass, property } = cc._decorator;
@ccclass("SwitchRotation")
export class SwitchRotation {
@property({ type: cc.Node })
public UI: cc.Node = null;
@property({ type: cc.Float/*, visible: function (this: ImageGroup) { return this.Reset; } */ })
public rotaitonNum: number[] = [];
public SetObjRotation(obj: cc.Node, r: number): void {
obj.angle = -r;
}
}
@ccclass
export default class SwitchRotationGroup extends cc.Component {
@property({ displayName: "設定rotation群組", type: SwitchRotation })
public ScaleGroups: SwitchRotation[] = [];
public Run(): void {
if (this.ScaleGroups != null && this.ScaleGroups.length) {
for (let group of this.ScaleGroups) {
group.SetObjRotation(group.UI, group.rotaitonNum[ScreenResize.IsPortrait]);
}
}
}
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "e53fa0f6-ddad-41e1-b0d2-df151a2f3ff0",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,27 @@
import ScreenResize from "../ScreenResize";
const { ccclass, property } = cc._decorator;
@ccclass("SwitchSize")
export class SwitchScale {
@property({ type: cc.Node })
public UI: cc.Node = null;
@property({ type: cc.Float/*, visible: function (this: ImageGroup) { return this.Reset; } */ })
public ScaleNum: number[] = [];
public SetObjScale(obj: cc.Node, scaleNum: number): void {
obj.setScale(scaleNum);
}
}
@ccclass
export default class SwitchScaleGroup extends cc.Component {
@property({ displayName: "縮放scale群組", type: SwitchScale })
public ScaleGroups: SwitchScale[] = [];
public Run(): void {
if (this.ScaleGroups != null && this.ScaleGroups.length) {
for (let group of this.ScaleGroups) {
group.SetObjScale(group.UI, group.ScaleNum[ScreenResize.IsPortrait]);
}
}
}
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "4e2f6235-b5a6-4c44-9ea5-4779b97f1630",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,32 @@
import ScreenResize from "../ScreenResize";
import { UIManager } from "../UIManager";
const { ccclass, property } = cc._decorator;
@ccclass("SwitchSizeObj")
export class SwitchScaleObj {
@property({ type: cc.Node })
public UI: cc.Node = null;
@property({ type: cc.Float/*, visible: function (this: ImageGroup) { return this.Reset; } */ })
public ScaleNum: number[] = [];
public SetObjScale(obj: cc.Node, scaleNum: number): void {
obj.setScale(scaleNum);
}
}
@ccclass
export default class SwitchScaleGroupExtra extends cc.Component {
@property({ displayName: "縮放scale群組", type: SwitchScaleObj })
public ScaleGroups: SwitchScaleObj[] = [];
public Run(): void {
if (this.ScaleGroups != null && this.ScaleGroups.length) {
for (let group of this.ScaleGroups) {
group.SetObjScale(group.UI, group.ScaleNum[ScreenResize.IsPortrait]);
}
}
}
onLoad() {
UIManager.DireEvent.AddCallback(this.Run, this);
this.Run();
}
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "065d43a0-b2c1-4a41-8e84-8a0f3d3817f2",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,34 @@
import ScreenResize from "../ScreenResize";
const { ccclass, property } = cc._decorator;
@ccclass("SwitchUIGroup")
export class SwitchUIGroup {
@property({ type: cc.Node })
public UI: cc.Node = null;
@property({ type: cc.Integer/*, visible: function (this: ImageGroup) { return this.Reset; } */ })
public SourceID: number[] = [];
public Set(obj: cc.Node, switchObj: cc.Node): void {
if (obj == null || switchObj == null) {
return;
}
obj.removeAllChildren();
obj.ExAddChild(switchObj);
}
}
@ccclass
export default class SwitchSoueceGroup extends cc.Component {
@property({ displayName: "換UI群組", type: SwitchUIGroup })
public UIGroups: SwitchUIGroup[] = [];
public Run(switchObg: cc.Node): void {
if (this.UIGroups != null && this.UIGroups.length) {
for (let group of this.UIGroups) {
let child: cc.Node[] = switchObg.getChildByName(group.SourceID[ScreenResize.IsPortrait].toString()).children;
for (let i: number = 0; i < child.length; i++) {
group.Set(group.UI, child[i]);
}
}
}
}
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "45ea513f-8665-4d40-8b51-3a67ab35f327",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,26 @@
import ScreenResize from "../ScreenResize";
const { ccclass, property } = cc._decorator;
@ccclass("SwitchWH")
export class SwitchWH {
@property({ type: cc.Node })
public UI: cc.Node = null;
@property({ type: cc.Vec2/*, visible: function (this: ImageGroup) { return this.Reset; } */ })
public WH: cc.Vec2[] = [];
public SetWH(obj: cc.Node, WHNum: cc.Vec2): void {
obj.SetSizeDelta(WHNum);
}
}
@ccclass
export default class SwitchWHGroup extends cc.Component {
@property({ displayName: "改變寬高群組", type: SwitchWH })
public WHGroups: SwitchWH[] = [];
public Run(): void {
if (this.WHGroups != null && this.WHGroups.length) {
for (let group of this.WHGroups) {
group.SetWH(group.UI, group.WH[ScreenResize.IsPortrait]);
}
}
}
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "5cfb2592-7ada-4b09-81dc-0dc14dc94aa5",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,31 @@
import ScreenResize from "../ScreenResize";
import { UIManager } from "../UIManager";
const { ccclass, property } = cc._decorator;
@ccclass("SwitchWHObj")
export class SwitchWHObj {
@property({ type: cc.Node })
public UI: cc.Node = null;
@property({ type: cc.Vec2/*, visible: function (this: ImageGroup) { return this.Reset; } */ })
public WH: cc.Vec2[] = [];
public SetWH(obj: cc.Node, WHNum: cc.Vec2): void {
obj.SetSizeDelta(WHNum);
}
}
@ccclass
export default class SwitchWHGroupExtra extends cc.Component {
@property({ displayName: "改變寬高群組", type: SwitchWHObj })
public WHGroups: SwitchWHObj[] = [];
public Run(): void {
if (this.WHGroups != null && this.WHGroups.length) {
for (let group of this.WHGroups) {
group.SetWH(group.UI, group.WH[ScreenResize.IsPortrait]);
}
}
}
onLoad() {
UIManager.DireEvent.AddCallback(this.Run, this);
this.Run();
}
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "b9806317-d4bd-4aac-be3e-a16b0a3159f9",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,8 @@
import { Action } from "../../CatanEngine/CSharp/System/Action";
export class UIManager {
public static readonly ScreenScale = 0.58;
/**橫直切換監聽 */
public static readonly DireEvent: Action<any[]> = new Action<any[]>();
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "277e84bb-8d5d-4e7c-8dd1-06d752d7bba1",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}

View File

@@ -0,0 +1,182 @@
import { CoroutineV2 } from "../../CatanEngine/CoroutineV2/CoroutineV2";
import ScreenResize from "./ScreenResize";
import SwitchActiveGroup from "./SwitchShowUI/SwitchActiveGroup";
import SwitchImgGroup from "./SwitchShowUI/SwitchImgGroup";
import SwitchPositionGroup from "./SwitchShowUI/SwitchPositionGroup";
import SwitchRotationGroup from "./SwitchShowUI/SwitchRotationGroup";
import SwitchScaleGroup from "./SwitchShowUI/SwitchScaleGroup";
import SwitchWHGroup from "./SwitchShowUI/SwitchWHGroup";
import { UIManager } from "./UIManager";
const { ccclass } = cc._decorator;
@ccclass
export default class UIPanel extends cc.Component {
/**[基底UIPanel]等待跳出旗標*/
private _isWaiting: boolean = false;
/**
* [基底UIPanel]初始化實做(UI每次創建時呼叫, 只會呼叫一次)
* @param initData
*/
protected ImplementInitial(...initData: any[]): void {
}
/**
* [基底UIPanel]顯示準備實做(UI顯示前呼叫)
* @param param
*/
protected *ImplementReadyShow(...param: any[]): IterableIterator<any> {
}
/**
* [基底UIPanel]顯示實做(UI顯示呼叫)
* @param param
*/
protected *ImplementShow(): IterableIterator<any> {
}
/**
* [基底UIPanel]隱藏(實做)
* @param param
*/
protected *ImplementHide(...param: any[]): IterableIterator<any> {
}
/**
* [基底UIPanel]移除實做
*/
protected ImplementDestroy() {
}
/**
* [基底UIPanel]直橫版切換
* @param param
*/
public ChangeDire(param: any[] = null): void {
if (!cc.isValid(this)) {
return;
}
cc.log("ChangeDire:" + this.name);
if (this.getComponent(SwitchScaleGroup)) {
this.getComponent(SwitchScaleGroup).Run();
}
if (this.getComponent(SwitchPositionGroup)) {
this.getComponent(SwitchPositionGroup).Run();
}
if (this.getComponent(SwitchWHGroup)) {
this.getComponent(SwitchWHGroup).Run();
}
if (this.getComponent(SwitchImgGroup)) {
this.getComponent(SwitchImgGroup).Run();
}
if (this.getComponent(SwitchActiveGroup)) {
this.getComponent(SwitchActiveGroup).Run();
}
if (this.getComponent(SwitchRotationGroup)) {
this.getComponent(SwitchRotationGroup).Run();
}
this._uiMaskHandler();
}
private _uiMaskHandler(): void {
let mask: cc.Node = this.node.getChildByName("Mask");
if (mask && this.node.parent.name == "ElementContent") {
let size: cc.Vec2 = ScreenResize.CanvasSize[ScreenResize.IsPortrait];
mask.SetSizeDelta(cc.v2(size.x / UIManager.ScreenScale, size.y / UIManager.ScreenScale));
}
}
//=======================================================================================
/**
* [禁止複寫]創UI
* @param source
* @param parent
* @param data
*/
public static CreateUI(source: cc.Prefab, parent: cc.Node, ...data: any[]): UIPanel {
let node = parent.ExAddChild(source);
let script = node.getComponent(UIPanel);
script.Initial(...data);
return script;
}
/**
* [禁止複寫]初始化
* @param initData
*/
public Initial(...initData: any[]): void {
UIManager.DireEvent.RemoveByBindTarget(this);
UIManager.DireEvent.AddCallback(this.ChangeDire, this);
this.node.active = false;
this._uiMaskHandler();
this.ImplementInitial(...initData);
}
/**
* [禁止複寫]顯示UI
* @param param
*/
public *Show(...param: any[]): IterableIterator<any> {
yield* this.ImplementReadyShow(...param);
this.node.active = true;
yield* this.ImplementShow();
}
/**
* [禁止複寫]隱藏UI
* @param param
*/
public *Hide(...param: any[]): IterableIterator<any> {
if (this._isWaiting) {
cc.warn(this.node.name, "_isWaiting = true無法關閉");
}
else {
yield* this.ImplementHide(...param);
if (this && this.node) {
this.node.active = false;
}
}
}
/**
* [禁止複寫]等待UI
* @param showData
* @param hideData
*/
public *Wait(showData: any[] = [], hideData: any[] = []): IterableIterator<any> {
yield* this.Show(...showData);
this._isWaiting = true;
while (this._isWaiting) {
yield null;
}
yield* this.Hide(...hideData);
}
/**
* [禁止複寫]關閉UI
* @param param
*/
public Close(...param: any[]): void {
if (this._isWaiting) {
this._isWaiting = false;
}
else {
CoroutineV2.Single(this.Hide(...param)).Start();
}
}
//=======================================================================================
onLoad() {
UIManager.DireEvent.RemoveByBindTarget(this);
UIManager.DireEvent.AddCallback(this.ChangeDire, this);
}
//COCOS引擎內建生命週期
//onLoad->start->update->lateUpdate->onDestroy->onEnable->onDisable
onDestroy() {
UIManager.DireEvent.RemoveByBindTarget(this);
this.ImplementDestroy();
}
//=======================================================================================
}

View File

@@ -0,0 +1,10 @@
{
"ver": "1.1.0",
"uuid": "066bf037-e621-482f-a93f-fc1e59e90cfb",
"importer": "typescript",
"isPlugin": false,
"loadPluginInWeb": true,
"loadPluginInNative": true,
"loadPluginInEditor": false,
"subMetas": {}
}