309 lines
10 KiB
JavaScript
309 lines
10 KiB
JavaScript
/*---------------------------------------------------------------------------*
|
||
* TorigoyaMZ_FrameTween.js v.2.2.1
|
||
*---------------------------------------------------------------------------*
|
||
* 2023/09/23 02:17 (JST)
|
||
*---------------------------------------------------------------------------*
|
||
* Ruたん ( @ru_shalm )
|
||
* https://torigoya-plugin.rutan.dev
|
||
*---------------------------------------------------------------------------*/
|
||
|
||
/*:
|
||
* @target MZ
|
||
* @plugindesc [Base] Tween-animation Engine (v.2.2.1)
|
||
* @author Rutan(ru_shalm)
|
||
* @license public domain
|
||
* @version 2.2.1
|
||
* @url https://raw.githubusercontent.com/rutan/torigoya-rpg-maker-plugin/gh-pages/TorigoyaMZ_FrameTween.js
|
||
* @help
|
||
* [Base] Tween-animation Engine (v.2.2.1)
|
||
* https://torigoya-plugin.rutan.dev
|
||
*
|
||
* This plugin is a base-plugin for Torigoya plugins.
|
||
*/
|
||
|
||
/*:ja
|
||
* @target MZ
|
||
* @plugindesc [鳥小屋.txt ベースプラグイン] Tweenアニメーション (v.2.2.1)
|
||
* @author Ruたん(ru_shalm)
|
||
* @license public domain
|
||
* @version 2.2.1
|
||
* @url https://raw.githubusercontent.com/rutan/torigoya-rpg-maker-plugin/gh-pages/TorigoyaMZ_FrameTween.js
|
||
* @help
|
||
* [鳥小屋.txt ベースプラグイン] Tweenアニメーション (v.2.2.1)
|
||
* https://torigoya-plugin.rutan.dev
|
||
*
|
||
* このプラグインはベースプラグインです。
|
||
* このプラグインを導入しただけでは特に何も起きません。
|
||
* Tweenアニメーション用の処理を追加します。
|
||
*/
|
||
|
||
(function () {
|
||
'use strict';
|
||
|
||
// Bundled with Packemon: https://packemon.dev
|
||
// Platform: browser, Support: stable, Format: esm
|
||
|
||
const linear = (n) => n;
|
||
const easeInSine = (n) => 1 - Math.cos((n * Math.PI) / 2);
|
||
const easeOutSine = (n) => Math.sin((n * Math.PI) / 2);
|
||
const easeInOutSine = (n) => (1 - Math.cos(n * Math.PI)) / 2;
|
||
const easeInQuad = (n) => n * n;
|
||
const easeOutQuad = (n) => n * (2 - n);
|
||
const easeInOutQuad = (n) => {
|
||
n *= 2;
|
||
if (n < 1) {
|
||
return (n * n) / 2;
|
||
} else {
|
||
--n;
|
||
return (1 + n * (2 - n)) / 2;
|
||
}
|
||
};
|
||
const easeInCubic = (n) => Math.pow(n, 3);
|
||
const easeOutCubic = (n) => {
|
||
--n;
|
||
return Math.pow(n, 3) + 1;
|
||
};
|
||
const easeInOutCubic = (n) => {
|
||
n *= 2;
|
||
if (n < 1) {
|
||
return Math.pow(n, 3) / 2;
|
||
} else {
|
||
n -= 2;
|
||
return (Math.pow(n, 3) + 2) / 2;
|
||
}
|
||
};
|
||
const easeInCircular = (n) => 1 - Math.sqrt(1 - n * n);
|
||
const easeOutCircular = (n) => {
|
||
n--;
|
||
return Math.sqrt(1 - n * n);
|
||
};
|
||
const easeInOutCircular = (n) => {
|
||
n *= 2;
|
||
if (n < 1) {
|
||
return -(Math.sqrt(1 - n * n) - 1) / 2;
|
||
} else {
|
||
n -= 2;
|
||
return (Math.sqrt(1 - n * n) + 1) / 2;
|
||
}
|
||
};
|
||
class Group {
|
||
_items = [];
|
||
get length() {
|
||
return this._items.length;
|
||
}
|
||
clear() {
|
||
this._items.forEach(([tween, _]) => tween.abort());
|
||
this._items.length = 0;
|
||
}
|
||
add(tween) {
|
||
const state = {
|
||
startParams: {},
|
||
finishParams: {},
|
||
duration: 0,
|
||
easingFunc: linear,
|
||
timer: 0,
|
||
isWaitingCallback: false,
|
||
};
|
||
if (!this._beginAnimation(tween, state)) return;
|
||
this._items.push([tween, state]);
|
||
}
|
||
remove(tween) {
|
||
this._items = this._items.filter(([t, _]) => t !== tween);
|
||
}
|
||
update() {
|
||
const items = this._items.slice();
|
||
this._items.length = 0;
|
||
this._items = items
|
||
.filter(([tween, state]) => {
|
||
if (tween.finished) return false;
|
||
if (state.isWaitingCallback) return true;
|
||
++state.timer;
|
||
if (state.timer < state.duration) {
|
||
const n = state.easingFunc(state.timer / state.duration);
|
||
Object.keys(state.finishParams).forEach((key) => {
|
||
tween.target[key] =
|
||
state.startParams[key] + (state.finishParams[key] - state.startParams[key]) * n;
|
||
});
|
||
} else {
|
||
Object.keys(state.finishParams).forEach((key) => {
|
||
tween.target[key] = state.finishParams[key];
|
||
});
|
||
}
|
||
const result = state.timer < state.duration || this._beginAnimation(tween, state);
|
||
tween.callUpdateListeners();
|
||
if (!result) tween.abort();
|
||
return result;
|
||
})
|
||
.concat(this._items);
|
||
}
|
||
_beginAnimation(tween, state) {
|
||
while (true) {
|
||
const stack = tween.stacks.shift();
|
||
if (!stack) return false;
|
||
switch (stack.type) {
|
||
case 'call':
|
||
if (stack.func.length === 0) {
|
||
stack.func();
|
||
} else {
|
||
state.isWaitingCallback = true;
|
||
stack.func(() => (state.isWaitingCallback = false));
|
||
}
|
||
if (state.isWaitingCallback) {
|
||
return true;
|
||
} else {
|
||
break; // loop!
|
||
}
|
||
|
||
case 'move': {
|
||
const startParams = {};
|
||
Object.keys(stack.params).forEach((key) => {
|
||
startParams[key] = tween.target[key];
|
||
});
|
||
state.startParams = startParams;
|
||
state.finishParams = stack.params;
|
||
state.duration = stack.duration;
|
||
state.easingFunc = stack.easingFunc;
|
||
state.timer = 0;
|
||
return true;
|
||
}
|
||
}
|
||
}
|
||
}
|
||
}
|
||
class Tween {
|
||
_target;
|
||
_stacks;
|
||
_group;
|
||
_onUpdateListeners;
|
||
_finished;
|
||
constructor(target, initialParams) {
|
||
this._target = target;
|
||
this._stacks = [];
|
||
this._group = null;
|
||
this._onUpdateListeners = [];
|
||
this._finished = false;
|
||
if (initialParams) {
|
||
Object.keys(initialParams).forEach((key) => {
|
||
target[key] = initialParams[key];
|
||
});
|
||
}
|
||
}
|
||
get stacks() {
|
||
return this._stacks;
|
||
}
|
||
get target() {
|
||
return this._target;
|
||
}
|
||
get finished() {
|
||
return this._finished;
|
||
}
|
||
group(group) {
|
||
this._group = group;
|
||
return this;
|
||
}
|
||
addUpdateListener(func) {
|
||
this._onUpdateListeners.push(func);
|
||
return this;
|
||
}
|
||
removeUpdateListener(func) {
|
||
this._onUpdateListeners = this._onUpdateListeners.filter((f) => f !== func);
|
||
return this;
|
||
}
|
||
callUpdateListeners() {
|
||
this._onUpdateListeners.forEach((f) => f());
|
||
}
|
||
to(params, duration, easingFunc) {
|
||
this._stacks.push({
|
||
type: 'move',
|
||
params,
|
||
duration,
|
||
easingFunc: easingFunc || linear,
|
||
});
|
||
return this;
|
||
}
|
||
wait(duration) {
|
||
this._stacks.push({
|
||
type: 'move',
|
||
params: {},
|
||
duration,
|
||
easingFunc: linear,
|
||
});
|
||
return this;
|
||
}
|
||
call(func) {
|
||
this._stacks.push({
|
||
type: 'call',
|
||
func,
|
||
});
|
||
return this;
|
||
}
|
||
start() {
|
||
if (!this._group) throw new Error('not grouped');
|
||
this._group.add(this);
|
||
return this;
|
||
}
|
||
abort() {
|
||
this._stacks.length = 0;
|
||
this._finished = true;
|
||
return this;
|
||
}
|
||
}
|
||
|
||
const Torigoya = (window.Torigoya = window.Torigoya || {});
|
||
|
||
function getPluginName() {
|
||
const cs = document.currentScript;
|
||
return cs ? cs.src.split('/').pop().replace(/\.js$/, '') : 'TorigoyaMZ_FrameTween';
|
||
}
|
||
|
||
function readParameter() {
|
||
PluginManager.parameters(getPluginName());
|
||
return {
|
||
version: '2.2.1',
|
||
};
|
||
}
|
||
|
||
const globalGroup = new Group();
|
||
|
||
Torigoya.FrameTween = {
|
||
name: getPluginName(),
|
||
parameter: readParameter(),
|
||
Tween,
|
||
Group,
|
||
Easing: {
|
||
linear,
|
||
easeInSine,
|
||
easeOutSine,
|
||
easeInOutSine,
|
||
easeInQuad,
|
||
easeOutQuad,
|
||
easeInOutQuad,
|
||
easeInCubic,
|
||
easeOutCubic,
|
||
easeInOutCubic,
|
||
easeInCircular,
|
||
easeOutCircular,
|
||
easeInOutCircular,
|
||
},
|
||
group: globalGroup,
|
||
create(obj, initParams = {}) {
|
||
return new Tween(obj, initParams).group(globalGroup);
|
||
},
|
||
};
|
||
|
||
(() => {
|
||
const upstream_updateScene = SceneManager.updateScene;
|
||
SceneManager.updateScene = function () {
|
||
const isStarted = this._scene && this._scene.isStarted() && this.isGameActive();
|
||
upstream_updateScene.apply(this);
|
||
|
||
if (isStarted) Torigoya.FrameTween.group.update();
|
||
};
|
||
|
||
const upstream_onSceneTerminate = SceneManager.onSceneTerminate;
|
||
SceneManager.onSceneTerminate = function () {
|
||
upstream_onSceneTerminate.apply(this);
|
||
Torigoya.FrameTween.group.clear();
|
||
};
|
||
})();
|
||
})();
|