@alepot55/chessboardjs 2.2.0 → 2.2.2
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/.eslintrc.json +227 -0
- package/README.md +127 -403
- package/assets/themes/alepot/theme.json +42 -0
- package/assets/themes/default/theme.json +42 -0
- package/chessboard.bundle.js +782 -119
- package/config/jest.config.js +15 -0
- package/config/rollup.config.js +36 -0
- package/dist/chessboard.cjs.js +10690 -0
- package/dist/chessboard.css +228 -0
- package/dist/chessboard.esm.js +10621 -0
- package/dist/chessboard.iife.js +10696 -0
- package/dist/chessboard.umd.js +10696 -0
- package/jest.config.js +2 -7
- package/package.json +18 -3
- package/rollup.config.js +2 -11
- package/{chessboard.move.js → src/components/Move.js} +3 -3
- package/src/components/Piece.js +288 -0
- package/{chessboard.square.js → src/components/Square.js} +60 -7
- package/src/constants/index.js +15 -0
- package/src/constants/positions.js +62 -0
- package/src/core/Chessboard.js +1939 -0
- package/src/core/ChessboardConfig.js +458 -0
- package/src/core/ChessboardFactory.js +385 -0
- package/src/core/index.js +141 -0
- package/src/errors/ChessboardError.js +133 -0
- package/src/errors/index.js +15 -0
- package/src/errors/messages.js +189 -0
- package/src/index.js +103 -0
- package/src/services/AnimationService.js +180 -0
- package/src/services/BoardService.js +156 -0
- package/src/services/CoordinateService.js +355 -0
- package/src/services/EventService.js +955 -0
- package/src/services/MoveService.js +629 -0
- package/src/services/PieceService.js +312 -0
- package/src/services/PositionService.js +237 -0
- package/src/services/ValidationService.js +673 -0
- package/src/services/index.js +14 -0
- package/src/styles/animations.css +46 -0
- package/{chessboard.css → src/styles/board.css} +8 -4
- package/src/styles/index.css +4 -0
- package/src/styles/pieces.css +70 -0
- package/src/utils/animations.js +37 -0
- package/{chess.js → src/utils/chess.js} +16 -16
- package/src/utils/coordinates.js +62 -0
- package/src/utils/cross-browser.js +150 -0
- package/src/utils/logger.js +422 -0
- package/src/utils/performance.js +311 -0
- package/src/utils/validation.js +458 -0
- package/tests/unit/chessboard-config-animations.test.js +106 -0
- package/tests/unit/chessboard-robust.test.js +163 -0
- package/tests/unit/chessboard.test.js +183 -0
- package/chessboard.config.js +0 -147
- package/chessboard.js +0 -981
- package/chessboard.piece.js +0 -115
- package/test/chessboard.test.js +0 -128
- /package/{alepot_theme → assets/themes/alepot}/bb.svg +0 -0
- /package/{alepot_theme → assets/themes/alepot}/bw.svg +0 -0
- /package/{alepot_theme → assets/themes/alepot}/kb.svg +0 -0
- /package/{alepot_theme → assets/themes/alepot}/kw.svg +0 -0
- /package/{alepot_theme → assets/themes/alepot}/nb.svg +0 -0
- /package/{alepot_theme → assets/themes/alepot}/nw.svg +0 -0
- /package/{alepot_theme → assets/themes/alepot}/pb.svg +0 -0
- /package/{alepot_theme → assets/themes/alepot}/pw.svg +0 -0
- /package/{alepot_theme → assets/themes/alepot}/qb.svg +0 -0
- /package/{alepot_theme → assets/themes/alepot}/qw.svg +0 -0
- /package/{alepot_theme → assets/themes/alepot}/rb.svg +0 -0
- /package/{alepot_theme → assets/themes/alepot}/rw.svg +0 -0
- /package/{default_pieces → assets/themes/default}/bb.svg +0 -0
- /package/{default_pieces → assets/themes/default}/bw.svg +0 -0
- /package/{default_pieces → assets/themes/default}/kb.svg +0 -0
- /package/{default_pieces → assets/themes/default}/kw.svg +0 -0
- /package/{default_pieces → assets/themes/default}/nb.svg +0 -0
- /package/{default_pieces → assets/themes/default}/nw.svg +0 -0
- /package/{default_pieces → assets/themes/default}/pb.svg +0 -0
- /package/{default_pieces → assets/themes/default}/pw.svg +0 -0
- /package/{default_pieces → assets/themes/default}/qb.svg +0 -0
- /package/{default_pieces → assets/themes/default}/qw.svg +0 -0
- /package/{default_pieces → assets/themes/default}/rb.svg +0 -0
- /package/{default_pieces → assets/themes/default}/rw.svg +0 -0
- /package/{.babelrc → config/.babelrc} +0 -0
|
@@ -0,0 +1,311 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Performance utilities for smooth interactions and monitoring
|
|
3
|
+
* @module utils/performance
|
|
4
|
+
* @since 2.0.0
|
|
5
|
+
*/
|
|
6
|
+
|
|
7
|
+
/**
|
|
8
|
+
* Performance monitoring class for measuring and tracking performance metrics
|
|
9
|
+
* @class
|
|
10
|
+
*/
|
|
11
|
+
export class PerformanceMonitor {
|
|
12
|
+
/**
|
|
13
|
+
* Creates a new PerformanceMonitor instance
|
|
14
|
+
*/
|
|
15
|
+
constructor() {
|
|
16
|
+
this.metrics = new Map();
|
|
17
|
+
this.observers = new Map();
|
|
18
|
+
this.isEnabled = typeof performance !== 'undefined' && performance.mark;
|
|
19
|
+
|
|
20
|
+
if (this.isEnabled) {
|
|
21
|
+
this._setupObservers();
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
/**
|
|
26
|
+
* Sets up performance observers for automatic metrics collection
|
|
27
|
+
* @private
|
|
28
|
+
*/
|
|
29
|
+
_setupObservers() {
|
|
30
|
+
try {
|
|
31
|
+
// Performance Observer for paint metrics
|
|
32
|
+
if (typeof PerformanceObserver !== 'undefined') {
|
|
33
|
+
const paintObserver = new PerformanceObserver((list) => {
|
|
34
|
+
for (const entry of list.getEntries()) {
|
|
35
|
+
this.recordMetric(entry.name, entry.startTime);
|
|
36
|
+
}
|
|
37
|
+
});
|
|
38
|
+
|
|
39
|
+
paintObserver.observe({ entryTypes: ['paint'] });
|
|
40
|
+
this.observers.set('paint', paintObserver);
|
|
41
|
+
}
|
|
42
|
+
} catch (error) {
|
|
43
|
+
console.warn('Performance observers not available:', error.message);
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
/**
|
|
48
|
+
* Starts measuring performance for a given operation
|
|
49
|
+
* @param {string} name - Name of the operation
|
|
50
|
+
*/
|
|
51
|
+
startMeasure(name) {
|
|
52
|
+
if (!this.isEnabled) return;
|
|
53
|
+
|
|
54
|
+
try {
|
|
55
|
+
performance.mark(`${name}-start`);
|
|
56
|
+
} catch (error) {
|
|
57
|
+
console.warn(`Failed to start performance measure for ${name}:`, error.message);
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
/**
|
|
62
|
+
* Ends measuring performance for a given operation
|
|
63
|
+
* @param {string} name - Name of the operation
|
|
64
|
+
* @returns {number} Duration in milliseconds
|
|
65
|
+
*/
|
|
66
|
+
endMeasure(name) {
|
|
67
|
+
if (!this.isEnabled) return 0;
|
|
68
|
+
|
|
69
|
+
try {
|
|
70
|
+
performance.mark(`${name}-end`);
|
|
71
|
+
const measure = performance.measure(name, `${name}-start`, `${name}-end`);
|
|
72
|
+
|
|
73
|
+
this.recordMetric(name, measure.duration);
|
|
74
|
+
|
|
75
|
+
// Clean up marks
|
|
76
|
+
performance.clearMarks(`${name}-start`);
|
|
77
|
+
performance.clearMarks(`${name}-end`);
|
|
78
|
+
performance.clearMeasures(name);
|
|
79
|
+
|
|
80
|
+
return measure.duration;
|
|
81
|
+
} catch (error) {
|
|
82
|
+
console.warn(`Failed to end performance measure for ${name}:`, error.message);
|
|
83
|
+
return 0;
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
/**
|
|
88
|
+
* Records a metric value
|
|
89
|
+
* @param {string} name - Metric name
|
|
90
|
+
* @param {number} value - Metric value
|
|
91
|
+
*/
|
|
92
|
+
recordMetric(name, value) {
|
|
93
|
+
if (!this.metrics.has(name)) {
|
|
94
|
+
this.metrics.set(name, {
|
|
95
|
+
count: 0,
|
|
96
|
+
total: 0,
|
|
97
|
+
min: Infinity,
|
|
98
|
+
max: -Infinity,
|
|
99
|
+
values: []
|
|
100
|
+
});
|
|
101
|
+
}
|
|
102
|
+
|
|
103
|
+
const metric = this.metrics.get(name);
|
|
104
|
+
metric.count++;
|
|
105
|
+
metric.total += value;
|
|
106
|
+
metric.min = Math.min(metric.min, value);
|
|
107
|
+
metric.max = Math.max(metric.max, value);
|
|
108
|
+
metric.values.push(value);
|
|
109
|
+
|
|
110
|
+
// Keep only last 100 values to prevent memory leaks
|
|
111
|
+
if (metric.values.length > 100) {
|
|
112
|
+
metric.values.shift();
|
|
113
|
+
}
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
/**
|
|
117
|
+
* Gets metrics summary
|
|
118
|
+
* @returns {Object} Metrics summary
|
|
119
|
+
*/
|
|
120
|
+
getMetrics() {
|
|
121
|
+
const summary = {};
|
|
122
|
+
|
|
123
|
+
for (const [name, metric] of this.metrics) {
|
|
124
|
+
summary[name] = {
|
|
125
|
+
count: metric.count,
|
|
126
|
+
average: metric.total / metric.count,
|
|
127
|
+
min: metric.min,
|
|
128
|
+
max: metric.max,
|
|
129
|
+
total: metric.total,
|
|
130
|
+
p95: this._calculatePercentile(metric.values, 95),
|
|
131
|
+
p99: this._calculatePercentile(metric.values, 99)
|
|
132
|
+
};
|
|
133
|
+
}
|
|
134
|
+
|
|
135
|
+
return summary;
|
|
136
|
+
}
|
|
137
|
+
|
|
138
|
+
/**
|
|
139
|
+
* Calculates percentile for a set of values
|
|
140
|
+
* @private
|
|
141
|
+
* @param {Array<number>} values - Array of values
|
|
142
|
+
* @param {number} percentile - Percentile to calculate (0-100)
|
|
143
|
+
* @returns {number} Percentile value
|
|
144
|
+
*/
|
|
145
|
+
_calculatePercentile(values, percentile) {
|
|
146
|
+
if (values.length === 0) return 0;
|
|
147
|
+
|
|
148
|
+
const sorted = [...values].sort((a, b) => a - b);
|
|
149
|
+
const index = Math.ceil((percentile / 100) * sorted.length) - 1;
|
|
150
|
+
return sorted[Math.max(0, index)];
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
/**
|
|
154
|
+
* Clears all metrics
|
|
155
|
+
*/
|
|
156
|
+
clearMetrics() {
|
|
157
|
+
this.metrics.clear();
|
|
158
|
+
}
|
|
159
|
+
|
|
160
|
+
/**
|
|
161
|
+
* Destroys the performance monitor and cleans up resources
|
|
162
|
+
*/
|
|
163
|
+
destroy() {
|
|
164
|
+
// Disconnect observers
|
|
165
|
+
for (const observer of this.observers.values()) {
|
|
166
|
+
if (observer && typeof observer.disconnect === 'function') {
|
|
167
|
+
observer.disconnect();
|
|
168
|
+
}
|
|
169
|
+
}
|
|
170
|
+
|
|
171
|
+
this.observers.clear();
|
|
172
|
+
this.metrics.clear();
|
|
173
|
+
}
|
|
174
|
+
}
|
|
175
|
+
|
|
176
|
+
/**
|
|
177
|
+
* Throttle function to limit how often a function can be called
|
|
178
|
+
* @param {Function} func - Function to throttle
|
|
179
|
+
* @param {number} limit - Time limit in milliseconds
|
|
180
|
+
* @returns {Function} Throttled function
|
|
181
|
+
*/
|
|
182
|
+
export function throttle(func, limit) {
|
|
183
|
+
let inThrottle;
|
|
184
|
+
return function(...args) {
|
|
185
|
+
const context = this;
|
|
186
|
+
if (!inThrottle) {
|
|
187
|
+
func.apply(context, args);
|
|
188
|
+
inThrottle = true;
|
|
189
|
+
setTimeout(() => inThrottle = false, limit);
|
|
190
|
+
}
|
|
191
|
+
};
|
|
192
|
+
}
|
|
193
|
+
|
|
194
|
+
/**
|
|
195
|
+
* Debounce function to delay function execution
|
|
196
|
+
* @param {Function} func - Function to debounce
|
|
197
|
+
* @param {number} delay - Delay in milliseconds
|
|
198
|
+
* @returns {Function} Debounced function
|
|
199
|
+
*/
|
|
200
|
+
export function debounce(func, delay) {
|
|
201
|
+
let timeoutId;
|
|
202
|
+
return function(...args) {
|
|
203
|
+
const context = this;
|
|
204
|
+
clearTimeout(timeoutId);
|
|
205
|
+
timeoutId = setTimeout(() => func.apply(context, args), delay);
|
|
206
|
+
};
|
|
207
|
+
}
|
|
208
|
+
|
|
209
|
+
/**
|
|
210
|
+
* Request animation frame throttle for smooth animations
|
|
211
|
+
* @param {Function} func - Function to throttle
|
|
212
|
+
* @returns {Function} RAF throttled function
|
|
213
|
+
*/
|
|
214
|
+
export function rafThrottle(func) {
|
|
215
|
+
let isThrottled = false;
|
|
216
|
+
return function(...args) {
|
|
217
|
+
if (isThrottled) return;
|
|
218
|
+
|
|
219
|
+
const context = this;
|
|
220
|
+
|
|
221
|
+
isThrottled = true;
|
|
222
|
+
requestAnimationFrame(() => {
|
|
223
|
+
func.apply(context, args);
|
|
224
|
+
isThrottled = false;
|
|
225
|
+
});
|
|
226
|
+
};
|
|
227
|
+
}
|
|
228
|
+
|
|
229
|
+
/**
|
|
230
|
+
* High performance transform utility with hardware acceleration
|
|
231
|
+
* @param {HTMLElement} element - Element to transform
|
|
232
|
+
* @param {number} x - X coordinate
|
|
233
|
+
* @param {number} y - Y coordinate
|
|
234
|
+
* @param {number} [scale=1] - Scale factor
|
|
235
|
+
*/
|
|
236
|
+
export function setTransform(element, x, y, scale = 1) {
|
|
237
|
+
if (!element || !element.style) return;
|
|
238
|
+
|
|
239
|
+
// Use transform3d for hardware acceleration
|
|
240
|
+
element.style.transform = `translate3d(${x}px, ${y}px, 0) scale(${scale})`;
|
|
241
|
+
|
|
242
|
+
// Promote to composite layer for better performance
|
|
243
|
+
element.style.willChange = 'transform';
|
|
244
|
+
}
|
|
245
|
+
|
|
246
|
+
/**
|
|
247
|
+
* Reset element position efficiently
|
|
248
|
+
* @param {HTMLElement} element - Element to reset
|
|
249
|
+
*/
|
|
250
|
+
export function resetTransform(element) {
|
|
251
|
+
if (!element || !element.style) return;
|
|
252
|
+
|
|
253
|
+
element.style.transform = '';
|
|
254
|
+
element.style.left = '';
|
|
255
|
+
element.style.top = '';
|
|
256
|
+
element.style.willChange = '';
|
|
257
|
+
}
|
|
258
|
+
|
|
259
|
+
/**
|
|
260
|
+
* Memory-efficient batch DOM operations
|
|
261
|
+
* @param {Function} callback - Callback containing DOM operations
|
|
262
|
+
* @returns {*} Result of the callback
|
|
263
|
+
*/
|
|
264
|
+
export function batchDOMOperations(callback) {
|
|
265
|
+
return new Promise((resolve) => {
|
|
266
|
+
requestAnimationFrame(() => {
|
|
267
|
+
const result = callback();
|
|
268
|
+
resolve(result);
|
|
269
|
+
});
|
|
270
|
+
});
|
|
271
|
+
}
|
|
272
|
+
|
|
273
|
+
/**
|
|
274
|
+
* Optimized element visibility check
|
|
275
|
+
* @param {HTMLElement} element - Element to check
|
|
276
|
+
* @returns {boolean} True if element is visible
|
|
277
|
+
*/
|
|
278
|
+
export function isElementVisible(element) {
|
|
279
|
+
if (!element || !element.getBoundingClientRect) return false;
|
|
280
|
+
|
|
281
|
+
const rect = element.getBoundingClientRect();
|
|
282
|
+
return (
|
|
283
|
+
rect.width > 0 &&
|
|
284
|
+
rect.height > 0 &&
|
|
285
|
+
rect.bottom > 0 &&
|
|
286
|
+
rect.right > 0 &&
|
|
287
|
+
rect.top < (window.innerHeight || document.documentElement.clientHeight) &&
|
|
288
|
+
rect.left < (window.innerWidth || document.documentElement.clientWidth)
|
|
289
|
+
);
|
|
290
|
+
}
|
|
291
|
+
|
|
292
|
+
/**
|
|
293
|
+
* Memory usage tracking utility
|
|
294
|
+
* @returns {Object} Memory usage information
|
|
295
|
+
*/
|
|
296
|
+
export function getMemoryUsage() {
|
|
297
|
+
if (typeof performance !== 'undefined' && performance.memory) {
|
|
298
|
+
return {
|
|
299
|
+
used: performance.memory.usedJSHeapSize,
|
|
300
|
+
total: performance.memory.totalJSHeapSize,
|
|
301
|
+
limit: performance.memory.jsHeapSizeLimit
|
|
302
|
+
};
|
|
303
|
+
}
|
|
304
|
+
|
|
305
|
+
return {
|
|
306
|
+
used: 0,
|
|
307
|
+
total: 0,
|
|
308
|
+
limit: 0,
|
|
309
|
+
supported: false
|
|
310
|
+
};
|
|
311
|
+
}
|