@litecanvas/utils 0.14.0 → 0.16.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +2 -1
- package/dist/actor.js +43 -15
- package/dist/actor.min.js +1 -1
- package/dist/all.js +219 -17
- package/dist/all.min.js +2 -2
- package/dist/math.js +14 -0
- package/dist/math.min.js +1 -1
- package/dist/tween.js +190 -0
- package/dist/tween.min.js +1 -0
- package/dist/vector.js +2 -2
- package/dist/vector.min.js +1 -1
- package/package.json +1 -1
- package/src/actor/README.md +31 -1
- package/src/actor/index.js +48 -15
- package/src/index.js +1 -0
- package/src/math/README.md +35 -0
- package/src/math/advance.js +20 -0
- package/src/math/index.js +1 -0
- package/src/tween/README.md +181 -0
- package/src/tween/_web.js +4 -0
- package/src/tween/index.js +170 -0
- package/src/vector/index.js +3 -2
package/dist/tween.js
ADDED
|
@@ -0,0 +1,190 @@
|
|
|
1
|
+
(() => {
|
|
2
|
+
var __defProp = Object.defineProperty;
|
|
3
|
+
var __export = (target, all) => {
|
|
4
|
+
for (var name in all)
|
|
5
|
+
__defProp(target, name, { get: all[name], enumerable: true });
|
|
6
|
+
};
|
|
7
|
+
|
|
8
|
+
// src/_global.js
|
|
9
|
+
globalThis.utils = globalThis.utils || {};
|
|
10
|
+
globalThis.utils.global = () => {
|
|
11
|
+
for (const key in globalThis.utils) {
|
|
12
|
+
if ("global" === key) continue;
|
|
13
|
+
globalThis[key] = globalThis.utils[key];
|
|
14
|
+
}
|
|
15
|
+
};
|
|
16
|
+
|
|
17
|
+
// src/tween/index.js
|
|
18
|
+
var tween_exports = {};
|
|
19
|
+
__export(tween_exports, {
|
|
20
|
+
BACK_IN: () => BACK_IN,
|
|
21
|
+
BACK_IN_OUT: () => BACK_IN_OUT,
|
|
22
|
+
BACK_OUT: () => BACK_OUT,
|
|
23
|
+
BOUNCE_IN: () => BOUNCE_IN,
|
|
24
|
+
BOUNCE_IN_OUT: () => BOUNCE_IN_OUT,
|
|
25
|
+
BOUNCE_OUT: () => BOUNCE_OUT,
|
|
26
|
+
EASE_IN: () => EASE_IN,
|
|
27
|
+
EASE_IN_OUT: () => EASE_IN_OUT,
|
|
28
|
+
EASE_OUT: () => EASE_OUT,
|
|
29
|
+
ELASTIC_IN: () => ELASTIC_IN,
|
|
30
|
+
ELASTIC_IN_OUT: () => ELASTIC_IN_OUT,
|
|
31
|
+
ELASTIC_OUT: () => ELASTIC_OUT,
|
|
32
|
+
LINEAR: () => LINEAR,
|
|
33
|
+
tween: () => tween
|
|
34
|
+
});
|
|
35
|
+
|
|
36
|
+
// node_modules/litecanvas/src/zzfx.js
|
|
37
|
+
globalThis.zzfxV = 1;
|
|
38
|
+
|
|
39
|
+
// src/tween/index.js
|
|
40
|
+
var HALF_PI = Math.PI / 2;
|
|
41
|
+
var tween = (object, prop, toValue, duration = 1, easing = LINEAR) => {
|
|
42
|
+
return new TweenController(object, prop, toValue, duration, easing);
|
|
43
|
+
};
|
|
44
|
+
var LINEAR = (n) => n;
|
|
45
|
+
var EASE_IN = (n) => n * n;
|
|
46
|
+
var EASE_OUT = (n) => -n * (n - 2);
|
|
47
|
+
var EASE_IN_OUT = (n) => {
|
|
48
|
+
if (n < 0.5) {
|
|
49
|
+
return 2 * n * n;
|
|
50
|
+
}
|
|
51
|
+
return -2 * n * n + 4 * n - 1;
|
|
52
|
+
};
|
|
53
|
+
var BACK_IN = (n) => n * n * n - n * Math.sin(n * Math.PI);
|
|
54
|
+
var BACK_OUT = (n) => {
|
|
55
|
+
let a = 1 - n;
|
|
56
|
+
return 1 - (a * a * a - a * Math.sin(a * Math.PI));
|
|
57
|
+
};
|
|
58
|
+
var BACK_IN_OUT = (n) => {
|
|
59
|
+
if (n < 0.5) {
|
|
60
|
+
let a2 = 2 * n;
|
|
61
|
+
return 0.5 * (a2 * a2 * a2 - a2 * Math.sin(a2 * Math.PI));
|
|
62
|
+
}
|
|
63
|
+
let a = 1 - (2 * n - 1);
|
|
64
|
+
return 0.5 * (1 - (a * a * a - a * Math.sin(n * Math.PI))) + 0.5;
|
|
65
|
+
};
|
|
66
|
+
var ELASTIC_IN = (n) => {
|
|
67
|
+
return Math.sin(13 * HALF_PI * n) * Math.pow(2, 10 * (n - 1));
|
|
68
|
+
};
|
|
69
|
+
var ELASTIC_OUT = (n) => {
|
|
70
|
+
return Math.sin(-13 * HALF_PI * (n + 1)) * Math.pow(2, -10 * n) + 1;
|
|
71
|
+
};
|
|
72
|
+
var ELASTIC_IN_OUT = (n) => {
|
|
73
|
+
if (n < 0.5) {
|
|
74
|
+
let a2 = Math.sin(13 * HALF_PI * (2 * n));
|
|
75
|
+
let b2 = Math.pow(2, 10 * (2 * n - 1));
|
|
76
|
+
return 0.5 * a2 * b2;
|
|
77
|
+
}
|
|
78
|
+
let a = Math.sin(-13 * HALF_PI * (2 * n - 1 + 1));
|
|
79
|
+
let b = Math.pow(2, -10 * (2 * n - 1));
|
|
80
|
+
return 0.5 * (a * b + 2);
|
|
81
|
+
};
|
|
82
|
+
var BOUNCE_IN = (n) => 1 - BOUNCE_OUT(1 - n);
|
|
83
|
+
var BOUNCE_OUT = (n) => {
|
|
84
|
+
if (n < 4 / 11) {
|
|
85
|
+
return 121 * n * n / 16;
|
|
86
|
+
} else if (n < 8 / 11) {
|
|
87
|
+
return 363 / 40 * n * n - 99 / 10 * n + 17 / 5;
|
|
88
|
+
} else if (n < 9 / 10) {
|
|
89
|
+
return 4356 / 361 * n * n - 35442 / 1805 * n + 16061 / 1805;
|
|
90
|
+
}
|
|
91
|
+
return 54 / 5 * n * n - 513 / 25 * n + 268 / 25;
|
|
92
|
+
};
|
|
93
|
+
var BOUNCE_IN_OUT = (n) => {
|
|
94
|
+
if (n < 0.5) {
|
|
95
|
+
return 0.5 * BOUNCE_IN(n * 2);
|
|
96
|
+
}
|
|
97
|
+
return 0.5 * BOUNCE_OUT(n * 2 - 1) + 0.5;
|
|
98
|
+
};
|
|
99
|
+
var TweenController = class {
|
|
100
|
+
/** @type {boolean} */
|
|
101
|
+
running = false;
|
|
102
|
+
/** @type {*} */
|
|
103
|
+
_o;
|
|
104
|
+
/** @type {string} */
|
|
105
|
+
_p;
|
|
106
|
+
/** @type {number} */
|
|
107
|
+
_x;
|
|
108
|
+
/** @type {number} */
|
|
109
|
+
_d;
|
|
110
|
+
/** @type {(x: number) => number} */
|
|
111
|
+
_e;
|
|
112
|
+
/** @type {Function[]} */
|
|
113
|
+
_cb = [];
|
|
114
|
+
/** @type {number} */
|
|
115
|
+
_t = 0;
|
|
116
|
+
/** @type {Function} */
|
|
117
|
+
_u = 0;
|
|
118
|
+
/** @type {LitecanvasInstance} */
|
|
119
|
+
_lc;
|
|
120
|
+
/**
|
|
121
|
+
* @param {*} object
|
|
122
|
+
* @param {string} prop
|
|
123
|
+
* @param {number} toValue
|
|
124
|
+
* @param {number} duration
|
|
125
|
+
* @param {(x: number) => number} easing
|
|
126
|
+
*/
|
|
127
|
+
constructor(object, prop, toValue, duration, easing) {
|
|
128
|
+
this._o = object;
|
|
129
|
+
this._p = prop;
|
|
130
|
+
this._x = toValue;
|
|
131
|
+
this._d = duration;
|
|
132
|
+
this._e = easing;
|
|
133
|
+
}
|
|
134
|
+
/**
|
|
135
|
+
*
|
|
136
|
+
* @param {LitecanvasInstance} engine
|
|
137
|
+
*/
|
|
138
|
+
start(engine = globalThis) {
|
|
139
|
+
if (!this.running) {
|
|
140
|
+
this.stop();
|
|
141
|
+
}
|
|
142
|
+
const fromValue = this._o[this._p] || 0;
|
|
143
|
+
this._lc = engine;
|
|
144
|
+
this._u = engine.listen("update", (dt) => {
|
|
145
|
+
this._o[this._p] = engine.lerp(
|
|
146
|
+
fromValue,
|
|
147
|
+
this._x,
|
|
148
|
+
this._e(this._t / this._d)
|
|
149
|
+
);
|
|
150
|
+
this._t += dt;
|
|
151
|
+
if (this._t >= this._d) {
|
|
152
|
+
this._o[this._p] = this._x;
|
|
153
|
+
this.stop();
|
|
154
|
+
}
|
|
155
|
+
});
|
|
156
|
+
this.running = true;
|
|
157
|
+
return this;
|
|
158
|
+
}
|
|
159
|
+
/**
|
|
160
|
+
* @param {Function} callback
|
|
161
|
+
*/
|
|
162
|
+
onEnd(callback) {
|
|
163
|
+
this._cb.push(callback);
|
|
164
|
+
}
|
|
165
|
+
/**
|
|
166
|
+
* @param {boolean} completed if `false` don't call the `onEnd()` registered callbacks.
|
|
167
|
+
* @returns
|
|
168
|
+
*/
|
|
169
|
+
stop(completed = true) {
|
|
170
|
+
if (!this.running || !this._u) return;
|
|
171
|
+
this.running = false;
|
|
172
|
+
this._u();
|
|
173
|
+
if (completed) {
|
|
174
|
+
for (const callback of this._cb) {
|
|
175
|
+
callback(this._o);
|
|
176
|
+
}
|
|
177
|
+
}
|
|
178
|
+
}
|
|
179
|
+
reset() {
|
|
180
|
+
this._cb.length = 0;
|
|
181
|
+
this.stop();
|
|
182
|
+
}
|
|
183
|
+
get progress() {
|
|
184
|
+
return this.running ? this._t / this._d : 0;
|
|
185
|
+
}
|
|
186
|
+
};
|
|
187
|
+
|
|
188
|
+
// src/tween/_web.js
|
|
189
|
+
globalThis.utils = Object.assign(globalThis.utils || {}, tween_exports);
|
|
190
|
+
})();
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
(()=>{var p=Object.defineProperty;var h=(t,e)=>{for(var o in e)p(t,o,{get:e[o],enumerable:!0})};globalThis.utils=globalThis.utils||{};globalThis.utils.global=()=>{for(let t in globalThis.utils)t!=="global"&&(globalThis[t]=globalThis.utils[t])};var l={};h(l,{BACK_IN:()=>x,BACK_IN_OUT:()=>m,BACK_OUT:()=>E,BOUNCE_IN:()=>f,BOUNCE_IN_OUT:()=>w,BOUNCE_OUT:()=>n,EASE_IN:()=>_,EASE_IN_OUT:()=>T,EASE_OUT:()=>g,ELASTIC_IN:()=>I,ELASTIC_IN_OUT:()=>y,ELASTIC_OUT:()=>b,LINEAR:()=>c,tween:()=>d});globalThis.zzfxV=1;var r=Math.PI/2,d=(t,e,o,s=1,i=c)=>new a(t,e,o,s,i),c=t=>t,_=t=>t*t,g=t=>-t*(t-2),T=t=>t<.5?2*t*t:-2*t*t+4*t-1,x=t=>t*t*t-t*Math.sin(t*Math.PI),E=t=>{let e=1-t;return 1-(e*e*e-e*Math.sin(e*Math.PI))},m=t=>{if(t<.5){let o=2*t;return .5*(o*o*o-o*Math.sin(o*Math.PI))}let e=1-(2*t-1);return .5*(1-(e*e*e-e*Math.sin(t*Math.PI)))+.5},I=t=>Math.sin(13*r*t)*Math.pow(2,10*(t-1)),b=t=>Math.sin(-13*r*(t+1))*Math.pow(2,-10*t)+1,y=t=>{if(t<.5){let s=Math.sin(13*r*(2*t)),i=Math.pow(2,10*(2*t-1));return .5*s*i}let e=Math.sin(-13*r*(2*t-1+1)),o=Math.pow(2,-10*(2*t-1));return .5*(e*o+2)},f=t=>1-n(1-t),n=t=>t<4/11?121*t*t/16:t<8/11?363/40*t*t-99/10*t+17/5:t<9/10?4356/361*t*t-35442/1805*t+16061/1805:54/5*t*t-513/25*t+268/25,w=t=>t<.5?.5*f(t*2):.5*n(t*2-1)+.5,a=class{running=!1;_o;_p;_x;_d;_e;_cb=[];_t=0;_u=0;_lc;constructor(e,o,s,i,u){this._o=e,this._p=o,this._x=s,this._d=i,this._e=u}start(e=globalThis){this.running||this.stop();let o=this._o[this._p]||0;return this._lc=e,this._u=e.listen("update",s=>{this._o[this._p]=e.lerp(o,this._x,this._e(this._t/this._d)),this._t+=s,this._t>=this._d&&(this._o[this._p]=this._x,this.stop())}),this.running=!0,this}onEnd(e){this._cb.push(e)}stop(e=!0){if(!(!this.running||!this._u)&&(this.running=!1,this._u(),e))for(let o of this._cb)o(this._o)}reset(){this._cb.length=0,this.stop()}get progress(){return this.running?this._t/this._d:0}};globalThis.utils=Object.assign(globalThis.utils||{},l);})();
|
package/dist/vector.js
CHANGED
package/dist/vector.min.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
(()=>{var A=Object.defineProperty;var C=(t,e)=>{for(var o in e)A(t,o,{get:e[o],enumerable:!0})};var h={};C(h,{DOWN:()=>K,LEFT:()=>Q,ONE:()=>k,RIGHT:()=>J,UP:()=>z,Vector:()=>s,ZERO:()=>q,vec:()=>c,vecAbs:()=>j,vecAdd:()=>i,vecAngle:()=>P,vecAngleBetween:()=>w,vecCeil:()=>B,vecClamp:()=>H,vecCross:()=>U,vecDist:()=>L,vecDist2:()=>N,vecDiv:()=>y,vecDot:()=>T,vecEq:()=>u,vecFloor:()=>F,vecIsZero:()=>W,vecLerp:()=>Z,vecLimit:()=>b,vecMag:()=>R,vecMag2:()=>D,vecMove:()=>V,vecMult:()=>x,vecNorm:()=>l,vecRand:()=>$,vecReflect:()=>O,vecRotate:()=>I,vecRound:()=>G,vecSet:()=>g,vecSetMag:()=>S,vecSub:()=>a});var p=Math.sqrt,f=Math.cos,d=Math.sin,E=2*Math.PI,s=class{x;y;constructor(e=0,o=e){this.x=e,this.y=o}toString(){return`Vector (${this.x}, ${this.y})`}},n=t=>t instanceof s,c=(t=0,e=t)=>(n(t)&&(e=t.y,t=t.x),new s(t,e)),u=(t,e,o=e)=>n(e)?u(t,e.x,e.y):t.x===e&&t.y===o,g=(t,e,o=e)=>(n(e)?g(t,e.x,e.y):(t.x=e,t.y=o),t),i=(t,e,o=e)=>n(e)?i(t,e.x,e.y):(t.x+=e,t.y+=o,t),a=(t,e,o=e)=>n(e)?a(t,e.x,e.y):(t.x-=e,t.y-=o,t),x=(t,e,o=e)=>n(e)?x(t,e.x,e.y):(t.x*=e,t.y*=o,t),y=(t,e,o=e)=>n(e)?y(t,e.x,e.y):(t.x/=e,t.y/=o,t),I=(t,e)=>{let o=f(e),r=d(e);return t.x=o*t.x-r*t.y,t.y=r*t.x+o*t.y,t},O=(t,e)=>{let o=l(c(e));return a(t,x(o,2*T(t,o)))},S=(t,e)=>(l(t),x(t,e),t),R=t=>p(t.x*t.x+t.y*t.y),D=t=>t.x*t.x+t.y*t.y,l=t=>{let e=R(t);return e>0&&y(t,e),t},b=(t,e=1)=>{let o=D(t);return o>e*e&&(y(t,p(o)),x(t,e)),t},L=(t,e)=>{let o=t.x-e.x,r=t.y-e.y;return p(o*o+r*r)},N=(t,e)=>{let o=t.x-e.x,r=t.y-e.y;return o*o+r*r},P=t=>Math.atan2(t.y,t.x),w=(t,e)=>Math.atan2(e.y-t.y,e.x-t.x),T=(t,e)=>t.x*e.x+t.y*e.y,U=(t,e)=>t.x*e.y-t.y*e.x,Z=(t,e,o)=>(t.x+=(e.x-t.x)*o||0,t.y+=(e.y-t.y)*o||0,t),$=(t=1,e=t,o=globalThis.rand||Math.random)=>{let r=o()*E,M=o()*(e-t)+t;return c(f(r)*M,d(r)*M)},j=t=>(t.x=Math.abs(t.x),t.y=Math.abs(t.y),t),B=t=>(t.x=Math.ceil(t.x),t.y=Math.ceil(t.y),t),F=t=>(t.x=Math.floor(t.x),t.y=Math.floor(t.y),t),G=t=>(t.x=Math.round(t.x),t.y=Math.round(t.y),t),H=(t,e,o)=>(t.x<e.x&&(t.x=e.x),t.x>o.x&&(t.x=o.x),t.y<e.y&&(t.y=e.y),t.y>o.y&&(t.y=o.y),t),V=(t,e,o=1)=>i(t,e.x*o,e.y*o),W=t=>u(t,q),q=c(0,0),k=c(1,1),z=c(0,-1),J=c(1,0),K=c(0,1),Q=c(-1,0);globalThis.utils=Object.assign(globalThis.utils||{},h);})();
|
|
1
|
+
(()=>{var A=Object.defineProperty;var C=(t,e)=>{for(var o in e)A(t,o,{get:e[o],enumerable:!0})};var h={};C(h,{DOWN:()=>K,LEFT:()=>Q,ONE:()=>k,RIGHT:()=>J,UP:()=>z,Vector:()=>s,ZERO:()=>q,vec:()=>c,vecAbs:()=>j,vecAdd:()=>i,vecAngle:()=>P,vecAngleBetween:()=>w,vecCeil:()=>B,vecClamp:()=>H,vecCross:()=>U,vecDist:()=>L,vecDist2:()=>N,vecDiv:()=>y,vecDot:()=>T,vecEq:()=>u,vecFloor:()=>F,vecIsZero:()=>W,vecLerp:()=>Z,vecLimit:()=>b,vecMag:()=>R,vecMag2:()=>D,vecMove:()=>V,vecMult:()=>x,vecNorm:()=>l,vecRand:()=>$,vecReflect:()=>O,vecRotate:()=>I,vecRound:()=>G,vecSet:()=>g,vecSetMag:()=>S,vecSub:()=>a});var p=Math.sqrt,f=Math.cos,d=Math.sin,E=2*Math.PI,s=class{x;y;constructor(e=0,o=e){this.x=e,this.y=o}toString(){return`Vector (${this.x}, ${this.y})`}},n=t=>t instanceof s,c=(t=0,e=t)=>(n(t)&&(e=t.y,t=t.x),new s(t,e)),u=(t,e,o=e)=>n(e)?u(t,e.x,e.y):t.x===e&&t.y===o,g=(t,e,o=e)=>(n(e)?g(t,e.x,e.y):(t.x=e,t.y=o),t),i=(t,e,o=e)=>n(e)?i(t,e.x,e.y):(t.x+=e,t.y+=o,t),a=(t,e,o=e)=>n(e)?a(t,e.x,e.y):(t.x-=e,t.y-=o,t),x=(t,e,o=e)=>n(e)?x(t,e.x,e.y):(t.x*=e,t.y*=o,t),y=(t,e,o=e)=>n(e)?y(t,e.x,e.y):(t.x/=e||1,t.y/=o||1,t),I=(t,e)=>{let o=f(e),r=d(e);return t.x=o*t.x-r*t.y,t.y=r*t.x+o*t.y,t},O=(t,e)=>{let o=l(c(e));return a(t,x(o,2*T(t,o)))},S=(t,e)=>(l(t),x(t,e),t),R=t=>p(t.x*t.x+t.y*t.y),D=t=>t.x*t.x+t.y*t.y,l=t=>{let e=R(t);return e>0&&y(t,e),t},b=(t,e=1)=>{let o=D(t);return o>e*e&&(y(t,p(o)),x(t,e)),t},L=(t,e)=>{let o=t.x-e.x,r=t.y-e.y;return p(o*o+r*r)},N=(t,e)=>{let o=t.x-e.x,r=t.y-e.y;return o*o+r*r},P=t=>Math.atan2(t.y,t.x),w=(t,e)=>Math.atan2(e.y-t.y,e.x-t.x),T=(t,e)=>t.x*e.x+t.y*e.y,U=(t,e)=>t.x*e.y-t.y*e.x,Z=(t,e,o)=>(t.x+=(e.x-t.x)*o||0,t.y+=(e.y-t.y)*o||0,t),$=(t=1,e=t,o=globalThis.rand||Math.random)=>{let r=o()*E,M=o()*(e-t)+t;return c(f(r)*M,d(r)*M)},j=t=>(t.x=Math.abs(t.x),t.y=Math.abs(t.y),t),B=t=>(t.x=Math.ceil(t.x),t.y=Math.ceil(t.y),t),F=t=>(t.x=Math.floor(t.x),t.y=Math.floor(t.y),t),G=t=>(t.x=Math.round(t.x),t.y=Math.round(t.y),t),H=(t,e,o)=>(t.x<e.x&&(t.x=e.x),t.x>o.x&&(t.x=o.x),t.y<e.y&&(t.y=e.y),t.y>o.y&&(t.y=o.y),t),V=(t,e,o=1)=>i(t,e.x*o,e.y*o),W=t=>u(t,q),q=c(0,0),k=c(1,1),z=c(0,-1),J=c(1,0),K=c(0,1),Q=c(-1,0);globalThis.utils=Object.assign(globalThis.utils||{},h);})();
|
package/package.json
CHANGED
package/src/actor/README.md
CHANGED
|
@@ -56,7 +56,7 @@ player.y = 200
|
|
|
56
56
|
|
|
57
57
|
## Actor#scale
|
|
58
58
|
|
|
59
|
-
Set or get the actor scale
|
|
59
|
+
Set or get the actor scale vector
|
|
60
60
|
|
|
61
61
|
```js
|
|
62
62
|
// twice bigger
|
|
@@ -64,6 +64,36 @@ player.scale.x = 2
|
|
|
64
64
|
player.scale.y = 2
|
|
65
65
|
```
|
|
66
66
|
|
|
67
|
+
## Actor#scaleBy(x, y = x)
|
|
68
|
+
|
|
69
|
+
```js
|
|
70
|
+
// multiplies the scale (y is optional)
|
|
71
|
+
player.scaleBy(3)
|
|
72
|
+
|
|
73
|
+
// same as
|
|
74
|
+
player.scale.x *= 3
|
|
75
|
+
player.scale.y *= 3
|
|
76
|
+
```
|
|
77
|
+
|
|
78
|
+
## Actor#scaleTo(x, y = x)
|
|
79
|
+
|
|
80
|
+
```js
|
|
81
|
+
// sets the scale (y is optional)
|
|
82
|
+
player.scaleTo(3)
|
|
83
|
+
|
|
84
|
+
// same as
|
|
85
|
+
player.scale.x = 3
|
|
86
|
+
player.scale.y = 3
|
|
87
|
+
```
|
|
88
|
+
|
|
89
|
+
## Actor#flipX
|
|
90
|
+
|
|
91
|
+
If `true` the actor sprite is flipped horizontally. Default is `false`.
|
|
92
|
+
|
|
93
|
+
## Actor#flipY
|
|
94
|
+
|
|
95
|
+
If `true` the actor sprite is flipped vertically. Default is `false`.
|
|
96
|
+
|
|
67
97
|
## Actor#anchor
|
|
68
98
|
|
|
69
99
|
Set or get the actor anchor (origin). By default, the anchor is a vector `(0, 0)` (meaning anchor Top Left).
|
package/src/actor/index.js
CHANGED
|
@@ -1,11 +1,11 @@
|
|
|
1
1
|
import { Vector, vec } from "../vector/index.js"
|
|
2
2
|
import "litecanvas"
|
|
3
3
|
|
|
4
|
-
export const ANCHOR_CENTER = vec(0.5, 0.5)
|
|
5
|
-
export const ANCHOR_TOP_LEFT = vec(0, 0)
|
|
6
|
-
export const ANCHOR_TOP_RIGHT = vec(1, 0)
|
|
7
|
-
export const ANCHOR_BOT_LEFT = vec(0, 1)
|
|
8
|
-
export const ANCHOR_BOT_RIGHT = vec(1, 1)
|
|
4
|
+
export const ANCHOR_CENTER = /** @__PURE__ */ vec(0.5, 0.5)
|
|
5
|
+
export const ANCHOR_TOP_LEFT = /** @__PURE__ */ vec(0, 0)
|
|
6
|
+
export const ANCHOR_TOP_RIGHT = /** @__PURE__ */ vec(1, 0)
|
|
7
|
+
export const ANCHOR_BOT_LEFT = /** @__PURE__ */ vec(0, 1)
|
|
8
|
+
export const ANCHOR_BOT_RIGHT = /** @__PURE__ */ vec(1, 1)
|
|
9
9
|
|
|
10
10
|
export class Actor {
|
|
11
11
|
/** @type {Image|HTMLCanvasElement|OffscreenCanvas} */
|
|
@@ -20,6 +20,12 @@ export class Actor {
|
|
|
20
20
|
/** @type {Vector} The actor scale */
|
|
21
21
|
_s
|
|
22
22
|
|
|
23
|
+
/** @type {boolean} */
|
|
24
|
+
flipX = false
|
|
25
|
+
|
|
26
|
+
/** @type {boolean} */
|
|
27
|
+
flipY = false
|
|
28
|
+
|
|
23
29
|
/** @type {number} The actor angle (in radians) */
|
|
24
30
|
angle = 0
|
|
25
31
|
|
|
@@ -105,6 +111,28 @@ export class Actor {
|
|
|
105
111
|
return this._s
|
|
106
112
|
}
|
|
107
113
|
|
|
114
|
+
/**
|
|
115
|
+
* Sets the actor scale
|
|
116
|
+
*
|
|
117
|
+
* @param {number} x
|
|
118
|
+
* @param {number} [y]
|
|
119
|
+
*/
|
|
120
|
+
scaleTo(x, y = x) {
|
|
121
|
+
this._s.x = x
|
|
122
|
+
this._s.y = y
|
|
123
|
+
}
|
|
124
|
+
|
|
125
|
+
/**
|
|
126
|
+
* Multiplies the actor scale
|
|
127
|
+
*
|
|
128
|
+
* @param {number} x
|
|
129
|
+
* @param {number} [y]
|
|
130
|
+
*/
|
|
131
|
+
scaleBy(x, y = x) {
|
|
132
|
+
this._s.x *= x
|
|
133
|
+
this._s.y *= y
|
|
134
|
+
}
|
|
135
|
+
|
|
108
136
|
/**
|
|
109
137
|
* @returns {number[]}
|
|
110
138
|
*/
|
|
@@ -117,19 +145,19 @@ export class Actor {
|
|
|
117
145
|
}
|
|
118
146
|
|
|
119
147
|
/**
|
|
120
|
-
*
|
|
148
|
+
* Draw the actor
|
|
121
149
|
*
|
|
122
150
|
* @param {LitecanvasInstance} [litecanvas]
|
|
123
151
|
*/
|
|
124
|
-
draw(litecanvas = globalThis) {
|
|
152
|
+
draw(litecanvas = globalThis, saveContext = true) {
|
|
125
153
|
if (this.hidden || this.opacity <= 0) return
|
|
126
154
|
|
|
127
|
-
litecanvas.push()
|
|
155
|
+
if (saveContext) litecanvas.push()
|
|
128
156
|
|
|
129
157
|
this.transform(litecanvas)
|
|
130
158
|
this.drawImage(litecanvas)
|
|
131
159
|
|
|
132
|
-
litecanvas.pop()
|
|
160
|
+
if (saveContext) litecanvas.pop()
|
|
133
161
|
}
|
|
134
162
|
|
|
135
163
|
/**
|
|
@@ -138,16 +166,21 @@ export class Actor {
|
|
|
138
166
|
transform(litecanvas) {
|
|
139
167
|
litecanvas.translate(this.pos.x, this.pos.y)
|
|
140
168
|
litecanvas.rotate(this.angle)
|
|
141
|
-
litecanvas.scale(
|
|
169
|
+
litecanvas.scale(
|
|
170
|
+
(this.flipX ? -1 : 1) * this._s.x,
|
|
171
|
+
(this.flipY ? -1 : 1) * this._s.y
|
|
172
|
+
)
|
|
142
173
|
}
|
|
143
174
|
|
|
144
175
|
/**
|
|
145
176
|
* @param {LitecanvasInstance} litecanvas
|
|
146
177
|
*/
|
|
147
|
-
drawImage(litecanvas) {
|
|
148
|
-
const
|
|
149
|
-
const
|
|
150
|
-
|
|
151
|
-
|
|
178
|
+
drawImage(litecanvas, alpha = true) {
|
|
179
|
+
const anchor = this.anchor
|
|
180
|
+
const x = -this.sprite.width * (this.flipX ? 1 - anchor.x : anchor.x)
|
|
181
|
+
const y = -this.sprite.height * (this.flipY ? 1 - anchor.y : anchor.y)
|
|
182
|
+
|
|
183
|
+
if (alpha) litecanvas.alpha(this.opacity)
|
|
184
|
+
litecanvas.image(x, y, this.sprite)
|
|
152
185
|
}
|
|
153
186
|
}
|
package/src/index.js
CHANGED
package/src/math/README.md
CHANGED
|
@@ -62,6 +62,41 @@ function draw() {
|
|
|
62
62
|
}
|
|
63
63
|
```
|
|
64
64
|
|
|
65
|
+
[See in playground](https://litecanvas.js.org?c=eJwlyrEKwjAUheE9T3HGBKME0UVwEM0mIuqgY4ytBC6JNGlLKXl3bVwOP4evTY7i4k3haYgLRi5V1vjORD4ygEL4bDDi1ZgeWbIsGKtbb5MLvpxcYHKWIldiiuBjwoAtetNVfL5USqKMPu7OV30oyDW2dkR8r083fblL%2FOOBGQaJ9U%2BvBMtfqxAsyg%3D%3D)
|
|
66
|
+
|
|
67
|
+
## advance
|
|
68
|
+
|
|
69
|
+
Returns a sequence of numbers from `0` to `size - 1`.
|
|
70
|
+
|
|
71
|
+
Syntax: `range(size: number): number[]`
|
|
72
|
+
|
|
73
|
+
```js
|
|
74
|
+
import litecanvas from "litecanvas"
|
|
75
|
+
import { vec, advance } from "@litecanvas/utils"
|
|
76
|
+
|
|
77
|
+
litecanvas()
|
|
78
|
+
|
|
79
|
+
function init() {
|
|
80
|
+
pos = vec(0, CENTERY)
|
|
81
|
+
vel = vec(0, 0)
|
|
82
|
+
acc = vec(100, 0)
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
function update(dt) {
|
|
86
|
+
advance(pos, vel, acc, dt)
|
|
87
|
+
if (pos.x > WIDTH) {
|
|
88
|
+
pos.x = 0
|
|
89
|
+
}
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
function draw() {
|
|
93
|
+
cls(0)
|
|
94
|
+
circ(pos.x, pos.y, 48, 4)
|
|
95
|
+
}
|
|
96
|
+
```
|
|
97
|
+
|
|
98
|
+
[See in playground](https://litecanvas.js.org?c=eJxVjjELwjAQhff%2BihtTCKWCg0tdtKCLgxTEMV5SCYS0NGlUpP%2FdS1NQhxvue7yPN3ptXHE33U0YlmdGe4XCBuHoydrRotedBW21Zzm8M4C%2Bc1BBUMhKDrv61NTna048KPPlZSQCcSGrMrHpRzn2UnjFpE9aIYOwqBjpeXTxWOdAMYW6hRgUT9jC5bhvDqkzjyFYQUnf9KeXg3gsi9E4Ng9CPWDy8Ln54rDe0NGwDwbOS1Q%3D)
|
|
99
|
+
|
|
65
100
|
## range
|
|
66
101
|
|
|
67
102
|
Returns a sequence of numbers from `0` to `size - 1`.
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import { Vector, vecMult, vecAdd } from "../vector"
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* Move a vector (position) using another vectors: velocity and acceleration (optional).
|
|
5
|
+
* Note: This function changes the position and velocity vectors.
|
|
6
|
+
*
|
|
7
|
+
* @param {Vector} position
|
|
8
|
+
* @param {Vector} velocity
|
|
9
|
+
* @param {Vector?} acceleration
|
|
10
|
+
* @param {number?} deltaTime
|
|
11
|
+
*/
|
|
12
|
+
export default advance = (position, velocity, acceleration, deltaTime = 1) => {
|
|
13
|
+
if (acceleration) {
|
|
14
|
+
velocity.x += acceleration.x * deltaTime
|
|
15
|
+
velocity.y += acceleration.y * deltaTime
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
position.x += velocity.x * deltaTime
|
|
19
|
+
position.y += velocity.y * deltaTime
|
|
20
|
+
}
|
package/src/math/index.js
CHANGED
|
@@ -0,0 +1,181 @@
|
|
|
1
|
+
# Tween
|
|
2
|
+
|
|
3
|
+
You can animate object property using the `tween().`
|
|
4
|
+
|
|
5
|
+
**CDN**: https://unpkg.com/@litecanvas/utils/dist/tween.js
|
|
6
|
+
|
|
7
|
+
## tween
|
|
8
|
+
|
|
9
|
+
Animate a object property over time.
|
|
10
|
+
|
|
11
|
+
Syntax:
|
|
12
|
+
|
|
13
|
+
```ts
|
|
14
|
+
tween(
|
|
15
|
+
object: any,
|
|
16
|
+
prop: string,
|
|
17
|
+
toValue: number,
|
|
18
|
+
duration?: number, // default: 1
|
|
19
|
+
easing?: (n: number) => number // default: LINEAR (see below)
|
|
20
|
+
): TweenController
|
|
21
|
+
```
|
|
22
|
+
|
|
23
|
+
```js
|
|
24
|
+
// basic example
|
|
25
|
+
// move the rect position x from 100 to 250 over 2 seconds
|
|
26
|
+
import litecanvas from "litecanvas"
|
|
27
|
+
import { tween } from "@litecanvas/utils"
|
|
28
|
+
|
|
29
|
+
let object
|
|
30
|
+
|
|
31
|
+
litecanvas()
|
|
32
|
+
|
|
33
|
+
function init() {
|
|
34
|
+
pos = {
|
|
35
|
+
x: 100,
|
|
36
|
+
y: CENTERY,
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
// create the animation
|
|
40
|
+
const animation = tween(pos, "x", 250, 2)
|
|
41
|
+
|
|
42
|
+
// start the animation
|
|
43
|
+
animation.start()
|
|
44
|
+
|
|
45
|
+
// or just
|
|
46
|
+
// tween(...).start()
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
function draw() {
|
|
50
|
+
cls(0)
|
|
51
|
+
// draw the animated rect
|
|
52
|
+
rectfill(pos.x, pos.y, 50, 50, 3)
|
|
53
|
+
}
|
|
54
|
+
```
|
|
55
|
+
|
|
56
|
+
## TweenController
|
|
57
|
+
|
|
58
|
+
### TweenController#start()
|
|
59
|
+
|
|
60
|
+
Starts the animation
|
|
61
|
+
|
|
62
|
+
Syntax: `.start(engine?: LitecanvasInstance): TweenController`
|
|
63
|
+
|
|
64
|
+
```js
|
|
65
|
+
// if your litecanvas has config.global = false
|
|
66
|
+
// you need to pass the engine instance to all animations
|
|
67
|
+
const engine = litecanvas({
|
|
68
|
+
global: false
|
|
69
|
+
})
|
|
70
|
+
|
|
71
|
+
function init () {
|
|
72
|
+
engine.tween(...).start(engine)
|
|
73
|
+
}
|
|
74
|
+
```
|
|
75
|
+
|
|
76
|
+
```js
|
|
77
|
+
// otherwhise, just call `start()` without arguments
|
|
78
|
+
const engine = litecanvas({
|
|
79
|
+
// global: true // default value
|
|
80
|
+
})
|
|
81
|
+
|
|
82
|
+
function init () {
|
|
83
|
+
// just call start
|
|
84
|
+
engine.tween(...).start()
|
|
85
|
+
}
|
|
86
|
+
```
|
|
87
|
+
|
|
88
|
+
### TweenController#onEnd()
|
|
89
|
+
|
|
90
|
+
Enqueues a callback to be executed when the animation finishes.
|
|
91
|
+
|
|
92
|
+
Syntax: `.onEnd(callback?: (object:any) => void): void`
|
|
93
|
+
|
|
94
|
+
```js
|
|
95
|
+
// lets imagine a animation
|
|
96
|
+
let anim = tween(...)
|
|
97
|
+
|
|
98
|
+
// print in console when that tween finishes
|
|
99
|
+
anim.onEnd(() => {
|
|
100
|
+
console.log('FINISHED')
|
|
101
|
+
})
|
|
102
|
+
```
|
|
103
|
+
|
|
104
|
+
### TweenController#stop()
|
|
105
|
+
|
|
106
|
+
Stops the animation.
|
|
107
|
+
|
|
108
|
+
Syntax: `.stop(complete?: boolean): void`
|
|
109
|
+
|
|
110
|
+
```js
|
|
111
|
+
// lets imagine a animation with 5 seconds of duration
|
|
112
|
+
let anim = tween(...)
|
|
113
|
+
|
|
114
|
+
// call `stop()` to interrumpt that animation
|
|
115
|
+
// and call all "onEnd" callbacks
|
|
116
|
+
anim.stop()
|
|
117
|
+
|
|
118
|
+
// or
|
|
119
|
+
// call `stop()` to interrumpt that animation
|
|
120
|
+
// and NOT call the "onEnd" callbacks
|
|
121
|
+
anim.stop(false)
|
|
122
|
+
```
|
|
123
|
+
|
|
124
|
+
### TweenController#reset()
|
|
125
|
+
|
|
126
|
+
Stops the animation and remove all `.onEnd()` registered callbacks.
|
|
127
|
+
|
|
128
|
+
### TweenController#progress
|
|
129
|
+
|
|
130
|
+
Returns the percentage of the animation's progress, a number between `0.0` and `1.0`. Where `0` represents 0% and `1` represents 100%.
|
|
131
|
+
|
|
132
|
+
### Easing Functions
|
|
133
|
+
|
|
134
|
+
We provide few easing functions:
|
|
135
|
+
|
|
136
|
+
- `LINEAR` (the default)
|
|
137
|
+
- `EASE_IN`
|
|
138
|
+
- `EASE_OUT`
|
|
139
|
+
- `EASE_IN_OUT`
|
|
140
|
+
- `ELASTIC_IN`
|
|
141
|
+
- `ELASTIC_OUT`
|
|
142
|
+
- `ELASTIC_IN_OUT`
|
|
143
|
+
- `BOUNCE_IN`
|
|
144
|
+
- `BOUNCE_OUT`
|
|
145
|
+
- `BOUNCE_IN_OUT`
|
|
146
|
+
- `BACK_IN`
|
|
147
|
+
- `BACK_OUT`
|
|
148
|
+
- `BACK_IN_OUT`
|
|
149
|
+
|
|
150
|
+
You should use the `tween()`'s fifth argument to choose a easing function.
|
|
151
|
+
|
|
152
|
+
```js
|
|
153
|
+
import litecanvas from "litecanvas"
|
|
154
|
+
import { tween, BOUNCE_OUT } from "@litecanvas/utils"
|
|
155
|
+
|
|
156
|
+
let object
|
|
157
|
+
|
|
158
|
+
litecanvas()
|
|
159
|
+
|
|
160
|
+
function init() {
|
|
161
|
+
pos = {
|
|
162
|
+
x: 100,
|
|
163
|
+
y: CENTERY,
|
|
164
|
+
}
|
|
165
|
+
|
|
166
|
+
tween(pos, "x", 250, 2, BOUNCE_OUT).start()
|
|
167
|
+
}
|
|
168
|
+
|
|
169
|
+
function draw() {
|
|
170
|
+
cls(0)
|
|
171
|
+
rectfill(pos.x, pos.y, 50, 50, 3)
|
|
172
|
+
}
|
|
173
|
+
```
|
|
174
|
+
|
|
175
|
+
[See all Easing Functions in action](https://litecanvas.js.org?c=eJylVEtvGjEQvvMrJpy8zXZD2vSCRCVKaYMaEakh6qGqKrM24Nax0a43sIry3zt%2BLSyQ9lCJRfP2fPONXRkhy2wp9ZxKknQ6uValAU5LoZYlDOCpA3AzmY6HX1OUxsO78c%2FJtBFv72d75ka9Gd7NJqMYGLQjZ7R8uL2fjmLZoBy6GsNw9CVGWrFt9upzC8SUPnDEcTv%2FxXOT%2FeZ1SQK6pBX3qVK5EVrtYh%2BprPhetOQxdlQVBVcGQ3vNxFCRwvCcqkdaEju2jWBm1Ye3vZ5tkVZGlzmVvA8LKkuOfeK4F%2FFUoYQhiRs3qwoaOrlEFX%2FaNRTYwFJKPLiIPqhKytQZt33oeakO0nMH%2F0pDC5v5yHNy2eslaOKKBcO3ycfZNbwGdKRwPZ58vp55LbGpTOfVA8LM5prVGV2vMXG0EpIRd0zjzgtODZ%2FxrZlqxkl3RtdgNOQrqpYczIrD2E0N4ojPuraNBIna4a%2FWDIsQZvwMxAKIR501aBMouKkK1Wkmkm0RiEOYbXfGJgGdZsO58v16rx9Rd9v1AkLKtl6MYw%2BO1lJ8b%2FH%2Bw3afuXMJTzonTs60GitGkNDB%2B0DaieYseZan%2FRJ1g6hG40vt13vt1%2F%2FZ%2Fj4LrKAbsmPg7G8U5LIkbp%2BkUNztOrlySC4uXB3HvF8%2FihtnNWzXJooiJ4G1NIJN8Z6k8C6Jfk9MABh9B8V9W5yF2YTUhZAy7g5WiHNN4c1REQrrQi8LXpYwpwV%2BpS2mwJYqMMuVwiz8%2Bavy6pjpWCGFq1M9Kvv86AXk4cnwTECcuOUYL4495BK%2F3ZN1QFmbJmMvIwtEtQLPzwN1Bw%2FVYHCwEpnkamlWSdjO43fNvh8v3cPTG40rpdck%2Bde2I5I%2FARL3JQ%3D%3D)
|
|
176
|
+
|
|
177
|
+
## Useful links
|
|
178
|
+
|
|
179
|
+
- https://en.wikipedia.org/wiki/Linear_interpolation
|
|
180
|
+
- https://gamedev.net/tutorials/programming/general-and-gameplay-programming/a-brief-introduction-to-lerp-r4954/
|
|
181
|
+
- https://easings.net/
|