toosoon-utils 1.4.0 → 2.0.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 +27 -23
- package/package.json +8 -4
- package/tsconfig.json +1 -3
- package/lib/classes/_pool.d.ts +0 -56
- package/lib/classes/_pool.js +0 -92
- package/lib/classes/color-scale.d.ts +0 -52
- package/lib/classes/color-scale.js +0 -160
- package/lib/classes/frame-rate.d.ts +0 -25
- package/lib/classes/frame-rate.js +0 -48
- package/lib/colors.d.ts +0 -155
- package/lib/colors.js +0 -367
- package/lib/constants.d.ts +0 -162
- package/lib/constants.js +0 -170
- package/lib/dom.d.ts +0 -25
- package/lib/dom.js +0 -47
- package/lib/files.d.ts +0 -14
- package/lib/files.js +0 -38
- package/lib/functions.d.ts +0 -22
- package/lib/functions.js +0 -53
- package/lib/geometry.d.ts +0 -89
- package/lib/geometry.js +0 -128
- package/lib/index.d.ts +0 -10
- package/lib/index.js +0 -39
- package/lib/maths.d.ts +0 -161
- package/lib/maths.js +0 -219
- package/lib/now.d.ts +0 -5
- package/lib/now.js +0 -28
- package/lib/prng.d.ts +0 -124
- package/lib/prng.js +0 -234
- package/lib/random.d.ts +0 -91
- package/lib/random.js +0 -162
- package/lib/strings.d.ts +0 -14
- package/lib/strings.js +0 -18
- package/lib/tsconfig.tsbuildinfo +0 -1
- package/lib/types.d.ts +0 -18
- package/lib/types.js +0 -1
- package/src/classes/_pool.ts +0 -92
- package/src/classes/color-scale.ts +0 -181
- package/src/classes/frame-rate.ts +0 -49
- package/src/colors.ts +0 -389
- package/src/constants.ts +0 -172
- package/src/dom.ts +0 -50
- package/src/files.ts +0 -42
- package/src/functions.ts +0 -56
- package/src/geometry.ts +0 -160
- package/src/maths.ts +0 -241
- package/src/prng.ts +0 -250
- package/src/random.ts +0 -162
- package/src/strings.ts +0 -19
- package/src/types.ts +0 -33
package/src/constants.ts
DELETED
|
@@ -1,172 +0,0 @@
|
|
|
1
|
-
// *********************
|
|
2
|
-
// Maths
|
|
3
|
-
// *********************
|
|
4
|
-
export const EPSILON = 1e-10;
|
|
5
|
-
export const PI = Math.PI;
|
|
6
|
-
export const TWO_PI = Math.PI * 2;
|
|
7
|
-
export const HALF_PI = Math.PI / 2;
|
|
8
|
-
export const QUARTER_PI = Math.PI / 4;
|
|
9
|
-
|
|
10
|
-
// *********************
|
|
11
|
-
// Colors
|
|
12
|
-
// *********************
|
|
13
|
-
|
|
14
|
-
// X11 colors
|
|
15
|
-
// -> https://www.w3.org/TR/css-color-3/#svg-color
|
|
16
|
-
export const W3CX11 = {
|
|
17
|
-
aliceblue: 0xf0f8ff,
|
|
18
|
-
antiquewhite: 0xfaebd7,
|
|
19
|
-
aqua: 0x00ffff,
|
|
20
|
-
aquamarine: 0x7fffd4,
|
|
21
|
-
azure: 0xf0ffff,
|
|
22
|
-
beige: 0xf5f5dc,
|
|
23
|
-
bisque: 0xffe4c4,
|
|
24
|
-
black: 0x000000,
|
|
25
|
-
blanchedalmond: 0xffebcd,
|
|
26
|
-
blue: 0x0000ff,
|
|
27
|
-
blueviolet: 0x8a2be2,
|
|
28
|
-
brown: 0xa52a2a,
|
|
29
|
-
burlywood: 0xdeb887,
|
|
30
|
-
cadetblue: 0x5f9ea0,
|
|
31
|
-
chartreuse: 0x7fff00,
|
|
32
|
-
chocolate: 0xd2691e,
|
|
33
|
-
coral: 0xff7f50,
|
|
34
|
-
cornflower: 0x6495ed,
|
|
35
|
-
cornflowerblue: 0x6495ed,
|
|
36
|
-
cornsilk: 0xfff8dc,
|
|
37
|
-
crimson: 0xdc143c,
|
|
38
|
-
cyan: 0x00ffff,
|
|
39
|
-
darkblue: 0x00008b,
|
|
40
|
-
darkcyan: 0x008b8b,
|
|
41
|
-
darkgoldenrod: 0xb8860b,
|
|
42
|
-
darkgray: 0xa9a9a9,
|
|
43
|
-
darkgreen: 0x006400,
|
|
44
|
-
darkgrey: 0xa9a9a9,
|
|
45
|
-
darkkhaki: 0xbdb76b,
|
|
46
|
-
darkmagenta: 0x8b008b,
|
|
47
|
-
darkolivegreen: 0x556b2f,
|
|
48
|
-
darkorange: 0xff8c00,
|
|
49
|
-
darkorchid: 0x9932cc,
|
|
50
|
-
darkred: 0x8b0000,
|
|
51
|
-
darksalmon: 0xe9967a,
|
|
52
|
-
darkseagreen: 0x8fbc8f,
|
|
53
|
-
darkslateblue: 0x483d8b,
|
|
54
|
-
darkslategray: 0x2f4f4f,
|
|
55
|
-
darkslategrey: 0x2f4f4f,
|
|
56
|
-
darkturquoise: 0x00ced1,
|
|
57
|
-
darkviolet: 0x9400d3,
|
|
58
|
-
deeppink: 0xff1493,
|
|
59
|
-
deepskyblue: 0x00bfff,
|
|
60
|
-
dimgray: 0x696969,
|
|
61
|
-
dimgrey: 0x696969,
|
|
62
|
-
dodgerblue: 0x1e90ff,
|
|
63
|
-
firebrick: 0xb22222,
|
|
64
|
-
floralwhite: 0xfffaf0,
|
|
65
|
-
forestgreen: 0x228b22,
|
|
66
|
-
fuchsia: 0xff00ff,
|
|
67
|
-
gainsboro: 0xdcdcdc,
|
|
68
|
-
ghostwhite: 0xf8f8ff,
|
|
69
|
-
gold: 0xffd700,
|
|
70
|
-
goldenrod: 0xdaa520,
|
|
71
|
-
gray: 0x808080,
|
|
72
|
-
green: 0x008000,
|
|
73
|
-
greenyellow: 0xadff2f,
|
|
74
|
-
grey: 0x808080,
|
|
75
|
-
honeydew: 0xf0fff0,
|
|
76
|
-
hotpink: 0xff69b4,
|
|
77
|
-
indianred: 0xcd5c5c,
|
|
78
|
-
indigo: 0x4b0082,
|
|
79
|
-
ivory: 0xfffff0,
|
|
80
|
-
khaki: 0xf0e68c,
|
|
81
|
-
laserlemon: 0xffff54,
|
|
82
|
-
lavender: 0xe6e6fa,
|
|
83
|
-
lavenderblush: 0xfff0f5,
|
|
84
|
-
lawngreen: 0x7cfc00,
|
|
85
|
-
lemonchiffon: 0xfffacd,
|
|
86
|
-
lightblue: 0xadd8e6,
|
|
87
|
-
lightcoral: 0xf08080,
|
|
88
|
-
lightcyan: 0xe0ffff,
|
|
89
|
-
lightgoldenrod: 0xfafad2,
|
|
90
|
-
lightgoldenrodyellow: 0xfafad2,
|
|
91
|
-
lightgray: 0xd3d3d3,
|
|
92
|
-
lightgreen: 0x90ee90,
|
|
93
|
-
lightgrey: 0xd3d3d3,
|
|
94
|
-
lightpink: 0xffb6c1,
|
|
95
|
-
lightsalmon: 0xffa07a,
|
|
96
|
-
lightseagreen: 0x20b2aa,
|
|
97
|
-
lightskyblue: 0x87cefa,
|
|
98
|
-
lightslategray: 0x778899,
|
|
99
|
-
lightslategrey: 0x778899,
|
|
100
|
-
lightsteelblue: 0xb0c4de,
|
|
101
|
-
lightyellow: 0xffffe0,
|
|
102
|
-
lime: 0x00ff00,
|
|
103
|
-
limegreen: 0x32cd32,
|
|
104
|
-
linen: 0xfaf0e6,
|
|
105
|
-
magenta: 0xff00ff,
|
|
106
|
-
maroon: 0x800000,
|
|
107
|
-
maroon2: 0x7f0000,
|
|
108
|
-
maroon3: 0xb03060,
|
|
109
|
-
mediumaquamarine: 0x66cdaa,
|
|
110
|
-
mediumblue: 0x0000cd,
|
|
111
|
-
mediumorchid: 0xba55d3,
|
|
112
|
-
mediumpurple: 0x9370db,
|
|
113
|
-
mediumseagreen: 0x3cb371,
|
|
114
|
-
mediumslateblue: 0x7b68ee,
|
|
115
|
-
mediumspringgreen: 0x00fa9a,
|
|
116
|
-
mediumturquoise: 0x48d1cc,
|
|
117
|
-
mediumvioletred: 0xc71585,
|
|
118
|
-
midnightblue: 0x191970,
|
|
119
|
-
mintcream: 0xf5fffa,
|
|
120
|
-
mistyrose: 0xffe4e1,
|
|
121
|
-
moccasin: 0xffe4b5,
|
|
122
|
-
navajowhite: 0xffdead,
|
|
123
|
-
navy: 0x000080,
|
|
124
|
-
oldlace: 0xfdf5e6,
|
|
125
|
-
olive: 0x808000,
|
|
126
|
-
olivedrab: 0x6b8e23,
|
|
127
|
-
orange: 0xffa500,
|
|
128
|
-
orangered: 0xff4500,
|
|
129
|
-
orchid: 0xda70d6,
|
|
130
|
-
palegoldenrod: 0xeee8aa,
|
|
131
|
-
palegreen: 0x98fb98,
|
|
132
|
-
paleturquoise: 0xafeeee,
|
|
133
|
-
palevioletred: 0xdb7093,
|
|
134
|
-
papayawhip: 0xffefd5,
|
|
135
|
-
peachpuff: 0xffdab9,
|
|
136
|
-
peru: 0xcd853f,
|
|
137
|
-
pink: 0xffc0cb,
|
|
138
|
-
plum: 0xdda0dd,
|
|
139
|
-
powderblue: 0xb0e0e6,
|
|
140
|
-
purple: 0x800080,
|
|
141
|
-
purple2: 0x7f007f,
|
|
142
|
-
purple3: 0xa020f0,
|
|
143
|
-
rebeccapurple: 0x663399,
|
|
144
|
-
red: 0xff0000,
|
|
145
|
-
rosybrown: 0xbc8f8f,
|
|
146
|
-
royalblue: 0x4169e1,
|
|
147
|
-
saddlebrown: 0x8b4513,
|
|
148
|
-
salmon: 0xfa8072,
|
|
149
|
-
sandybrown: 0xf4a460,
|
|
150
|
-
seagreen: 0x2e8b57,
|
|
151
|
-
seashell: 0xfff5ee,
|
|
152
|
-
sienna: 0xa0522d,
|
|
153
|
-
silver: 0xc0c0c0,
|
|
154
|
-
skyblue: 0x87ceeb,
|
|
155
|
-
slateblue: 0x6a5acd,
|
|
156
|
-
slategray: 0x708090,
|
|
157
|
-
slategrey: 0x708090,
|
|
158
|
-
snow: 0xfffafa,
|
|
159
|
-
springgreen: 0x00ff7f,
|
|
160
|
-
steelblue: 0x4682b4,
|
|
161
|
-
tan: 0xd2b48c,
|
|
162
|
-
teal: 0x008080,
|
|
163
|
-
thistle: 0xd8bfd8,
|
|
164
|
-
tomato: 0xff6347,
|
|
165
|
-
turquoise: 0x40e0d0,
|
|
166
|
-
violet: 0xee82ee,
|
|
167
|
-
wheat: 0xf5deb3,
|
|
168
|
-
white: 0xffffff,
|
|
169
|
-
whitesmoke: 0xf5f5f5,
|
|
170
|
-
yellow: 0xffff00,
|
|
171
|
-
yellowgreen: 0x9acd32
|
|
172
|
-
};
|
package/src/dom.ts
DELETED
|
@@ -1,50 +0,0 @@
|
|
|
1
|
-
const DOCUMENT_NODE_TYPE = 9;
|
|
2
|
-
|
|
3
|
-
/**
|
|
4
|
-
* Find the closest parent that matches a selector
|
|
5
|
-
*
|
|
6
|
-
* @param {Element} element Target element
|
|
7
|
-
* @param {(Element|string)} selector Selector or parent to match
|
|
8
|
-
* @returns {Element|null}
|
|
9
|
-
*/
|
|
10
|
-
export function closest(element: Element, selector: Element | string): Element | null {
|
|
11
|
-
let current: Element | null = element;
|
|
12
|
-
while (current && current.nodeType !== DOCUMENT_NODE_TYPE) {
|
|
13
|
-
if ((typeof selector === 'string' && current.matches(selector)) || current === selector) {
|
|
14
|
-
return current;
|
|
15
|
-
}
|
|
16
|
-
current = element.parentNode as Element | null;
|
|
17
|
-
}
|
|
18
|
-
return current;
|
|
19
|
-
}
|
|
20
|
-
|
|
21
|
-
/**
|
|
22
|
-
* Create a canvas and 2d context
|
|
23
|
-
*
|
|
24
|
-
* @param {Number} width Width of the canvas
|
|
25
|
-
* @param {Number} height Height of the canvas
|
|
26
|
-
* @returns {{ canvas: HTMLCanvasElement, ctx: CanvasRenderingContext2D }}
|
|
27
|
-
*/
|
|
28
|
-
export function createCanvas(
|
|
29
|
-
width: number,
|
|
30
|
-
height: number
|
|
31
|
-
): { canvas: HTMLCanvasElement; ctx: CanvasRenderingContext2D } {
|
|
32
|
-
const canvas = document.createElement('canvas');
|
|
33
|
-
canvas.width = width;
|
|
34
|
-
canvas.height = height;
|
|
35
|
-
const ctx = canvas.getContext('2d') ?? new CanvasRenderingContext2D();
|
|
36
|
-
return { canvas, ctx };
|
|
37
|
-
}
|
|
38
|
-
|
|
39
|
-
/**
|
|
40
|
-
* Inject CSS styles in `document.head`
|
|
41
|
-
*
|
|
42
|
-
* @param {string} styles CSS styles to inject
|
|
43
|
-
*/
|
|
44
|
-
export function injectStyles(styles: string): void {
|
|
45
|
-
const $style = document.createElement('style');
|
|
46
|
-
$style.innerHTML = styles;
|
|
47
|
-
const $before = document.querySelector('head link[rel=stylesheet], head style');
|
|
48
|
-
if ($before) document.head.insertBefore($style, $before);
|
|
49
|
-
else document.head.appendChild($style);
|
|
50
|
-
}
|
package/src/files.ts
DELETED
|
@@ -1,42 +0,0 @@
|
|
|
1
|
-
type InputChangeEvent = Event & { target: (EventTarget & { files?: FileList }) | null };
|
|
2
|
-
|
|
3
|
-
/**
|
|
4
|
-
* Download a Blob object into user files
|
|
5
|
-
*
|
|
6
|
-
* @param {Blob} blob Blob object to download
|
|
7
|
-
* @param {string} filename Downloaded file name
|
|
8
|
-
*/
|
|
9
|
-
export function download(blob: Blob, filename: string): void {
|
|
10
|
-
const link = document.createElement('a');
|
|
11
|
-
link.setAttribute('href', URL.createObjectURL(blob));
|
|
12
|
-
link.setAttribute('download', filename);
|
|
13
|
-
|
|
14
|
-
document.body.appendChild(link);
|
|
15
|
-
link.click();
|
|
16
|
-
document.body.removeChild(link);
|
|
17
|
-
}
|
|
18
|
-
|
|
19
|
-
/**
|
|
20
|
-
* Upload a file from user files
|
|
21
|
-
*
|
|
22
|
-
* @param {Function} onLoad Callback called once the file is loaded
|
|
23
|
-
* @param {string} [accept=''] MIME type the file input should accept
|
|
24
|
-
*/
|
|
25
|
-
export function upload(onLoad: (dataUrl: string) => void, accept: string = ''): void {
|
|
26
|
-
const input = document.createElement('input');
|
|
27
|
-
input.setAttribute('type', 'file');
|
|
28
|
-
input.setAttribute('accept', accept);
|
|
29
|
-
|
|
30
|
-
input.addEventListener('change', (event: InputChangeEvent) => {
|
|
31
|
-
const file = event.target?.files?.[0];
|
|
32
|
-
if (file) {
|
|
33
|
-
const fileReader = new FileReader();
|
|
34
|
-
fileReader.addEventListener('load', () => onLoad(URL.createObjectURL(file)));
|
|
35
|
-
fileReader.readAsDataURL(file);
|
|
36
|
-
}
|
|
37
|
-
});
|
|
38
|
-
|
|
39
|
-
document.body.appendChild(input);
|
|
40
|
-
input.click();
|
|
41
|
-
document.body.removeChild(input);
|
|
42
|
-
}
|
package/src/functions.ts
DELETED
|
@@ -1,56 +0,0 @@
|
|
|
1
|
-
import { Deferred } from './types';
|
|
2
|
-
|
|
3
|
-
/**
|
|
4
|
-
* No-op function
|
|
5
|
-
*/
|
|
6
|
-
export const noop: () => void = () => {};
|
|
7
|
-
|
|
8
|
-
/**
|
|
9
|
-
* Promise wrapped setTimeout
|
|
10
|
-
*
|
|
11
|
-
* @param {number} [timeout=0] Time to wait (in milliseconds)
|
|
12
|
-
* @returns {Promise}
|
|
13
|
-
*/
|
|
14
|
-
export function wait(timeout: number = 0): Promise<void> {
|
|
15
|
-
return new Promise((resolve) => setTimeout(resolve, timeout));
|
|
16
|
-
}
|
|
17
|
-
|
|
18
|
-
/**
|
|
19
|
-
* Deferred promise implementation
|
|
20
|
-
*
|
|
21
|
-
* @returns {Deferred}
|
|
22
|
-
*/
|
|
23
|
-
export function defer<T = void>(): Deferred<T> {
|
|
24
|
-
let resolve!: (value: T | PromiseLike<T>) => void;
|
|
25
|
-
let reject!: (reason?: unknown) => void;
|
|
26
|
-
const promise = new Promise<T>((_resolve, _reject) => {
|
|
27
|
-
resolve = _resolve;
|
|
28
|
-
reject = _reject;
|
|
29
|
-
});
|
|
30
|
-
return { promise, resolve, reject };
|
|
31
|
-
}
|
|
32
|
-
|
|
33
|
-
/**
|
|
34
|
-
* Polyfill for `now()` functions
|
|
35
|
-
*/
|
|
36
|
-
export let now: () => number;
|
|
37
|
-
|
|
38
|
-
// In node.js, use `process.hrtime`
|
|
39
|
-
if (typeof process !== 'undefined' && process.hrtime) {
|
|
40
|
-
now = function () {
|
|
41
|
-
// Convert [seconds, nanoseconds] to milliseconds
|
|
42
|
-
const time = process.hrtime();
|
|
43
|
-
return time[0] * 1000 + time[1] / 1000000;
|
|
44
|
-
};
|
|
45
|
-
}
|
|
46
|
-
// In a browser use `performance` or `Date`
|
|
47
|
-
else if (typeof performance !== 'undefined') {
|
|
48
|
-
// This must be bound, because directly assigning this function leads to an invocation exception in Chrome
|
|
49
|
-
now = performance.now.bind(performance);
|
|
50
|
-
} else if (typeof Date.now !== 'undefined') {
|
|
51
|
-
now = Date.now;
|
|
52
|
-
} else {
|
|
53
|
-
now = function () {
|
|
54
|
-
return new Date().getTime();
|
|
55
|
-
};
|
|
56
|
-
}
|
package/src/geometry.ts
DELETED
|
@@ -1,160 +0,0 @@
|
|
|
1
|
-
import { PI } from './constants';
|
|
2
|
-
import { Vector3 } from './types';
|
|
3
|
-
|
|
4
|
-
/**
|
|
5
|
-
* Convert a radians value into degrees
|
|
6
|
-
*
|
|
7
|
-
* @param {number} radians Angle in radians
|
|
8
|
-
* @returns {number} Angle in degrees
|
|
9
|
-
*/
|
|
10
|
-
export function toDegrees(radians: number): number {
|
|
11
|
-
return (radians * 180) / PI;
|
|
12
|
-
}
|
|
13
|
-
|
|
14
|
-
/**
|
|
15
|
-
* Convert a degrees value into radians
|
|
16
|
-
*
|
|
17
|
-
* @param {number} degrees Angle in degrees
|
|
18
|
-
* @returns {number} Angle in radians
|
|
19
|
-
*/
|
|
20
|
-
export function toRadians(degrees: number): number {
|
|
21
|
-
return (degrees * PI) / 180;
|
|
22
|
-
}
|
|
23
|
-
|
|
24
|
-
/**
|
|
25
|
-
* Calculate the angle from a point to another
|
|
26
|
-
*
|
|
27
|
-
* @param {number} x1 X value of the first point
|
|
28
|
-
* @param {number} y1 Y value of the first point
|
|
29
|
-
* @param {number} x2 X value of the second point
|
|
30
|
-
* @param {number} y2 Y value of the second point
|
|
31
|
-
* @returns {number} Angle
|
|
32
|
-
*/
|
|
33
|
-
export function angle(x1: number, y1: number, x2: number, y2: number): number {
|
|
34
|
-
return Math.atan2(y2 - y1, x2 - x1);
|
|
35
|
-
}
|
|
36
|
-
|
|
37
|
-
/**
|
|
38
|
-
* Find the closest angle between to angles
|
|
39
|
-
*
|
|
40
|
-
* @param {number} source Source angle in radians
|
|
41
|
-
* @param {number} target Target angle in radians
|
|
42
|
-
* @returns {number} Closest angle
|
|
43
|
-
*/
|
|
44
|
-
export function closestAngle(source: number, target: number): number {
|
|
45
|
-
const delta = target - source;
|
|
46
|
-
return delta > PI ? target - 2 * PI : target < -PI ? delta + 2 * PI : target;
|
|
47
|
-
}
|
|
48
|
-
|
|
49
|
-
/**
|
|
50
|
-
* Calculate the distance between two points
|
|
51
|
-
*
|
|
52
|
-
* @param {number} x1 X coord of the first point
|
|
53
|
-
* @param {number} y1 Y coord of the first point
|
|
54
|
-
* @param {number} x2 X coord of the second point
|
|
55
|
-
* @param {number} y2 Y coord of the second point
|
|
56
|
-
* @returns {number} Computed distance
|
|
57
|
-
*/
|
|
58
|
-
export function distance(x1: number, y1: number, x2: number, y2: number): number {
|
|
59
|
-
const dx = x1 - x2;
|
|
60
|
-
const dy = y1 - y2;
|
|
61
|
-
return Math.sqrt(dx * dx + dy * dy);
|
|
62
|
-
}
|
|
63
|
-
|
|
64
|
-
/**
|
|
65
|
-
* Calculate the length of the diagonal of a rectangle
|
|
66
|
-
*
|
|
67
|
-
* @param {number} width Width of the rectangle
|
|
68
|
-
* @param {number} height Height of the rectangle
|
|
69
|
-
* @returns {number} Diagonal length
|
|
70
|
-
*/
|
|
71
|
-
export function diagonal(width: number, height: number): number {
|
|
72
|
-
return Math.sqrt(width * width + height * height);
|
|
73
|
-
}
|
|
74
|
-
|
|
75
|
-
/**
|
|
76
|
-
* Convert radians to a 3D point on the surface of a unit sphere
|
|
77
|
-
*
|
|
78
|
-
* @param {number} radius Radius of the sphere
|
|
79
|
-
* @param {number} phi Polar angle from the y (up) axis : [0, PI]
|
|
80
|
-
* @param {number} theta Equator angle around the y (up) axis : [0, 2*PI]
|
|
81
|
-
* @param {Vector3} target Target vector
|
|
82
|
-
* @returns {Vector3}
|
|
83
|
-
*/
|
|
84
|
-
export function radToSphere(
|
|
85
|
-
radius: number,
|
|
86
|
-
phi: number,
|
|
87
|
-
theta: number,
|
|
88
|
-
target: Vector3 = { x: 0, y: 0, z: 0 }
|
|
89
|
-
): Vector3 {
|
|
90
|
-
target.x = radius * Math.sin(phi) * Math.sin(theta);
|
|
91
|
-
target.y = radius * Math.cos(phi);
|
|
92
|
-
target.z = radius * Math.sin(phi) * Math.cos(theta);
|
|
93
|
-
return target;
|
|
94
|
-
}
|
|
95
|
-
|
|
96
|
-
// *********************
|
|
97
|
-
// Fit
|
|
98
|
-
// *********************
|
|
99
|
-
interface FitInput {
|
|
100
|
-
width: number;
|
|
101
|
-
height: number;
|
|
102
|
-
}
|
|
103
|
-
|
|
104
|
-
interface FitOutput {
|
|
105
|
-
left: number;
|
|
106
|
-
top: number;
|
|
107
|
-
width: number;
|
|
108
|
-
height: number;
|
|
109
|
-
scale: number;
|
|
110
|
-
}
|
|
111
|
-
|
|
112
|
-
/**
|
|
113
|
-
* Make a target fit a container
|
|
114
|
-
*
|
|
115
|
-
* @param {FitInput} target Dimension of the target
|
|
116
|
-
* @param {FitInput} container Dimension of the container
|
|
117
|
-
* @param {string} mode Can be 'contain' | 'cover'
|
|
118
|
-
* @returns {FitOutput}
|
|
119
|
-
*/
|
|
120
|
-
function fit(target: FitInput, container: FitInput, mode: 'contain' | 'cover'): FitOutput {
|
|
121
|
-
const ratioWidth = container.width / target.width;
|
|
122
|
-
const ratioHeight = container.height / target.height;
|
|
123
|
-
|
|
124
|
-
let scale: number;
|
|
125
|
-
if (mode === 'contain') {
|
|
126
|
-
scale = ratioWidth < ratioHeight ? ratioWidth : ratioHeight;
|
|
127
|
-
} else {
|
|
128
|
-
scale = ratioWidth > ratioHeight ? ratioWidth : ratioHeight;
|
|
129
|
-
}
|
|
130
|
-
|
|
131
|
-
return {
|
|
132
|
-
left: (container.width - target.width * scale) >> 1,
|
|
133
|
-
top: (container.height - target.height * scale) >> 1,
|
|
134
|
-
width: target.width * scale,
|
|
135
|
-
height: target.height * scale,
|
|
136
|
-
scale
|
|
137
|
-
};
|
|
138
|
-
}
|
|
139
|
-
|
|
140
|
-
/**
|
|
141
|
-
* Make a target fit a container (cover mode)
|
|
142
|
-
*
|
|
143
|
-
* @param {FitInput} target Dimension of the target
|
|
144
|
-
* @param {FitInput} container Dimension of the container
|
|
145
|
-
* @returns {FitOutput}
|
|
146
|
-
*/
|
|
147
|
-
export function cover(target: FitInput, container: FitInput): FitOutput {
|
|
148
|
-
return fit(target, container, 'cover');
|
|
149
|
-
}
|
|
150
|
-
|
|
151
|
-
/**
|
|
152
|
-
* Make a target fit a container (contain mode)
|
|
153
|
-
*
|
|
154
|
-
* @param {FitInput} target Dimension of the target
|
|
155
|
-
* @param {FitInput} container Dimension of the container
|
|
156
|
-
* @returns {FitOutput}
|
|
157
|
-
*/
|
|
158
|
-
export function contain(target: FitInput, container: FitInput): FitOutput {
|
|
159
|
-
return fit(target, container, 'contain');
|
|
160
|
-
}
|