@rm-graph/core 0.1.2 → 0.1.3
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/dist/{index-DWzDIVQ9.d.mts → index-QzUVGlSo.d.mts} +68 -66
- package/dist/{index-DWzDIVQ9.d.ts → index-QzUVGlSo.d.ts} +68 -66
- package/dist/index.d.mts +110 -186
- package/dist/index.d.ts +110 -186
- package/dist/index.js +646 -900
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +646 -894
- package/dist/index.mjs.map +1 -1
- package/dist/themes/index.d.mts +1 -1
- package/dist/themes/index.d.ts +1 -1
- package/package.json +2 -2
package/dist/index.js
CHANGED
|
@@ -2,6 +2,7 @@
|
|
|
2
2
|
|
|
3
3
|
var chunkKATRK3C3_js = require('./chunk-KATRK3C3.js');
|
|
4
4
|
var scichart = require('scichart');
|
|
5
|
+
var SciChartJSLightTheme = require('scichart/Charting/Themes/SciChartJSLightTheme');
|
|
5
6
|
|
|
6
7
|
// src/utils/helpers.ts
|
|
7
8
|
function generateId(prefix = "chart") {
|
|
@@ -128,7 +129,7 @@ function hexToRgba(hex, alpha = 1) {
|
|
|
128
129
|
}
|
|
129
130
|
|
|
130
131
|
// src/charts/BaseChart.ts
|
|
131
|
-
var SCICHART_VERSION = "
|
|
132
|
+
var SCICHART_VERSION = "4.0.933";
|
|
132
133
|
var sciChartConfigured = false;
|
|
133
134
|
function ensureSciChartConfigured() {
|
|
134
135
|
if (sciChartConfigured) return;
|
|
@@ -138,8 +139,7 @@ function ensureSciChartConfigured() {
|
|
|
138
139
|
} catch {
|
|
139
140
|
try {
|
|
140
141
|
scichart.SciChartSurface.configure({
|
|
141
|
-
wasmUrl: `https://cdn.jsdelivr.net/npm/scichart@${SCICHART_VERSION}/_wasm/scichart2d.wasm
|
|
142
|
-
dataUrl: `https://cdn.jsdelivr.net/npm/scichart@${SCICHART_VERSION}/_wasm/scichart2d.data`
|
|
142
|
+
wasmUrl: `https://cdn.jsdelivr.net/npm/scichart@${SCICHART_VERSION}/_wasm/scichart2d.wasm`
|
|
143
143
|
});
|
|
144
144
|
sciChartConfigured = true;
|
|
145
145
|
} catch {
|
|
@@ -224,6 +224,42 @@ var BaseChart = class {
|
|
|
224
224
|
applyTheme() {
|
|
225
225
|
if (!this.surface) return;
|
|
226
226
|
this.surface.background = this.theme.backgroundColor ?? "#ffffff";
|
|
227
|
+
try {
|
|
228
|
+
const themeName = this.config.theme;
|
|
229
|
+
const { SciChartJSDarkTheme, SciChartJSLightTheme: SciChartJSLightTheme2 } = chunkKATRK3C3_js.__require("scichart");
|
|
230
|
+
const nextThemeProvider = themeName === "light" ? new SciChartJSLightTheme2() : new SciChartJSDarkTheme();
|
|
231
|
+
this.surface.applyTheme?.(nextThemeProvider);
|
|
232
|
+
} catch {
|
|
233
|
+
}
|
|
234
|
+
try {
|
|
235
|
+
const applyAxisTheme = (axis) => {
|
|
236
|
+
if (!axis) return;
|
|
237
|
+
axis.axisTitleStyle = {
|
|
238
|
+
...axis.axisTitleStyle ?? {},
|
|
239
|
+
color: this.theme.axis?.titleColor,
|
|
240
|
+
fontFamily: this.theme.fontFamily
|
|
241
|
+
};
|
|
242
|
+
axis.labelStyle = {
|
|
243
|
+
...axis.labelStyle ?? {},
|
|
244
|
+
color: this.theme.axis?.labelColor,
|
|
245
|
+
fontFamily: this.theme.fontFamily
|
|
246
|
+
};
|
|
247
|
+
axis.majorGridLineStyle = {
|
|
248
|
+
...axis.majorGridLineStyle ?? {},
|
|
249
|
+
color: this.theme.axis?.gridLineColor
|
|
250
|
+
};
|
|
251
|
+
axis.axisBorder = {
|
|
252
|
+
...axis.axisBorder ?? {},
|
|
253
|
+
color: this.theme.axis?.lineColor
|
|
254
|
+
};
|
|
255
|
+
};
|
|
256
|
+
const xAxes = this.surface.xAxes;
|
|
257
|
+
const yAxes = this.surface.yAxes;
|
|
258
|
+
const toArray = (axes) => axes?.asArray?.() ?? axes?.itemsArray ?? axes?.items ?? [];
|
|
259
|
+
for (const axis of toArray(xAxes)) applyAxisTheme(axis);
|
|
260
|
+
for (const axis of toArray(yAxes)) applyAxisTheme(axis);
|
|
261
|
+
} catch {
|
|
262
|
+
}
|
|
227
263
|
}
|
|
228
264
|
/**
|
|
229
265
|
* Set up resize observer for responsive charts
|
|
@@ -255,6 +291,17 @@ var BaseChart = class {
|
|
|
255
291
|
}
|
|
256
292
|
this.handleResize();
|
|
257
293
|
}
|
|
294
|
+
/**
|
|
295
|
+
* Reset zoom to fit all data (zoom extents)
|
|
296
|
+
* Note: not part of the ChartInstance interface, but available on concrete chart classes.
|
|
297
|
+
*/
|
|
298
|
+
resetZoom() {
|
|
299
|
+
if (!this.surface) return;
|
|
300
|
+
try {
|
|
301
|
+
this.surface.zoomExtents?.();
|
|
302
|
+
} catch {
|
|
303
|
+
}
|
|
304
|
+
}
|
|
258
305
|
/**
|
|
259
306
|
* Export chart as image
|
|
260
307
|
*/
|
|
@@ -270,901 +317,72 @@ var BaseChart = class {
|
|
|
270
317
|
return canvas.toDataURL(mimeType);
|
|
271
318
|
}
|
|
272
319
|
/**
|
|
273
|
-
* Add event listener
|
|
274
|
-
*/
|
|
275
|
-
on(event, handler) {
|
|
276
|
-
if (!this.eventHandlers.has(event)) {
|
|
277
|
-
this.eventHandlers.set(event, /* @__PURE__ */ new Set());
|
|
278
|
-
}
|
|
279
|
-
this.eventHandlers.get(event).add(handler);
|
|
280
|
-
}
|
|
281
|
-
/**
|
|
282
|
-
* Remove event listener
|
|
283
|
-
*/
|
|
284
|
-
off(event, handler) {
|
|
285
|
-
const handlers = this.eventHandlers.get(event);
|
|
286
|
-
if (handlers) {
|
|
287
|
-
handlers.delete(handler);
|
|
288
|
-
}
|
|
289
|
-
}
|
|
290
|
-
/**
|
|
291
|
-
* Emit an event
|
|
292
|
-
*/
|
|
293
|
-
emit(event, data) {
|
|
294
|
-
const handlers = this.eventHandlers.get(event);
|
|
295
|
-
if (handlers) {
|
|
296
|
-
handlers.forEach((handler) => handler(data));
|
|
297
|
-
}
|
|
298
|
-
}
|
|
299
|
-
/**
|
|
300
|
-
* Destroy the chart and clean up resources
|
|
301
|
-
*/
|
|
302
|
-
destroy() {
|
|
303
|
-
if (this.isDestroyed) return;
|
|
304
|
-
if (this.resizeObserver) {
|
|
305
|
-
this.resizeObserver.disconnect();
|
|
306
|
-
this.resizeObserver = null;
|
|
307
|
-
}
|
|
308
|
-
this.eventHandlers.clear();
|
|
309
|
-
if (this.surface) {
|
|
310
|
-
this.surface.delete();
|
|
311
|
-
this.surface = null;
|
|
312
|
-
}
|
|
313
|
-
if (this.container) {
|
|
314
|
-
this.container.innerHTML = "";
|
|
315
|
-
}
|
|
316
|
-
this.isDestroyed = true;
|
|
317
|
-
this.isInitialized = false;
|
|
318
|
-
}
|
|
319
|
-
/**
|
|
320
|
-
* Get current configuration
|
|
321
|
-
*/
|
|
322
|
-
getConfig() {
|
|
323
|
-
return { ...this.config };
|
|
324
|
-
}
|
|
325
|
-
/**
|
|
326
|
-
* Get current theme
|
|
327
|
-
*/
|
|
328
|
-
getTheme() {
|
|
329
|
-
return { ...this.theme };
|
|
330
|
-
}
|
|
331
|
-
/**
|
|
332
|
-
* Check if chart is initialized
|
|
333
|
-
*/
|
|
334
|
-
isReady() {
|
|
335
|
-
return this.isInitialized && !this.isDestroyed;
|
|
336
|
-
}
|
|
337
|
-
};
|
|
338
|
-
function getSciChartTheme(themeName) {
|
|
339
|
-
switch (themeName) {
|
|
340
|
-
case "light":
|
|
341
|
-
return new scichart.SciChartJSLightTheme();
|
|
342
|
-
case "dark":
|
|
343
|
-
case "modern":
|
|
344
|
-
case "midnight":
|
|
345
|
-
default:
|
|
346
|
-
return new scichart.SciChartJSDarkTheme();
|
|
347
|
-
}
|
|
348
|
-
}
|
|
349
|
-
var LineChart = class extends BaseChart {
|
|
350
|
-
constructor(config) {
|
|
351
|
-
super(config);
|
|
352
|
-
this.dataSeries = /* @__PURE__ */ new Map();
|
|
353
|
-
this.renderableSeries = [];
|
|
354
|
-
this.wasmContext = null;
|
|
355
|
-
}
|
|
356
|
-
/**
|
|
357
|
-
* Create the SciChart surface for line chart
|
|
358
|
-
*/
|
|
359
|
-
async createSurface() {
|
|
360
|
-
if (!this.container) {
|
|
361
|
-
throw new Error("Container not set");
|
|
362
|
-
}
|
|
363
|
-
const sciChartTheme = getSciChartTheme(this.config.theme);
|
|
364
|
-
if (!this.container.id) {
|
|
365
|
-
this.container.id = this.id;
|
|
366
|
-
}
|
|
367
|
-
const { sciChartSurface, wasmContext } = await scichart.SciChartSurface.create(
|
|
368
|
-
this.container,
|
|
369
|
-
{
|
|
370
|
-
theme: sciChartTheme
|
|
371
|
-
}
|
|
372
|
-
);
|
|
373
|
-
this.surface = sciChartSurface;
|
|
374
|
-
this.wasmContext = wasmContext;
|
|
375
|
-
const xAxis = new scichart.NumericAxis(wasmContext, {
|
|
376
|
-
axisTitle: this.config.xAxis?.title,
|
|
377
|
-
drawMajorGridLines: this.config.xAxis?.gridLines?.show ?? true,
|
|
378
|
-
drawMinorGridLines: false,
|
|
379
|
-
axisTitleStyle: {
|
|
380
|
-
fontSize: 14,
|
|
381
|
-
fontFamily: this.theme.fontFamily,
|
|
382
|
-
color: this.theme.axis?.titleColor
|
|
383
|
-
},
|
|
384
|
-
labelStyle: {
|
|
385
|
-
fontSize: 12,
|
|
386
|
-
fontFamily: this.theme.fontFamily,
|
|
387
|
-
color: this.theme.axis?.labelColor
|
|
388
|
-
},
|
|
389
|
-
majorGridLineStyle: {
|
|
390
|
-
color: this.theme.axis?.gridLineColor ?? "#e9ecef",
|
|
391
|
-
strokeThickness: 1
|
|
392
|
-
},
|
|
393
|
-
axisBorder: {
|
|
394
|
-
color: this.theme.axis?.lineColor ?? "#dee2e6"
|
|
395
|
-
},
|
|
396
|
-
autoRange: scichart.EAutoRange.Always
|
|
397
|
-
});
|
|
398
|
-
const yAxis = new scichart.NumericAxis(wasmContext, {
|
|
399
|
-
axisTitle: this.config.yAxis?.title,
|
|
400
|
-
drawMajorGridLines: this.config.yAxis?.gridLines?.show ?? true,
|
|
401
|
-
drawMinorGridLines: false,
|
|
402
|
-
axisTitleStyle: {
|
|
403
|
-
fontSize: 14,
|
|
404
|
-
fontFamily: this.theme.fontFamily,
|
|
405
|
-
color: this.theme.axis?.titleColor
|
|
406
|
-
},
|
|
407
|
-
labelStyle: {
|
|
408
|
-
fontSize: 12,
|
|
409
|
-
fontFamily: this.theme.fontFamily,
|
|
410
|
-
color: this.theme.axis?.labelColor
|
|
411
|
-
},
|
|
412
|
-
majorGridLineStyle: {
|
|
413
|
-
color: this.theme.axis?.gridLineColor ?? "#e9ecef",
|
|
414
|
-
strokeThickness: 1
|
|
415
|
-
},
|
|
416
|
-
axisBorder: {
|
|
417
|
-
color: this.theme.axis?.lineColor ?? "#dee2e6"
|
|
418
|
-
},
|
|
419
|
-
autoRange: scichart.EAutoRange.Always
|
|
420
|
-
});
|
|
421
|
-
if (this.config.xAxis?.min !== void 0 && this.config.xAxis?.max !== void 0) {
|
|
422
|
-
xAxis.visibleRange = new scichart.NumberRange(this.config.xAxis.min, this.config.xAxis.max);
|
|
423
|
-
xAxis.autoRange = scichart.EAutoRange.Never;
|
|
424
|
-
}
|
|
425
|
-
if (this.config.yAxis?.min !== void 0 && this.config.yAxis?.max !== void 0) {
|
|
426
|
-
yAxis.visibleRange = new scichart.NumberRange(this.config.yAxis.min, this.config.yAxis.max);
|
|
427
|
-
yAxis.autoRange = scichart.EAutoRange.Never;
|
|
428
|
-
}
|
|
429
|
-
sciChartSurface.xAxes.add(xAxis);
|
|
430
|
-
sciChartSurface.yAxes.add(yAxis);
|
|
431
|
-
if (this.config.tooltip?.enabled !== false) {
|
|
432
|
-
sciChartSurface.chartModifiers.add(
|
|
433
|
-
new scichart.RolloverModifier({
|
|
434
|
-
showTooltip: true,
|
|
435
|
-
showAxisLabel: true
|
|
436
|
-
})
|
|
437
|
-
);
|
|
438
|
-
}
|
|
439
|
-
sciChartSurface.chartModifiers.add(new scichart.ZoomPanModifier());
|
|
440
|
-
sciChartSurface.chartModifiers.add(new scichart.MouseWheelZoomModifier());
|
|
441
|
-
this.addSeries(this.config.series);
|
|
442
|
-
}
|
|
443
|
-
/**
|
|
444
|
-
* Add series to the chart
|
|
445
|
-
*/
|
|
446
|
-
addSeries(seriesConfigs) {
|
|
447
|
-
if (!this.surface || !this.wasmContext) return;
|
|
448
|
-
const wasmContext = this.wasmContext;
|
|
449
|
-
const colorPalette = this.theme.colorPalette ?? [];
|
|
450
|
-
seriesConfigs.forEach((seriesConfig, index) => {
|
|
451
|
-
const data = normalizeDataPoints(seriesConfig.data);
|
|
452
|
-
const xValues = extractXValues(data);
|
|
453
|
-
const yValues = extractYValues(data);
|
|
454
|
-
const dataSeries = new scichart.XyDataSeries(wasmContext, {
|
|
455
|
-
xValues,
|
|
456
|
-
yValues,
|
|
457
|
-
dataSeriesName: seriesConfig.name
|
|
458
|
-
});
|
|
459
|
-
this.dataSeries.set(seriesConfig.name, dataSeries);
|
|
460
|
-
const color = seriesConfig.color ?? colorPalette[index % colorPalette.length] ?? "#6366f1";
|
|
461
|
-
const lineSeries = new scichart.FastLineRenderableSeries(wasmContext);
|
|
462
|
-
lineSeries.dataSeries = dataSeries;
|
|
463
|
-
lineSeries.stroke = color;
|
|
464
|
-
lineSeries.strokeThickness = this.config.lineWidth ?? 2;
|
|
465
|
-
if (this.config.showPoints) {
|
|
466
|
-
lineSeries.pointMarker = new scichart.EllipsePointMarker(wasmContext, {
|
|
467
|
-
width: this.config.pointSize ?? 8,
|
|
468
|
-
height: this.config.pointSize ?? 8,
|
|
469
|
-
fill: color,
|
|
470
|
-
stroke: color,
|
|
471
|
-
strokeThickness: 0
|
|
472
|
-
});
|
|
473
|
-
}
|
|
474
|
-
if (this.config.animation !== false) {
|
|
475
|
-
lineSeries.animation = new scichart.SweepAnimation({
|
|
476
|
-
duration: typeof this.config.animation === "object" ? this.config.animation.duration ?? 500 : 500
|
|
477
|
-
});
|
|
478
|
-
}
|
|
479
|
-
this.renderableSeries.push(lineSeries);
|
|
480
|
-
this.surface.renderableSeries.add(lineSeries);
|
|
481
|
-
});
|
|
482
|
-
}
|
|
483
|
-
/**
|
|
484
|
-
* Set new data for the chart
|
|
485
|
-
*/
|
|
486
|
-
setData(data) {
|
|
487
|
-
if (!this.surface) {
|
|
488
|
-
this.config.series = data;
|
|
489
|
-
return;
|
|
490
|
-
}
|
|
491
|
-
this.clearSeries();
|
|
492
|
-
this.config.series = data;
|
|
493
|
-
this.addSeries(data);
|
|
494
|
-
}
|
|
495
|
-
/**
|
|
496
|
-
* Update specific series data
|
|
497
|
-
*/
|
|
498
|
-
updateSeriesData(seriesName, data) {
|
|
499
|
-
const dataSeries = this.dataSeries.get(seriesName);
|
|
500
|
-
if (!dataSeries) {
|
|
501
|
-
console.warn(`Series "${seriesName}" not found`);
|
|
502
|
-
return;
|
|
503
|
-
}
|
|
504
|
-
const normalized = normalizeDataPoints(data);
|
|
505
|
-
const xValues = extractXValues(normalized);
|
|
506
|
-
const yValues = extractYValues(normalized);
|
|
507
|
-
dataSeries.clear();
|
|
508
|
-
dataSeries.appendRange(xValues, yValues);
|
|
509
|
-
}
|
|
510
|
-
/**
|
|
511
|
-
* Append data to a series
|
|
512
|
-
*/
|
|
513
|
-
appendData(seriesName, data) {
|
|
514
|
-
const dataSeries = this.dataSeries.get(seriesName);
|
|
515
|
-
if (!dataSeries) {
|
|
516
|
-
console.warn(`Series "${seriesName}" not found`);
|
|
517
|
-
return;
|
|
518
|
-
}
|
|
519
|
-
const points = Array.isArray(data) ? data : [data];
|
|
520
|
-
const normalized = normalizeDataPoints(points);
|
|
521
|
-
const xValues = extractXValues(normalized);
|
|
522
|
-
const yValues = extractYValues(normalized);
|
|
523
|
-
dataSeries.appendRange(xValues, yValues);
|
|
524
|
-
}
|
|
525
|
-
/**
|
|
526
|
-
* Clear all series
|
|
527
|
-
*/
|
|
528
|
-
clearSeries() {
|
|
529
|
-
if (!this.surface) return;
|
|
530
|
-
this.renderableSeries.forEach((series) => {
|
|
531
|
-
this.surface.renderableSeries.remove(series);
|
|
532
|
-
series.delete();
|
|
533
|
-
});
|
|
534
|
-
this.renderableSeries = [];
|
|
535
|
-
this.dataSeries.forEach((ds) => ds.delete());
|
|
536
|
-
this.dataSeries.clear();
|
|
537
|
-
}
|
|
538
|
-
/**
|
|
539
|
-
* Update chart
|
|
540
|
-
*/
|
|
541
|
-
update() {
|
|
542
|
-
if (!this.surface) return;
|
|
543
|
-
this.applyTheme();
|
|
544
|
-
this.surface.invalidateElement();
|
|
545
|
-
}
|
|
546
|
-
/**
|
|
547
|
-
* Apply theme to line chart
|
|
548
|
-
*/
|
|
549
|
-
applyTheme() {
|
|
550
|
-
super.applyTheme();
|
|
551
|
-
if (!this.surface) return;
|
|
552
|
-
const colorPalette = this.theme.colorPalette ?? [];
|
|
553
|
-
this.renderableSeries.forEach((series, index) => {
|
|
554
|
-
const originalColor = this.config.series[index]?.color;
|
|
555
|
-
if (!originalColor) {
|
|
556
|
-
series.stroke = colorPalette[index % colorPalette.length];
|
|
557
|
-
}
|
|
558
|
-
});
|
|
559
|
-
}
|
|
560
|
-
/**
|
|
561
|
-
* Destroy and clean up
|
|
562
|
-
*/
|
|
563
|
-
destroy() {
|
|
564
|
-
this.clearSeries();
|
|
565
|
-
super.destroy();
|
|
566
|
-
}
|
|
567
|
-
};
|
|
568
|
-
async function createLineChart(container, config) {
|
|
569
|
-
const chart = new LineChart(config);
|
|
570
|
-
await chart.init(container);
|
|
571
|
-
return chart;
|
|
572
|
-
}
|
|
573
|
-
function getSciChartTheme2(themeName) {
|
|
574
|
-
switch (themeName) {
|
|
575
|
-
case "light":
|
|
576
|
-
return new scichart.SciChartJSLightTheme();
|
|
577
|
-
case "dark":
|
|
578
|
-
case "modern":
|
|
579
|
-
case "midnight":
|
|
580
|
-
default:
|
|
581
|
-
return new scichart.SciChartJSDarkTheme();
|
|
582
|
-
}
|
|
583
|
-
}
|
|
584
|
-
var BarChart = class extends BaseChart {
|
|
585
|
-
constructor(config) {
|
|
586
|
-
super(config);
|
|
587
|
-
this.dataSeries = /* @__PURE__ */ new Map();
|
|
588
|
-
this.renderableSeries = [];
|
|
589
|
-
this.wasmContext = null;
|
|
590
|
-
}
|
|
591
|
-
/**
|
|
592
|
-
* Create the SciChart surface for bar chart
|
|
593
|
-
*/
|
|
594
|
-
async createSurface() {
|
|
595
|
-
if (!this.container) {
|
|
596
|
-
throw new Error("Container not set");
|
|
597
|
-
}
|
|
598
|
-
const sciChartTheme = getSciChartTheme2(this.config.theme);
|
|
599
|
-
if (!this.container.id) {
|
|
600
|
-
this.container.id = this.id;
|
|
601
|
-
}
|
|
602
|
-
const { sciChartSurface, wasmContext } = await scichart.SciChartSurface.create(
|
|
603
|
-
this.container,
|
|
604
|
-
{
|
|
605
|
-
theme: sciChartTheme
|
|
606
|
-
}
|
|
607
|
-
);
|
|
608
|
-
this.surface = sciChartSurface;
|
|
609
|
-
this.wasmContext = wasmContext;
|
|
610
|
-
const xAxis = new scichart.NumericAxis(wasmContext, {
|
|
611
|
-
axisTitle: this.config.xAxis?.title,
|
|
612
|
-
drawMajorGridLines: this.config.xAxis?.gridLines?.show ?? false,
|
|
613
|
-
drawMinorGridLines: false,
|
|
614
|
-
axisTitleStyle: {
|
|
615
|
-
fontSize: 14,
|
|
616
|
-
fontFamily: this.theme.fontFamily,
|
|
617
|
-
color: this.theme.axis?.titleColor
|
|
618
|
-
},
|
|
619
|
-
labelStyle: {
|
|
620
|
-
fontSize: 12,
|
|
621
|
-
fontFamily: this.theme.fontFamily,
|
|
622
|
-
color: this.theme.axis?.labelColor
|
|
623
|
-
},
|
|
624
|
-
autoRange: scichart.EAutoRange.Always
|
|
625
|
-
});
|
|
626
|
-
const yAxis = new scichart.NumericAxis(wasmContext, {
|
|
627
|
-
axisTitle: this.config.yAxis?.title,
|
|
628
|
-
drawMajorGridLines: this.config.yAxis?.gridLines?.show ?? true,
|
|
629
|
-
drawMinorGridLines: false,
|
|
630
|
-
axisTitleStyle: {
|
|
631
|
-
fontSize: 14,
|
|
632
|
-
fontFamily: this.theme.fontFamily,
|
|
633
|
-
color: this.theme.axis?.titleColor
|
|
634
|
-
},
|
|
635
|
-
labelStyle: {
|
|
636
|
-
fontSize: 12,
|
|
637
|
-
fontFamily: this.theme.fontFamily,
|
|
638
|
-
color: this.theme.axis?.labelColor
|
|
639
|
-
},
|
|
640
|
-
autoRange: scichart.EAutoRange.Always,
|
|
641
|
-
growBy: new scichart.NumberRange(0, 0.1)
|
|
642
|
-
// Add 10% padding at top
|
|
643
|
-
});
|
|
644
|
-
if (this.config.xAxis?.min !== void 0 && this.config.xAxis?.max !== void 0) {
|
|
645
|
-
xAxis.visibleRange = new scichart.NumberRange(this.config.xAxis.min, this.config.xAxis.max);
|
|
646
|
-
xAxis.autoRange = scichart.EAutoRange.Never;
|
|
647
|
-
}
|
|
648
|
-
if (this.config.yAxis?.min !== void 0 && this.config.yAxis?.max !== void 0) {
|
|
649
|
-
yAxis.visibleRange = new scichart.NumberRange(this.config.yAxis.min, this.config.yAxis.max);
|
|
650
|
-
yAxis.autoRange = scichart.EAutoRange.Never;
|
|
651
|
-
}
|
|
652
|
-
sciChartSurface.xAxes.add(xAxis);
|
|
653
|
-
sciChartSurface.yAxes.add(yAxis);
|
|
654
|
-
if (this.config.tooltip?.enabled !== false) {
|
|
655
|
-
sciChartSurface.chartModifiers.add(
|
|
656
|
-
new scichart.RolloverModifier({
|
|
657
|
-
showTooltip: true,
|
|
658
|
-
showAxisLabel: true
|
|
659
|
-
})
|
|
660
|
-
);
|
|
661
|
-
}
|
|
662
|
-
sciChartSurface.chartModifiers.add(new scichart.ZoomPanModifier());
|
|
663
|
-
this.addSeries(this.config.series);
|
|
664
|
-
}
|
|
665
|
-
/**
|
|
666
|
-
* Add series to the chart
|
|
667
|
-
*/
|
|
668
|
-
addSeries(seriesConfigs) {
|
|
669
|
-
if (!this.surface || !this.wasmContext) return;
|
|
670
|
-
const wasmContext = this.wasmContext;
|
|
671
|
-
const colorPalette = this.theme.colorPalette ?? [];
|
|
672
|
-
const seriesCount = seriesConfigs.length;
|
|
673
|
-
const dataPointWidth = this.config.barWidth ?? 0.7;
|
|
674
|
-
seriesConfigs.forEach((seriesConfig, index) => {
|
|
675
|
-
const data = normalizeDataPoints(seriesConfig.data);
|
|
676
|
-
let xValues = extractXValues(data);
|
|
677
|
-
if (!this.config.stacked && seriesCount > 1) {
|
|
678
|
-
const offset = (index - (seriesCount - 1) / 2) * (dataPointWidth / seriesCount);
|
|
679
|
-
xValues = xValues.map((x) => x + offset);
|
|
680
|
-
}
|
|
681
|
-
const yValues = extractYValues(data);
|
|
682
|
-
const dataSeries = new scichart.XyDataSeries(wasmContext, {
|
|
683
|
-
xValues,
|
|
684
|
-
yValues,
|
|
685
|
-
dataSeriesName: seriesConfig.name
|
|
686
|
-
});
|
|
687
|
-
this.dataSeries.set(seriesConfig.name, dataSeries);
|
|
688
|
-
const color = seriesConfig.color ?? colorPalette[index % colorPalette.length] ?? "#6366f1";
|
|
689
|
-
const columnSeries = new scichart.FastColumnRenderableSeries(wasmContext);
|
|
690
|
-
columnSeries.dataSeries = dataSeries;
|
|
691
|
-
columnSeries.fill = color;
|
|
692
|
-
columnSeries.stroke = color;
|
|
693
|
-
columnSeries.strokeThickness = 0;
|
|
694
|
-
columnSeries.dataPointWidth = this.config.stacked ? dataPointWidth : dataPointWidth / seriesCount;
|
|
695
|
-
columnSeries.cornerRadius = this.config.borderRadius ?? 0;
|
|
696
|
-
if (this.config.animation !== false) {
|
|
697
|
-
columnSeries.animation = new scichart.WaveAnimation({
|
|
698
|
-
duration: typeof this.config.animation === "object" ? this.config.animation.duration ?? 500 : 500
|
|
699
|
-
});
|
|
700
|
-
}
|
|
701
|
-
columnSeries.fillLinearGradient = new scichart.GradientParams(
|
|
702
|
-
new scichart.Point(0, 0),
|
|
703
|
-
new scichart.Point(0, 1),
|
|
704
|
-
[
|
|
705
|
-
{ color, offset: 0 },
|
|
706
|
-
{ color: hexToRgba(color, 0.7), offset: 1 }
|
|
707
|
-
]
|
|
708
|
-
);
|
|
709
|
-
this.renderableSeries.push(columnSeries);
|
|
710
|
-
this.surface.renderableSeries.add(columnSeries);
|
|
711
|
-
});
|
|
712
|
-
}
|
|
713
|
-
/**
|
|
714
|
-
* Set new data for the chart
|
|
715
|
-
*/
|
|
716
|
-
setData(data) {
|
|
717
|
-
if (!this.surface) {
|
|
718
|
-
this.config.series = data;
|
|
719
|
-
return;
|
|
720
|
-
}
|
|
721
|
-
this.clearSeries();
|
|
722
|
-
this.config.series = data;
|
|
723
|
-
this.addSeries(data);
|
|
724
|
-
}
|
|
725
|
-
/**
|
|
726
|
-
* Update specific series data
|
|
727
|
-
*/
|
|
728
|
-
updateSeriesData(seriesName, data) {
|
|
729
|
-
const dataSeries = this.dataSeries.get(seriesName);
|
|
730
|
-
if (!dataSeries) {
|
|
731
|
-
console.warn(`Series "${seriesName}" not found`);
|
|
732
|
-
return;
|
|
733
|
-
}
|
|
734
|
-
const normalized = normalizeDataPoints(data);
|
|
735
|
-
const xValues = extractXValues(normalized);
|
|
736
|
-
const yValues = extractYValues(normalized);
|
|
737
|
-
dataSeries.clear();
|
|
738
|
-
dataSeries.appendRange(xValues, yValues);
|
|
739
|
-
}
|
|
740
|
-
/**
|
|
741
|
-
* Clear all series
|
|
742
|
-
*/
|
|
743
|
-
clearSeries() {
|
|
744
|
-
if (!this.surface) return;
|
|
745
|
-
this.renderableSeries.forEach((series) => {
|
|
746
|
-
this.surface.renderableSeries.remove(series);
|
|
747
|
-
series.delete();
|
|
748
|
-
});
|
|
749
|
-
this.renderableSeries = [];
|
|
750
|
-
this.dataSeries.forEach((ds) => ds.delete());
|
|
751
|
-
this.dataSeries.clear();
|
|
752
|
-
}
|
|
753
|
-
/**
|
|
754
|
-
* Update chart
|
|
755
|
-
*/
|
|
756
|
-
update() {
|
|
757
|
-
if (!this.surface) return;
|
|
758
|
-
this.applyTheme();
|
|
759
|
-
this.surface.invalidateElement();
|
|
760
|
-
}
|
|
761
|
-
/**
|
|
762
|
-
* Destroy and clean up
|
|
763
|
-
*/
|
|
764
|
-
destroy() {
|
|
765
|
-
this.clearSeries();
|
|
766
|
-
super.destroy();
|
|
767
|
-
}
|
|
768
|
-
};
|
|
769
|
-
async function createBarChart(container, config) {
|
|
770
|
-
const chart = new BarChart(config);
|
|
771
|
-
await chart.init(container);
|
|
772
|
-
return chart;
|
|
773
|
-
}
|
|
774
|
-
function getSciChartTheme3(themeName) {
|
|
775
|
-
switch (themeName) {
|
|
776
|
-
case "light":
|
|
777
|
-
return new scichart.SciChartJSLightTheme();
|
|
778
|
-
case "dark":
|
|
779
|
-
case "modern":
|
|
780
|
-
case "midnight":
|
|
781
|
-
default:
|
|
782
|
-
return new scichart.SciChartJSDarkTheme();
|
|
783
|
-
}
|
|
784
|
-
}
|
|
785
|
-
var AreaChart = class extends BaseChart {
|
|
786
|
-
constructor(config) {
|
|
787
|
-
super(config);
|
|
788
|
-
this.dataSeries = /* @__PURE__ */ new Map();
|
|
789
|
-
this.renderableSeries = [];
|
|
790
|
-
this.wasmContext = null;
|
|
791
|
-
}
|
|
792
|
-
/**
|
|
793
|
-
* Create the SciChart surface for area chart
|
|
794
|
-
*/
|
|
795
|
-
async createSurface() {
|
|
796
|
-
if (!this.container) {
|
|
797
|
-
throw new Error("Container not set");
|
|
798
|
-
}
|
|
799
|
-
const sciChartTheme = getSciChartTheme3(this.config.theme);
|
|
800
|
-
if (!this.container.id) {
|
|
801
|
-
this.container.id = this.id;
|
|
802
|
-
}
|
|
803
|
-
const { sciChartSurface, wasmContext } = await scichart.SciChartSurface.create(
|
|
804
|
-
this.container,
|
|
805
|
-
{
|
|
806
|
-
theme: sciChartTheme
|
|
807
|
-
}
|
|
808
|
-
);
|
|
809
|
-
this.surface = sciChartSurface;
|
|
810
|
-
this.wasmContext = wasmContext;
|
|
811
|
-
const xAxis = new scichart.NumericAxis(wasmContext, {
|
|
812
|
-
axisTitle: this.config.xAxis?.title,
|
|
813
|
-
drawMajorGridLines: this.config.xAxis?.gridLines?.show ?? true,
|
|
814
|
-
drawMinorGridLines: false,
|
|
815
|
-
axisTitleStyle: {
|
|
816
|
-
fontSize: 14,
|
|
817
|
-
fontFamily: this.theme.fontFamily,
|
|
818
|
-
color: this.theme.axis?.titleColor
|
|
819
|
-
},
|
|
820
|
-
labelStyle: {
|
|
821
|
-
fontSize: 12,
|
|
822
|
-
fontFamily: this.theme.fontFamily,
|
|
823
|
-
color: this.theme.axis?.labelColor
|
|
824
|
-
},
|
|
825
|
-
autoRange: scichart.EAutoRange.Always
|
|
826
|
-
});
|
|
827
|
-
const yAxis = new scichart.NumericAxis(wasmContext, {
|
|
828
|
-
axisTitle: this.config.yAxis?.title,
|
|
829
|
-
drawMajorGridLines: this.config.yAxis?.gridLines?.show ?? true,
|
|
830
|
-
drawMinorGridLines: false,
|
|
831
|
-
axisTitleStyle: {
|
|
832
|
-
fontSize: 14,
|
|
833
|
-
fontFamily: this.theme.fontFamily,
|
|
834
|
-
color: this.theme.axis?.titleColor
|
|
835
|
-
},
|
|
836
|
-
labelStyle: {
|
|
837
|
-
fontSize: 12,
|
|
838
|
-
fontFamily: this.theme.fontFamily,
|
|
839
|
-
color: this.theme.axis?.labelColor
|
|
840
|
-
},
|
|
841
|
-
autoRange: scichart.EAutoRange.Always,
|
|
842
|
-
growBy: new scichart.NumberRange(0, 0.1)
|
|
843
|
-
});
|
|
844
|
-
if (this.config.xAxis?.min !== void 0 && this.config.xAxis?.max !== void 0) {
|
|
845
|
-
xAxis.visibleRange = new scichart.NumberRange(this.config.xAxis.min, this.config.xAxis.max);
|
|
846
|
-
xAxis.autoRange = scichart.EAutoRange.Never;
|
|
847
|
-
}
|
|
848
|
-
if (this.config.yAxis?.min !== void 0 && this.config.yAxis?.max !== void 0) {
|
|
849
|
-
yAxis.visibleRange = new scichart.NumberRange(this.config.yAxis.min, this.config.yAxis.max);
|
|
850
|
-
yAxis.autoRange = scichart.EAutoRange.Never;
|
|
851
|
-
}
|
|
852
|
-
sciChartSurface.xAxes.add(xAxis);
|
|
853
|
-
sciChartSurface.yAxes.add(yAxis);
|
|
854
|
-
if (this.config.tooltip?.enabled !== false) {
|
|
855
|
-
sciChartSurface.chartModifiers.add(
|
|
856
|
-
new scichart.RolloverModifier({
|
|
857
|
-
showTooltip: true,
|
|
858
|
-
showAxisLabel: true
|
|
859
|
-
})
|
|
860
|
-
);
|
|
861
|
-
}
|
|
862
|
-
sciChartSurface.chartModifiers.add(new scichart.ZoomPanModifier());
|
|
863
|
-
sciChartSurface.chartModifiers.add(new scichart.MouseWheelZoomModifier());
|
|
864
|
-
this.addSeries(this.config.series);
|
|
865
|
-
}
|
|
866
|
-
/**
|
|
867
|
-
* Add series to the chart
|
|
868
|
-
*/
|
|
869
|
-
addSeries(seriesConfigs) {
|
|
870
|
-
if (!this.surface || !this.wasmContext) return;
|
|
871
|
-
const wasmContext = this.wasmContext;
|
|
872
|
-
const colorPalette = this.theme.colorPalette ?? [];
|
|
873
|
-
const fillOpacity = this.config.fillOpacity ?? 0.5;
|
|
874
|
-
seriesConfigs.forEach((seriesConfig, index) => {
|
|
875
|
-
const data = normalizeDataPoints(seriesConfig.data);
|
|
876
|
-
const xValues = extractXValues(data);
|
|
877
|
-
const yValues = extractYValues(data);
|
|
878
|
-
const dataSeries = new scichart.XyDataSeries(wasmContext, {
|
|
879
|
-
xValues,
|
|
880
|
-
yValues,
|
|
881
|
-
dataSeriesName: seriesConfig.name
|
|
882
|
-
});
|
|
883
|
-
this.dataSeries.set(seriesConfig.name, dataSeries);
|
|
884
|
-
const color = seriesConfig.color ?? colorPalette[index % colorPalette.length] ?? "#6366f1";
|
|
885
|
-
const areaSeries = new scichart.FastMountainRenderableSeries(wasmContext, {
|
|
886
|
-
dataSeries,
|
|
887
|
-
stroke: color,
|
|
888
|
-
strokeThickness: this.config.lineWidth ?? 2,
|
|
889
|
-
fill: hexToRgba(color, fillOpacity),
|
|
890
|
-
...this.config.animation !== false && {
|
|
891
|
-
animation: new scichart.SweepAnimation({
|
|
892
|
-
duration: typeof this.config.animation === "object" ? this.config.animation.duration ?? 500 : 500
|
|
893
|
-
})
|
|
894
|
-
}
|
|
895
|
-
});
|
|
896
|
-
areaSeries.fillLinearGradient = new scichart.GradientParams(
|
|
897
|
-
new scichart.Point(0, 0),
|
|
898
|
-
new scichart.Point(0, 1),
|
|
899
|
-
[
|
|
900
|
-
{ color: hexToRgba(color, fillOpacity), offset: 0 },
|
|
901
|
-
{ color: hexToRgba(color, 0.05), offset: 1 }
|
|
902
|
-
]
|
|
903
|
-
);
|
|
904
|
-
this.renderableSeries.push(areaSeries);
|
|
905
|
-
this.surface.renderableSeries.add(areaSeries);
|
|
906
|
-
});
|
|
907
|
-
}
|
|
908
|
-
/**
|
|
909
|
-
* Set new data for the chart
|
|
910
|
-
*/
|
|
911
|
-
setData(data) {
|
|
912
|
-
if (!this.surface) {
|
|
913
|
-
this.config.series = data;
|
|
914
|
-
return;
|
|
915
|
-
}
|
|
916
|
-
this.clearSeries();
|
|
917
|
-
this.config.series = data;
|
|
918
|
-
this.addSeries(data);
|
|
919
|
-
}
|
|
920
|
-
/**
|
|
921
|
-
* Update specific series data
|
|
922
|
-
*/
|
|
923
|
-
updateSeriesData(seriesName, data) {
|
|
924
|
-
const dataSeries = this.dataSeries.get(seriesName);
|
|
925
|
-
if (!dataSeries) {
|
|
926
|
-
console.warn(`Series "${seriesName}" not found`);
|
|
927
|
-
return;
|
|
928
|
-
}
|
|
929
|
-
const normalized = normalizeDataPoints(data);
|
|
930
|
-
const xValues = extractXValues(normalized);
|
|
931
|
-
const yValues = extractYValues(normalized);
|
|
932
|
-
dataSeries.clear();
|
|
933
|
-
dataSeries.appendRange(xValues, yValues);
|
|
934
|
-
}
|
|
935
|
-
/**
|
|
936
|
-
* Clear all series
|
|
937
|
-
*/
|
|
938
|
-
clearSeries() {
|
|
939
|
-
if (!this.surface) return;
|
|
940
|
-
this.renderableSeries.forEach((series) => {
|
|
941
|
-
this.surface.renderableSeries.remove(series);
|
|
942
|
-
series.delete();
|
|
943
|
-
});
|
|
944
|
-
this.renderableSeries = [];
|
|
945
|
-
this.dataSeries.forEach((ds) => ds.delete());
|
|
946
|
-
this.dataSeries.clear();
|
|
947
|
-
}
|
|
948
|
-
/**
|
|
949
|
-
* Update chart
|
|
950
|
-
*/
|
|
951
|
-
update() {
|
|
952
|
-
if (!this.surface) return;
|
|
953
|
-
this.applyTheme();
|
|
954
|
-
this.surface.invalidateElement();
|
|
955
|
-
}
|
|
956
|
-
/**
|
|
957
|
-
* Destroy and clean up
|
|
958
|
-
*/
|
|
959
|
-
destroy() {
|
|
960
|
-
this.clearSeries();
|
|
961
|
-
super.destroy();
|
|
962
|
-
}
|
|
963
|
-
};
|
|
964
|
-
async function createAreaChart(container, config) {
|
|
965
|
-
const chart = new AreaChart(config);
|
|
966
|
-
await chart.init(container);
|
|
967
|
-
return chart;
|
|
968
|
-
}
|
|
969
|
-
function getSciChartTheme4(themeName) {
|
|
970
|
-
switch (themeName) {
|
|
971
|
-
case "light":
|
|
972
|
-
return new scichart.SciChartJSLightTheme();
|
|
973
|
-
case "dark":
|
|
974
|
-
case "modern":
|
|
975
|
-
case "midnight":
|
|
976
|
-
default:
|
|
977
|
-
return new scichart.SciChartJSDarkTheme();
|
|
978
|
-
}
|
|
979
|
-
}
|
|
980
|
-
var defaultColorStops = [
|
|
981
|
-
{ offset: 0, color: "#000080" },
|
|
982
|
-
// Dark blue
|
|
983
|
-
{ offset: 0.2, color: "#0000ff" },
|
|
984
|
-
// Blue
|
|
985
|
-
{ offset: 0.4, color: "#00ffff" },
|
|
986
|
-
// Cyan
|
|
987
|
-
{ offset: 0.6, color: "#00ff00" },
|
|
988
|
-
// Green
|
|
989
|
-
{ offset: 0.8, color: "#ffff00" },
|
|
990
|
-
// Yellow
|
|
991
|
-
{ offset: 1, color: "#ff0000" }
|
|
992
|
-
// Red
|
|
993
|
-
];
|
|
994
|
-
var HeatmapChart = class extends BaseChart {
|
|
995
|
-
constructor(config) {
|
|
996
|
-
super(config);
|
|
997
|
-
this.heatmapDataSeries = null;
|
|
998
|
-
this.heatmapSeries = null;
|
|
999
|
-
this.wasmContext = null;
|
|
1000
|
-
}
|
|
1001
|
-
/**
|
|
1002
|
-
* Create the SciChart surface for heatmap chart
|
|
1003
|
-
*/
|
|
1004
|
-
async createSurface() {
|
|
1005
|
-
if (!this.container) {
|
|
1006
|
-
throw new Error("Container not set");
|
|
1007
|
-
}
|
|
1008
|
-
const sciChartTheme = getSciChartTheme4(this.config.theme);
|
|
1009
|
-
if (!this.container.id) {
|
|
1010
|
-
this.container.id = this.id;
|
|
1011
|
-
}
|
|
1012
|
-
const { sciChartSurface, wasmContext } = await scichart.SciChartSurface.create(
|
|
1013
|
-
this.container,
|
|
1014
|
-
{
|
|
1015
|
-
theme: sciChartTheme
|
|
1016
|
-
}
|
|
1017
|
-
);
|
|
1018
|
-
this.surface = sciChartSurface;
|
|
1019
|
-
this.wasmContext = wasmContext;
|
|
1020
|
-
const xAxis = new scichart.NumericAxis(wasmContext, {
|
|
1021
|
-
axisTitle: this.config.xAxis?.title,
|
|
1022
|
-
drawMajorGridLines: this.config.xAxis?.gridLines?.show ?? false,
|
|
1023
|
-
drawMinorGridLines: false,
|
|
1024
|
-
axisTitleStyle: {
|
|
1025
|
-
fontSize: 14,
|
|
1026
|
-
fontFamily: this.theme.fontFamily,
|
|
1027
|
-
color: this.theme.axis?.titleColor
|
|
1028
|
-
},
|
|
1029
|
-
labelStyle: {
|
|
1030
|
-
fontSize: 12,
|
|
1031
|
-
fontFamily: this.theme.fontFamily,
|
|
1032
|
-
color: this.theme.axis?.labelColor
|
|
1033
|
-
},
|
|
1034
|
-
autoRange: scichart.EAutoRange.Always
|
|
1035
|
-
});
|
|
1036
|
-
const yAxis = new scichart.NumericAxis(wasmContext, {
|
|
1037
|
-
axisTitle: this.config.yAxis?.title,
|
|
1038
|
-
drawMajorGridLines: this.config.yAxis?.gridLines?.show ?? false,
|
|
1039
|
-
drawMinorGridLines: false,
|
|
1040
|
-
axisTitleStyle: {
|
|
1041
|
-
fontSize: 14,
|
|
1042
|
-
fontFamily: this.theme.fontFamily,
|
|
1043
|
-
color: this.theme.axis?.titleColor
|
|
1044
|
-
},
|
|
1045
|
-
labelStyle: {
|
|
1046
|
-
fontSize: 12,
|
|
1047
|
-
fontFamily: this.theme.fontFamily,
|
|
1048
|
-
color: this.theme.axis?.labelColor
|
|
1049
|
-
},
|
|
1050
|
-
autoRange: scichart.EAutoRange.Always
|
|
1051
|
-
});
|
|
1052
|
-
if (this.config.xAxis?.min !== void 0 && this.config.xAxis?.max !== void 0) {
|
|
1053
|
-
xAxis.visibleRange = new scichart.NumberRange(this.config.xAxis.min, this.config.xAxis.max);
|
|
1054
|
-
xAxis.autoRange = scichart.EAutoRange.Never;
|
|
1055
|
-
}
|
|
1056
|
-
if (this.config.yAxis?.min !== void 0 && this.config.yAxis?.max !== void 0) {
|
|
1057
|
-
yAxis.visibleRange = new scichart.NumberRange(this.config.yAxis.min, this.config.yAxis.max);
|
|
1058
|
-
yAxis.autoRange = scichart.EAutoRange.Never;
|
|
1059
|
-
}
|
|
1060
|
-
sciChartSurface.xAxes.add(xAxis);
|
|
1061
|
-
sciChartSurface.yAxes.add(yAxis);
|
|
1062
|
-
if (this.config.tooltip?.enabled !== false) {
|
|
1063
|
-
sciChartSurface.chartModifiers.add(
|
|
1064
|
-
new scichart.RolloverModifier({
|
|
1065
|
-
showTooltip: true,
|
|
1066
|
-
showAxisLabel: true
|
|
1067
|
-
})
|
|
1068
|
-
);
|
|
1069
|
-
}
|
|
1070
|
-
sciChartSurface.chartModifiers.add(new scichart.ZoomPanModifier());
|
|
1071
|
-
sciChartSurface.chartModifiers.add(new scichart.MouseWheelZoomModifier());
|
|
1072
|
-
this.addHeatmapData(this.config.zValues);
|
|
1073
|
-
}
|
|
1074
|
-
/**
|
|
1075
|
-
* Add heatmap data to the chart
|
|
320
|
+
* Add event listener
|
|
1076
321
|
*/
|
|
1077
|
-
|
|
1078
|
-
if (!this.
|
|
1079
|
-
|
|
1080
|
-
|
|
1081
|
-
|
|
1082
|
-
if (min === void 0 || max === void 0) {
|
|
1083
|
-
const flatValues = zValues.flat();
|
|
1084
|
-
min = min ?? Math.min(...flatValues);
|
|
1085
|
-
max = max ?? Math.max(...flatValues);
|
|
1086
|
-
}
|
|
1087
|
-
this.heatmapDataSeries = new scichart.UniformHeatmapDataSeries(wasmContext, {
|
|
1088
|
-
zValues,
|
|
1089
|
-
xStart: this.config.xStart ?? 0,
|
|
1090
|
-
xStep: this.config.xStep ?? 1,
|
|
1091
|
-
yStart: this.config.yStart ?? 0,
|
|
1092
|
-
yStep: this.config.yStep ?? 1
|
|
1093
|
-
});
|
|
1094
|
-
const colorStops = this.config.colorStops ?? defaultColorStops;
|
|
1095
|
-
this.heatmapSeries = new scichart.UniformHeatmapRenderableSeries(wasmContext, {
|
|
1096
|
-
dataSeries: this.heatmapDataSeries,
|
|
1097
|
-
colorMap: new scichart.HeatmapColorMap({
|
|
1098
|
-
minimum: min,
|
|
1099
|
-
maximum: max,
|
|
1100
|
-
gradientStops: colorStops
|
|
1101
|
-
})
|
|
1102
|
-
});
|
|
1103
|
-
this.surface.renderableSeries.add(this.heatmapSeries);
|
|
322
|
+
on(event, handler) {
|
|
323
|
+
if (!this.eventHandlers.has(event)) {
|
|
324
|
+
this.eventHandlers.set(event, /* @__PURE__ */ new Set());
|
|
325
|
+
}
|
|
326
|
+
this.eventHandlers.get(event).add(handler);
|
|
1104
327
|
}
|
|
1105
328
|
/**
|
|
1106
|
-
*
|
|
329
|
+
* Remove event listener
|
|
1107
330
|
*/
|
|
1108
|
-
|
|
1109
|
-
|
|
331
|
+
off(event, handler) {
|
|
332
|
+
const handlers = this.eventHandlers.get(event);
|
|
333
|
+
if (handlers) {
|
|
334
|
+
handlers.delete(handler);
|
|
335
|
+
}
|
|
1110
336
|
}
|
|
1111
337
|
/**
|
|
1112
|
-
*
|
|
338
|
+
* Emit an event
|
|
1113
339
|
*/
|
|
1114
|
-
|
|
1115
|
-
|
|
1116
|
-
|
|
1117
|
-
|
|
340
|
+
emit(event, data) {
|
|
341
|
+
const handlers = this.eventHandlers.get(event);
|
|
342
|
+
if (handlers) {
|
|
343
|
+
handlers.forEach((handler) => handler(data));
|
|
1118
344
|
}
|
|
1119
|
-
this.clearHeatmap();
|
|
1120
|
-
this.config.zValues = zValues;
|
|
1121
|
-
this.addHeatmapData(zValues);
|
|
1122
345
|
}
|
|
1123
346
|
/**
|
|
1124
|
-
*
|
|
347
|
+
* Destroy the chart and clean up resources
|
|
1125
348
|
*/
|
|
1126
|
-
|
|
1127
|
-
if (this.
|
|
1128
|
-
|
|
349
|
+
destroy() {
|
|
350
|
+
if (this.isDestroyed) return;
|
|
351
|
+
if (this.resizeObserver) {
|
|
352
|
+
this.resizeObserver.disconnect();
|
|
353
|
+
this.resizeObserver = null;
|
|
354
|
+
}
|
|
355
|
+
this.eventHandlers.clear();
|
|
356
|
+
if (this.surface) {
|
|
357
|
+
this.surface.delete();
|
|
358
|
+
this.surface = null;
|
|
359
|
+
}
|
|
360
|
+
if (this.container) {
|
|
361
|
+
this.container.innerHTML = "";
|
|
1129
362
|
}
|
|
363
|
+
this.isDestroyed = true;
|
|
364
|
+
this.isInitialized = false;
|
|
1130
365
|
}
|
|
1131
366
|
/**
|
|
1132
|
-
*
|
|
367
|
+
* Get current configuration
|
|
1133
368
|
*/
|
|
1134
|
-
|
|
1135
|
-
|
|
1136
|
-
if (this.heatmapSeries) {
|
|
1137
|
-
this.surface.renderableSeries.remove(this.heatmapSeries);
|
|
1138
|
-
this.heatmapSeries.delete();
|
|
1139
|
-
this.heatmapSeries = null;
|
|
1140
|
-
}
|
|
1141
|
-
if (this.heatmapDataSeries) {
|
|
1142
|
-
this.heatmapDataSeries.delete();
|
|
1143
|
-
this.heatmapDataSeries = null;
|
|
1144
|
-
}
|
|
369
|
+
getConfig() {
|
|
370
|
+
return { ...this.config };
|
|
1145
371
|
}
|
|
1146
372
|
/**
|
|
1147
|
-
*
|
|
373
|
+
* Get current theme
|
|
1148
374
|
*/
|
|
1149
|
-
|
|
1150
|
-
|
|
1151
|
-
this.applyTheme();
|
|
1152
|
-
this.surface.invalidateElement();
|
|
375
|
+
getTheme() {
|
|
376
|
+
return { ...this.theme };
|
|
1153
377
|
}
|
|
1154
378
|
/**
|
|
1155
|
-
*
|
|
379
|
+
* Check if chart is initialized
|
|
1156
380
|
*/
|
|
1157
|
-
|
|
1158
|
-
this.
|
|
1159
|
-
super.destroy();
|
|
381
|
+
isReady() {
|
|
382
|
+
return this.isInitialized && !this.isDestroyed;
|
|
1160
383
|
}
|
|
1161
384
|
};
|
|
1162
|
-
|
|
1163
|
-
const chart = new HeatmapChart(config);
|
|
1164
|
-
await chart.init(container);
|
|
1165
|
-
return chart;
|
|
1166
|
-
}
|
|
1167
|
-
var SCICHART_VERSION2 = "3.5.750";
|
|
385
|
+
var SCICHART_VERSION2 = "4.0.933";
|
|
1168
386
|
var sciChart3DConfigured = false;
|
|
1169
387
|
function ensureSciChart3DConfigured() {
|
|
1170
388
|
if (sciChart3DConfigured) return;
|
|
@@ -1174,15 +392,14 @@ function ensureSciChart3DConfigured() {
|
|
|
1174
392
|
} catch {
|
|
1175
393
|
try {
|
|
1176
394
|
scichart.SciChart3DSurface.configure({
|
|
1177
|
-
wasmUrl: `https://cdn.jsdelivr.net/npm/scichart@${SCICHART_VERSION2}/_wasm/scichart3d.wasm
|
|
1178
|
-
dataUrl: `https://cdn.jsdelivr.net/npm/scichart@${SCICHART_VERSION2}/_wasm/scichart3d.data`
|
|
395
|
+
wasmUrl: `https://cdn.jsdelivr.net/npm/scichart@${SCICHART_VERSION2}/_wasm/scichart3d.wasm`
|
|
1179
396
|
});
|
|
1180
397
|
sciChart3DConfigured = true;
|
|
1181
398
|
} catch {
|
|
1182
399
|
}
|
|
1183
400
|
}
|
|
1184
401
|
}
|
|
1185
|
-
var
|
|
402
|
+
var defaultColorStops = [
|
|
1186
403
|
{ offset: 0, color: "#1e3a8a" },
|
|
1187
404
|
// Dark blue
|
|
1188
405
|
{ offset: 0.25, color: "#3b82f6" },
|
|
@@ -1279,7 +496,7 @@ var Surface3DChart = class {
|
|
|
1279
496
|
xStep: this.config.xStep ?? 1,
|
|
1280
497
|
zStep: this.config.zStep ?? 1
|
|
1281
498
|
});
|
|
1282
|
-
const colorStops = this.config.colorStops ??
|
|
499
|
+
const colorStops = this.config.colorStops ?? defaultColorStops;
|
|
1283
500
|
const colorPalette = new scichart.GradientColorPalette(wasmContext, {
|
|
1284
501
|
gradientStops: colorStops
|
|
1285
502
|
});
|
|
@@ -1382,7 +599,7 @@ async function createSurface3DChart(container, config) {
|
|
|
1382
599
|
await chart.init(container);
|
|
1383
600
|
return chart;
|
|
1384
601
|
}
|
|
1385
|
-
var SCICHART_VERSION3 = "
|
|
602
|
+
var SCICHART_VERSION3 = "4.0.933";
|
|
1386
603
|
var sciChart3DConfigured2 = false;
|
|
1387
604
|
function ensureSciChart3DConfigured2() {
|
|
1388
605
|
if (sciChart3DConfigured2) return;
|
|
@@ -1392,8 +609,7 @@ function ensureSciChart3DConfigured2() {
|
|
|
1392
609
|
} catch {
|
|
1393
610
|
try {
|
|
1394
611
|
scichart.SciChart3DSurface.configure({
|
|
1395
|
-
wasmUrl: `https://cdn.jsdelivr.net/npm/scichart@${SCICHART_VERSION3}/_wasm/scichart3d.wasm
|
|
1396
|
-
dataUrl: `https://cdn.jsdelivr.net/npm/scichart@${SCICHART_VERSION3}/_wasm/scichart3d.data`
|
|
612
|
+
wasmUrl: `https://cdn.jsdelivr.net/npm/scichart@${SCICHART_VERSION3}/_wasm/scichart3d.wasm`
|
|
1397
613
|
});
|
|
1398
614
|
sciChart3DConfigured2 = true;
|
|
1399
615
|
} catch {
|
|
@@ -1641,18 +857,555 @@ async function createColumn3DChart(container, config) {
|
|
|
1641
857
|
await chart.init(container);
|
|
1642
858
|
return chart;
|
|
1643
859
|
}
|
|
860
|
+
var HORIZONTAL_RESOLUTION = 360;
|
|
861
|
+
var VERTICAL_SCALE_MAX_DEFAULT = 5e3;
|
|
862
|
+
var HORIZONTAL_RESOLUTION_MULTIPLIER = 1;
|
|
863
|
+
var RESOLUTION_CONFIG = {
|
|
864
|
+
UNI: {
|
|
865
|
+
HI: { VERTICAL_RESOLUTION: 256, VERTICAL_OFFSET: 0, MIN_PEAK_ZERO: true },
|
|
866
|
+
LO: { VERTICAL_RESOLUTION: 100, VERTICAL_OFFSET: 0, MIN_PEAK_ZERO: true }
|
|
867
|
+
},
|
|
868
|
+
BI: {
|
|
869
|
+
HI: { VERTICAL_RESOLUTION: 512, VERTICAL_OFFSET: 256, MIN_PEAK_ZERO: false },
|
|
870
|
+
LO: { VERTICAL_RESOLUTION: 200, VERTICAL_OFFSET: 100, MIN_PEAK_ZERO: false }
|
|
871
|
+
}
|
|
872
|
+
};
|
|
873
|
+
var defaultPRPDColorStops = [
|
|
874
|
+
{ offset: 0, color: "transparent" },
|
|
875
|
+
{ offset: 5e-3, color: "transparent" },
|
|
876
|
+
{ offset: 9e-3, color: "transparent" },
|
|
877
|
+
{ offset: 0.01, color: "CornflowerBlue" },
|
|
878
|
+
{ offset: 0.4, color: "DarkGreen" },
|
|
879
|
+
{ offset: 0.6, color: "Chartreuse" },
|
|
880
|
+
{ offset: 0.8, color: "Yellow" },
|
|
881
|
+
{ offset: 1, color: "Red" }
|
|
882
|
+
];
|
|
883
|
+
var createPRPDTheme = () => {
|
|
884
|
+
const theme = new SciChartJSLightTheme.SciChartJSLightTheme();
|
|
885
|
+
theme.sciChartBackground = "#f9f9f9";
|
|
886
|
+
theme.gridBackgroundBrush = "grey";
|
|
887
|
+
theme.axisBandsFill = "#dcdcdc";
|
|
888
|
+
theme.majorGridLineBrush = "#888888";
|
|
889
|
+
theme.minorGridLineBrush = "transparent";
|
|
890
|
+
return theme;
|
|
891
|
+
};
|
|
892
|
+
var createLegendTheme = () => {
|
|
893
|
+
const theme = new SciChartJSLightTheme.SciChartJSLightTheme();
|
|
894
|
+
theme.sciChartBackground = "#ffffff";
|
|
895
|
+
theme.gridBackgroundBrush = "#ffffff";
|
|
896
|
+
theme.axisBandsFill = "#ffffff";
|
|
897
|
+
theme.majorGridLineBrush = "transparent";
|
|
898
|
+
theme.minorGridLineBrush = "transparent";
|
|
899
|
+
return theme;
|
|
900
|
+
};
|
|
901
|
+
function getResolutionConfig(uniBiLabel, hiLoLabel, maxPeak, minPeak, isLowResolution) {
|
|
902
|
+
const cfg = isLowResolution ? RESOLUTION_CONFIG.UNI.HI : RESOLUTION_CONFIG?.[uniBiLabel]?.[hiLoLabel] ?? RESOLUTION_CONFIG.BI.HI;
|
|
903
|
+
const newMinPeak = cfg.MIN_PEAK_ZERO ? 0 : minPeak ?? -5e3;
|
|
904
|
+
const newMaxPeak = maxPeak ?? 5e3;
|
|
905
|
+
return {
|
|
906
|
+
verticalResolution: cfg.VERTICAL_RESOLUTION,
|
|
907
|
+
verticalOffset: cfg.VERTICAL_OFFSET,
|
|
908
|
+
newMinPeak,
|
|
909
|
+
newMaxPeak,
|
|
910
|
+
isUnipolar: uniBiLabel === "UNI" || isLowResolution
|
|
911
|
+
};
|
|
912
|
+
}
|
|
913
|
+
function getPhaseColumnIndex(phaseAngle, maxPhaseAngle) {
|
|
914
|
+
const maxPhase = maxPhaseAngle || 360;
|
|
915
|
+
if (maxPhase <= 0) return 0;
|
|
916
|
+
const clampedPhase = Math.min(Math.max(phaseAngle, 0), maxPhase);
|
|
917
|
+
const ratio = clampedPhase / maxPhase;
|
|
918
|
+
return Math.min(HORIZONTAL_RESOLUTION - 1, Math.floor(ratio * (HORIZONTAL_RESOLUTION - 1)));
|
|
919
|
+
}
|
|
920
|
+
function generateSineWaveData(startX, endX, amplitude, frequency = 1, phaseShift = 0, step = 1, offset = 0) {
|
|
921
|
+
const data = [];
|
|
922
|
+
for (let x = startX; x <= endX; x += step) {
|
|
923
|
+
const rad = (x - phaseShift) * Math.PI * frequency / 180;
|
|
924
|
+
const y = offset + amplitude * Math.sin(rad);
|
|
925
|
+
data.push([x, y]);
|
|
926
|
+
}
|
|
927
|
+
return data;
|
|
928
|
+
}
|
|
929
|
+
function buildZValues(data, scalingFactor, minPeak, maxPhaseAngle, verticalScaleMax, uniBiLabel, hiLoLabel, windowingData = [], isLowResolution) {
|
|
930
|
+
const { verticalResolution, verticalOffset, newMinPeak, newMaxPeak, isUnipolar } = getResolutionConfig(uniBiLabel, hiLoLabel, verticalScaleMax, minPeak, isLowResolution);
|
|
931
|
+
const zValues = Array.from(
|
|
932
|
+
{ length: verticalResolution },
|
|
933
|
+
() => new Array(HORIZONTAL_RESOLUTION).fill(0)
|
|
934
|
+
);
|
|
935
|
+
const vResolution = newMinPeak === 0 ? verticalResolution : verticalResolution / 2;
|
|
936
|
+
const multiplier = newMaxPeak * scalingFactor / vResolution;
|
|
937
|
+
let maxValue = 0;
|
|
938
|
+
let totalCount = 0;
|
|
939
|
+
const isInsideWindow = (phaseDeg, ampVal) => {
|
|
940
|
+
if (!windowingData?.length) return false;
|
|
941
|
+
return windowingData.some(
|
|
942
|
+
(w) => phaseDeg >= w.minPhase && phaseDeg <= w.maxPhase && ampVal >= w.minAmp && ampVal <= w.maxAmp
|
|
943
|
+
);
|
|
944
|
+
};
|
|
945
|
+
data?.forEach(([phase_angle, amplitude, count]) => {
|
|
946
|
+
const colIndex = getPhaseColumnIndex(phase_angle, maxPhaseAngle);
|
|
947
|
+
const scaledAmp = Math.floor(
|
|
948
|
+
(isUnipolar ? Math.abs(amplitude) : amplitude) * scalingFactor
|
|
949
|
+
);
|
|
950
|
+
if (isInsideWindow(phase_angle, scaledAmp)) {
|
|
951
|
+
return;
|
|
952
|
+
}
|
|
953
|
+
let rowIndex = Math.floor(scaledAmp / multiplier + verticalOffset);
|
|
954
|
+
rowIndex = Math.max(0, Math.min(verticalResolution - 1, rowIndex));
|
|
955
|
+
zValues[rowIndex][colIndex] += count;
|
|
956
|
+
if (Math.abs(scaledAmp) > Math.abs(maxValue)) maxValue = scaledAmp;
|
|
957
|
+
totalCount += count;
|
|
958
|
+
});
|
|
959
|
+
return {
|
|
960
|
+
zValues,
|
|
961
|
+
multiplier,
|
|
962
|
+
maxValue,
|
|
963
|
+
totalCount,
|
|
964
|
+
verticalResolution,
|
|
965
|
+
isUnipolar,
|
|
966
|
+
newMinPeak
|
|
967
|
+
};
|
|
968
|
+
}
|
|
969
|
+
var PRPDChart = class {
|
|
970
|
+
constructor(config) {
|
|
971
|
+
this.container = null;
|
|
972
|
+
// Root container (may contain sub-divs)
|
|
973
|
+
this.chartHost = null;
|
|
974
|
+
// Div where SciChartSurface is mounted
|
|
975
|
+
this.surface = null;
|
|
976
|
+
this.wasmContext = null;
|
|
977
|
+
this.isDestroyed = false;
|
|
978
|
+
// Chart components
|
|
979
|
+
this.heatmapDataSeries = null;
|
|
980
|
+
this.heatmapSeries = null;
|
|
981
|
+
this.heatmapColorMap = null;
|
|
982
|
+
this.heatmapLegend = null;
|
|
983
|
+
this.heatmapLegendDiv = null;
|
|
984
|
+
this.sineDataSeries = null;
|
|
985
|
+
this.sineLineSeries = null;
|
|
986
|
+
this.xAxis = null;
|
|
987
|
+
this.yAxis = null;
|
|
988
|
+
// Statistics
|
|
989
|
+
this.stats = { peakValue: 0, totalCount: 0 };
|
|
990
|
+
this.id = config.id ?? generateId("prpd");
|
|
991
|
+
this.config = {
|
|
992
|
+
scalingFactor: 1,
|
|
993
|
+
unitOfMeasurement: "mVp",
|
|
994
|
+
maxPeak: 5e3,
|
|
995
|
+
minPeak: -5e3,
|
|
996
|
+
maxPhaseAngle: 360,
|
|
997
|
+
resolutionLabel: { UniBi: "BI", HiLo: "HI" },
|
|
998
|
+
windowingData: [],
|
|
999
|
+
yAxisRange: 5e3,
|
|
1000
|
+
isLowResolution: false,
|
|
1001
|
+
showColorPalette: true,
|
|
1002
|
+
showSineWave: true,
|
|
1003
|
+
colorMin: 0,
|
|
1004
|
+
colorMax: 100,
|
|
1005
|
+
...config
|
|
1006
|
+
};
|
|
1007
|
+
}
|
|
1008
|
+
/**
|
|
1009
|
+
* Initialize the chart in the given container
|
|
1010
|
+
*/
|
|
1011
|
+
async init(container) {
|
|
1012
|
+
if (this.isDestroyed) {
|
|
1013
|
+
throw new Error("Cannot initialize a destroyed chart");
|
|
1014
|
+
}
|
|
1015
|
+
if (typeof container === "string") {
|
|
1016
|
+
const el = document.getElementById(container);
|
|
1017
|
+
if (!el) {
|
|
1018
|
+
throw new Error(`Container element "${container}" not found`);
|
|
1019
|
+
}
|
|
1020
|
+
this.container = el;
|
|
1021
|
+
} else {
|
|
1022
|
+
this.container = container;
|
|
1023
|
+
}
|
|
1024
|
+
if (!this.container.id) {
|
|
1025
|
+
this.container.id = this.id;
|
|
1026
|
+
}
|
|
1027
|
+
const chartGraph = this.container.querySelector(".chart-graph");
|
|
1028
|
+
this.chartHost = chartGraph ?? this.container;
|
|
1029
|
+
if (!this.chartHost.id) {
|
|
1030
|
+
this.chartHost.id = `${this.id}_host`;
|
|
1031
|
+
}
|
|
1032
|
+
await this.createSurface();
|
|
1033
|
+
}
|
|
1034
|
+
/**
|
|
1035
|
+
* Create the SciChart surface
|
|
1036
|
+
*/
|
|
1037
|
+
async createSurface() {
|
|
1038
|
+
if (!this.container || !this.chartHost) {
|
|
1039
|
+
throw new Error("Container not set");
|
|
1040
|
+
}
|
|
1041
|
+
const theme = createPRPDTheme();
|
|
1042
|
+
const { sciChartSurface, wasmContext } = await scichart.SciChartSurface.create(
|
|
1043
|
+
this.chartHost,
|
|
1044
|
+
{ theme }
|
|
1045
|
+
);
|
|
1046
|
+
this.surface = sciChartSurface;
|
|
1047
|
+
this.wasmContext = wasmContext;
|
|
1048
|
+
const verticalScaleMax = this.config.maxPeak || VERTICAL_SCALE_MAX_DEFAULT;
|
|
1049
|
+
const { zValues, multiplier, maxValue, totalCount, verticalResolution, isUnipolar } = buildZValues(
|
|
1050
|
+
this.config.data,
|
|
1051
|
+
this.config.scalingFactor,
|
|
1052
|
+
this.config.minPeak,
|
|
1053
|
+
this.config.maxPhaseAngle,
|
|
1054
|
+
verticalScaleMax,
|
|
1055
|
+
this.config.resolutionLabel?.UniBi ?? "BI",
|
|
1056
|
+
this.config.resolutionLabel?.HiLo ?? "HI",
|
|
1057
|
+
this.config.windowingData,
|
|
1058
|
+
this.config.isLowResolution
|
|
1059
|
+
);
|
|
1060
|
+
this.stats = { peakValue: maxValue, totalCount };
|
|
1061
|
+
const yAxisRange = this.config.yAxisRange || verticalScaleMax;
|
|
1062
|
+
this.xAxis = new scichart.NumericAxis(wasmContext, {
|
|
1063
|
+
autoRange: scichart.EAutoRange.Never,
|
|
1064
|
+
labelFormat: scichart.ENumericFormat.Decimal,
|
|
1065
|
+
labelPrecision: 0,
|
|
1066
|
+
labelPostfix: "\xB0",
|
|
1067
|
+
minorDelta: 2,
|
|
1068
|
+
majorDelta: 45,
|
|
1069
|
+
drawMajorBands: true,
|
|
1070
|
+
autoTicks: false,
|
|
1071
|
+
axisAlignment: scichart.EAxisAlignment.Bottom,
|
|
1072
|
+
axisTitle: "Phase Angle (\xB0)",
|
|
1073
|
+
axisTitleStyle: {
|
|
1074
|
+
fontSize: 14,
|
|
1075
|
+
fontWeight: "bold",
|
|
1076
|
+
color: "black"
|
|
1077
|
+
},
|
|
1078
|
+
visibleRange: new scichart.NumberRange(0, 360),
|
|
1079
|
+
visibleRangeLimit: new scichart.NumberRange(0, 360)
|
|
1080
|
+
});
|
|
1081
|
+
const yRange = isUnipolar ? new scichart.NumberRange(0, yAxisRange) : new scichart.NumberRange(-yAxisRange, yAxisRange);
|
|
1082
|
+
this.yAxis = new scichart.NumericAxis(wasmContext, {
|
|
1083
|
+
autoRange: scichart.EAutoRange.Never,
|
|
1084
|
+
labelFormat: scichart.ENumericFormat.Decimal,
|
|
1085
|
+
labelPrecision: 0,
|
|
1086
|
+
drawMajorBands: true,
|
|
1087
|
+
axisAlignment: scichart.EAxisAlignment.Right,
|
|
1088
|
+
axisTitle: `Amplitude (${this.config.unitOfMeasurement})`,
|
|
1089
|
+
axisTitleStyle: {
|
|
1090
|
+
fontSize: 14,
|
|
1091
|
+
fontWeight: "bold",
|
|
1092
|
+
color: "black",
|
|
1093
|
+
rotation: 270
|
|
1094
|
+
},
|
|
1095
|
+
visibleRange: yRange,
|
|
1096
|
+
visibleRangeLimit: yRange
|
|
1097
|
+
});
|
|
1098
|
+
sciChartSurface.xAxes.add(this.xAxis);
|
|
1099
|
+
sciChartSurface.yAxes.add(this.yAxis);
|
|
1100
|
+
this.createHeatmap(zValues, multiplier, verticalResolution, isUnipolar);
|
|
1101
|
+
if (this.config.showSineWave) {
|
|
1102
|
+
this.createSineWave(yAxisRange, isUnipolar);
|
|
1103
|
+
}
|
|
1104
|
+
const cursorModifier = new scichart.CursorModifier();
|
|
1105
|
+
cursorModifier.axisLabelFill = "#FFFFFF";
|
|
1106
|
+
cursorModifier.axisLabelStroke = "#000000";
|
|
1107
|
+
sciChartSurface.chartModifiers.add(
|
|
1108
|
+
cursorModifier,
|
|
1109
|
+
new scichart.RubberBandXyZoomModifier(),
|
|
1110
|
+
new scichart.ZoomExtentsModifier()
|
|
1111
|
+
);
|
|
1112
|
+
if (this.config.showColorPalette) {
|
|
1113
|
+
await this.createHeatmapLegend();
|
|
1114
|
+
}
|
|
1115
|
+
this.onStatsChange?.(this.stats);
|
|
1116
|
+
}
|
|
1117
|
+
createHeatmap(zValues, multiplier, verticalResolution, isUnipolar) {
|
|
1118
|
+
if (!this.surface || !this.wasmContext) return;
|
|
1119
|
+
const colorStops = this.config.colorStops ?? defaultPRPDColorStops;
|
|
1120
|
+
this.heatmapColorMap = new scichart.HeatmapColorMap({
|
|
1121
|
+
minimum: this.config.colorMin ?? 0,
|
|
1122
|
+
maximum: this.config.colorMax ?? 100,
|
|
1123
|
+
gradientStops: colorStops
|
|
1124
|
+
});
|
|
1125
|
+
this.heatmapDataSeries = new scichart.UniformHeatmapDataSeries(this.wasmContext, {
|
|
1126
|
+
zValues,
|
|
1127
|
+
xStart: 0,
|
|
1128
|
+
xStep: HORIZONTAL_RESOLUTION_MULTIPLIER,
|
|
1129
|
+
yStart: isUnipolar ? 0 : -1 * verticalResolution * multiplier / 2,
|
|
1130
|
+
yStep: multiplier
|
|
1131
|
+
});
|
|
1132
|
+
this.heatmapSeries = new scichart.UniformHeatmapRenderableSeries(this.wasmContext, {
|
|
1133
|
+
dataSeries: this.heatmapDataSeries,
|
|
1134
|
+
colorMap: this.heatmapColorMap
|
|
1135
|
+
});
|
|
1136
|
+
this.surface.renderableSeries.add(this.heatmapSeries);
|
|
1137
|
+
}
|
|
1138
|
+
createSineWave(yAxisRange, isUnipolar) {
|
|
1139
|
+
if (!this.surface || !this.wasmContext) return;
|
|
1140
|
+
const sineAmplitude = isUnipolar ? yAxisRange / 2 : yAxisRange;
|
|
1141
|
+
const sineOffset = isUnipolar ? yAxisRange / 2 : 0;
|
|
1142
|
+
const sineWaveData = generateSineWaveData(0, 360, sineAmplitude, 1, 0, 1, sineOffset);
|
|
1143
|
+
this.sineDataSeries = new scichart.XyDataSeries(this.wasmContext);
|
|
1144
|
+
sineWaveData.forEach(([x, y]) => this.sineDataSeries.append(x, y));
|
|
1145
|
+
this.sineLineSeries = new scichart.FastLineRenderableSeries(this.wasmContext, {
|
|
1146
|
+
dataSeries: this.sineDataSeries,
|
|
1147
|
+
stroke: "Black",
|
|
1148
|
+
strokeThickness: 3
|
|
1149
|
+
});
|
|
1150
|
+
this.surface.renderableSeries.add(this.sineLineSeries);
|
|
1151
|
+
}
|
|
1152
|
+
async createHeatmapLegend() {
|
|
1153
|
+
if (!this.container || !this.heatmapColorMap) return;
|
|
1154
|
+
this.clearHeatmapLegend();
|
|
1155
|
+
let div = this.container.querySelector(".heatmap-chart");
|
|
1156
|
+
if (!div) {
|
|
1157
|
+
div = document.createElement("div");
|
|
1158
|
+
div.className = "heatmap-chart";
|
|
1159
|
+
div.style.position = "absolute";
|
|
1160
|
+
div.style.top = "40px";
|
|
1161
|
+
div.style.left = "0px";
|
|
1162
|
+
div.style.bottom = "40px";
|
|
1163
|
+
div.style.width = "65px";
|
|
1164
|
+
div.style.pointerEvents = "none";
|
|
1165
|
+
this.container.appendChild(div);
|
|
1166
|
+
}
|
|
1167
|
+
if (!div.id) {
|
|
1168
|
+
div.id = `${this.id}_legend`;
|
|
1169
|
+
}
|
|
1170
|
+
this.heatmapLegendDiv = div;
|
|
1171
|
+
const min = this.config.colorMin ?? 0;
|
|
1172
|
+
const max = this.config.colorMax ?? 100;
|
|
1173
|
+
const { heatmapLegend } = await scichart.HeatmapLegend.create(div, {
|
|
1174
|
+
theme: createLegendTheme(),
|
|
1175
|
+
yAxisOptions: {
|
|
1176
|
+
visibleRange: new scichart.NumberRange(min, max),
|
|
1177
|
+
majorDelta: (max - min) / 5,
|
|
1178
|
+
minorDelta: (max - min) / 10,
|
|
1179
|
+
labelFormat: scichart.ENumericFormat.Decimal,
|
|
1180
|
+
labelPrecision: 0,
|
|
1181
|
+
labelPadding: 6,
|
|
1182
|
+
axisTitleGap: 8,
|
|
1183
|
+
labelStyle: { fontSize: 12, color: "#A0A0A0" },
|
|
1184
|
+
majorTickLineStyle: {
|
|
1185
|
+
color: "#A0A0A0",
|
|
1186
|
+
tickSize: 8,
|
|
1187
|
+
strokeThickness: 1
|
|
1188
|
+
},
|
|
1189
|
+
minorTickLineStyle: {
|
|
1190
|
+
color: "gray",
|
|
1191
|
+
tickSize: 5,
|
|
1192
|
+
strokeThickness: 1
|
|
1193
|
+
},
|
|
1194
|
+
axisBorder: {
|
|
1195
|
+
borderLeft: 0,
|
|
1196
|
+
borderRight: 0,
|
|
1197
|
+
borderTop: 0,
|
|
1198
|
+
borderBottom: 0,
|
|
1199
|
+
color: "transparent"
|
|
1200
|
+
}
|
|
1201
|
+
},
|
|
1202
|
+
colorMap: this.heatmapColorMap
|
|
1203
|
+
});
|
|
1204
|
+
this.heatmapLegend = heatmapLegend;
|
|
1205
|
+
}
|
|
1206
|
+
clearHeatmapLegend() {
|
|
1207
|
+
if (this.heatmapLegend) {
|
|
1208
|
+
try {
|
|
1209
|
+
this.heatmapLegend.delete();
|
|
1210
|
+
} catch (e) {
|
|
1211
|
+
}
|
|
1212
|
+
this.heatmapLegend = null;
|
|
1213
|
+
}
|
|
1214
|
+
if (this.heatmapLegendDiv) {
|
|
1215
|
+
this.heatmapLegendDiv.remove();
|
|
1216
|
+
this.heatmapLegendDiv = null;
|
|
1217
|
+
}
|
|
1218
|
+
}
|
|
1219
|
+
/**
|
|
1220
|
+
* Update chart with new data
|
|
1221
|
+
*/
|
|
1222
|
+
updateData(data) {
|
|
1223
|
+
this.config.data = data;
|
|
1224
|
+
this.refresh();
|
|
1225
|
+
}
|
|
1226
|
+
/**
|
|
1227
|
+
* Update resolution label (UNI/BI, HI/LO)
|
|
1228
|
+
*/
|
|
1229
|
+
setResolutionLabel(label) {
|
|
1230
|
+
this.config.resolutionLabel = label;
|
|
1231
|
+
this.refresh();
|
|
1232
|
+
}
|
|
1233
|
+
/**
|
|
1234
|
+
* Update windowing data
|
|
1235
|
+
*/
|
|
1236
|
+
setWindowingData(windowingData) {
|
|
1237
|
+
this.config.windowingData = windowingData;
|
|
1238
|
+
this.refresh();
|
|
1239
|
+
}
|
|
1240
|
+
/**
|
|
1241
|
+
* Update Y-axis range
|
|
1242
|
+
*/
|
|
1243
|
+
setYAxisRange(range) {
|
|
1244
|
+
this.config.yAxisRange = range;
|
|
1245
|
+
this.refresh();
|
|
1246
|
+
}
|
|
1247
|
+
/**
|
|
1248
|
+
* Set stats change callback
|
|
1249
|
+
*/
|
|
1250
|
+
onStats(callback) {
|
|
1251
|
+
this.onStatsChange = callback;
|
|
1252
|
+
}
|
|
1253
|
+
/**
|
|
1254
|
+
* Get current statistics
|
|
1255
|
+
*/
|
|
1256
|
+
getStats() {
|
|
1257
|
+
return { ...this.stats };
|
|
1258
|
+
}
|
|
1259
|
+
/**
|
|
1260
|
+
* Refresh the chart with current configuration
|
|
1261
|
+
*/
|
|
1262
|
+
refresh() {
|
|
1263
|
+
if (!this.surface || !this.wasmContext) return;
|
|
1264
|
+
const verticalScaleMax = this.config.maxPeak || VERTICAL_SCALE_MAX_DEFAULT;
|
|
1265
|
+
const yAxisRange = this.config.yAxisRange || verticalScaleMax;
|
|
1266
|
+
const { zValues, multiplier, maxValue, totalCount, verticalResolution, isUnipolar } = buildZValues(
|
|
1267
|
+
this.config.data,
|
|
1268
|
+
this.config.scalingFactor,
|
|
1269
|
+
this.config.minPeak,
|
|
1270
|
+
this.config.maxPhaseAngle,
|
|
1271
|
+
verticalScaleMax,
|
|
1272
|
+
this.config.resolutionLabel?.UniBi ?? "BI",
|
|
1273
|
+
this.config.resolutionLabel?.HiLo ?? "HI",
|
|
1274
|
+
this.config.windowingData,
|
|
1275
|
+
this.config.isLowResolution
|
|
1276
|
+
);
|
|
1277
|
+
this.stats = { peakValue: maxValue, totalCount };
|
|
1278
|
+
if (this.yAxis) {
|
|
1279
|
+
const yRange = isUnipolar ? new scichart.NumberRange(0, yAxisRange) : new scichart.NumberRange(-yAxisRange, yAxisRange);
|
|
1280
|
+
this.yAxis.visibleRange = yRange;
|
|
1281
|
+
this.yAxis.visibleRangeLimit = yRange;
|
|
1282
|
+
}
|
|
1283
|
+
if (this.heatmapDataSeries) {
|
|
1284
|
+
const needNewDs = this.heatmapDataSeries.arrayHeight !== verticalResolution || this.heatmapDataSeries.arrayWidth !== HORIZONTAL_RESOLUTION;
|
|
1285
|
+
if (needNewDs) {
|
|
1286
|
+
if (this.heatmapSeries) {
|
|
1287
|
+
this.surface.renderableSeries.remove(this.heatmapSeries);
|
|
1288
|
+
this.heatmapSeries.delete();
|
|
1289
|
+
}
|
|
1290
|
+
this.heatmapDataSeries.delete();
|
|
1291
|
+
this.heatmapDataSeries = new scichart.UniformHeatmapDataSeries(this.wasmContext, {
|
|
1292
|
+
zValues,
|
|
1293
|
+
xStart: 0,
|
|
1294
|
+
xStep: HORIZONTAL_RESOLUTION_MULTIPLIER,
|
|
1295
|
+
yStart: isUnipolar ? 0 : -1 * verticalResolution * multiplier / 2,
|
|
1296
|
+
yStep: multiplier
|
|
1297
|
+
});
|
|
1298
|
+
this.heatmapSeries = new scichart.UniformHeatmapRenderableSeries(this.wasmContext, {
|
|
1299
|
+
dataSeries: this.heatmapDataSeries,
|
|
1300
|
+
colorMap: this.heatmapColorMap
|
|
1301
|
+
});
|
|
1302
|
+
this.surface.renderableSeries.add(this.heatmapSeries);
|
|
1303
|
+
} else {
|
|
1304
|
+
if (typeof this.heatmapDataSeries.setZValues === "function") {
|
|
1305
|
+
this.heatmapDataSeries.setZValues(zValues);
|
|
1306
|
+
} else {
|
|
1307
|
+
this.heatmapDataSeries.zValues = zValues;
|
|
1308
|
+
}
|
|
1309
|
+
this.heatmapDataSeries.yStart = isUnipolar ? 0 : -1 * verticalResolution * multiplier / 2;
|
|
1310
|
+
this.heatmapDataSeries.yStep = multiplier;
|
|
1311
|
+
}
|
|
1312
|
+
}
|
|
1313
|
+
if (this.sineDataSeries && this.config.showSineWave) {
|
|
1314
|
+
this.sineDataSeries.clear();
|
|
1315
|
+
const sineAmplitude = isUnipolar ? yAxisRange / 2 : yAxisRange;
|
|
1316
|
+
const sineOffset = isUnipolar ? yAxisRange / 2 : 0;
|
|
1317
|
+
const sineWaveData = generateSineWaveData(0, 360, sineAmplitude, 1, 0, 1, sineOffset);
|
|
1318
|
+
sineWaveData.forEach(([x, y]) => this.sineDataSeries.append(x, y));
|
|
1319
|
+
}
|
|
1320
|
+
this.surface.invalidateElement();
|
|
1321
|
+
this.onStatsChange?.(this.stats);
|
|
1322
|
+
}
|
|
1323
|
+
/**
|
|
1324
|
+
* Set chart options
|
|
1325
|
+
*/
|
|
1326
|
+
setOptions(options) {
|
|
1327
|
+
this.config = { ...this.config, ...options };
|
|
1328
|
+
this.refresh();
|
|
1329
|
+
}
|
|
1330
|
+
/**
|
|
1331
|
+
* Reset zoom to full extent
|
|
1332
|
+
*/
|
|
1333
|
+
resetZoom() {
|
|
1334
|
+
if (!this.surface) return;
|
|
1335
|
+
this.surface.zoomExtents();
|
|
1336
|
+
}
|
|
1337
|
+
/**
|
|
1338
|
+
* Export chart as image
|
|
1339
|
+
*/
|
|
1340
|
+
async exportImage(format = "png") {
|
|
1341
|
+
if (!this.container) {
|
|
1342
|
+
throw new Error("Chart not initialized");
|
|
1343
|
+
}
|
|
1344
|
+
const canvas = this.container.querySelector("canvas");
|
|
1345
|
+
if (!canvas) {
|
|
1346
|
+
throw new Error("Canvas not found");
|
|
1347
|
+
}
|
|
1348
|
+
const mimeType = format === "jpeg" ? "image/jpeg" : "image/png";
|
|
1349
|
+
return canvas.toDataURL(mimeType);
|
|
1350
|
+
}
|
|
1351
|
+
/**
|
|
1352
|
+
* Get current configuration
|
|
1353
|
+
*/
|
|
1354
|
+
getConfig() {
|
|
1355
|
+
return { ...this.config };
|
|
1356
|
+
}
|
|
1357
|
+
/**
|
|
1358
|
+
* Check if chart is ready
|
|
1359
|
+
*/
|
|
1360
|
+
isReady() {
|
|
1361
|
+
return this.surface !== null && !this.isDestroyed;
|
|
1362
|
+
}
|
|
1363
|
+
/**
|
|
1364
|
+
* Destroy and clean up
|
|
1365
|
+
*/
|
|
1366
|
+
destroy() {
|
|
1367
|
+
if (this.isDestroyed) return;
|
|
1368
|
+
this.clearHeatmapLegend();
|
|
1369
|
+
if (this.sineLineSeries && this.surface) {
|
|
1370
|
+
this.surface.renderableSeries.remove(this.sineLineSeries);
|
|
1371
|
+
this.sineLineSeries.delete();
|
|
1372
|
+
this.sineLineSeries = null;
|
|
1373
|
+
}
|
|
1374
|
+
if (this.sineDataSeries) {
|
|
1375
|
+
this.sineDataSeries.delete();
|
|
1376
|
+
this.sineDataSeries = null;
|
|
1377
|
+
}
|
|
1378
|
+
if (this.heatmapSeries && this.surface) {
|
|
1379
|
+
this.surface.renderableSeries.remove(this.heatmapSeries);
|
|
1380
|
+
this.heatmapSeries.delete();
|
|
1381
|
+
this.heatmapSeries = null;
|
|
1382
|
+
}
|
|
1383
|
+
if (this.heatmapDataSeries) {
|
|
1384
|
+
this.heatmapDataSeries.delete();
|
|
1385
|
+
this.heatmapDataSeries = null;
|
|
1386
|
+
}
|
|
1387
|
+
if (this.surface) {
|
|
1388
|
+
this.surface.delete();
|
|
1389
|
+
this.surface = null;
|
|
1390
|
+
}
|
|
1391
|
+
this.isDestroyed = true;
|
|
1392
|
+
}
|
|
1393
|
+
};
|
|
1394
|
+
async function createPRPDChart(container, config) {
|
|
1395
|
+
const chart = new PRPDChart(config);
|
|
1396
|
+
await chart.init(container);
|
|
1397
|
+
return chart;
|
|
1398
|
+
}
|
|
1644
1399
|
var VERSION = "0.1.1";
|
|
1645
|
-
var SCICHART_VERSION4 = "
|
|
1400
|
+
var SCICHART_VERSION4 = "4.0.933";
|
|
1646
1401
|
var DEFAULT_WASM_URL = `https://cdn.jsdelivr.net/npm/scichart@${SCICHART_VERSION4}/_wasm/scichart2d.wasm`;
|
|
1647
|
-
var DEFAULT_DATA_URL = `https://cdn.jsdelivr.net/npm/scichart@${SCICHART_VERSION4}/_wasm/scichart2d.data`;
|
|
1648
1402
|
var isConfigured = false;
|
|
1649
1403
|
function autoConfigureSciChart() {
|
|
1650
1404
|
if (isConfigured) return;
|
|
1651
1405
|
try {
|
|
1652
|
-
const { SciChartSurface:
|
|
1653
|
-
|
|
1654
|
-
wasmUrl: DEFAULT_WASM_URL
|
|
1655
|
-
dataUrl: DEFAULT_DATA_URL
|
|
1406
|
+
const { SciChartSurface: SciChartSurface4 } = chunkKATRK3C3_js.__require("scichart");
|
|
1407
|
+
SciChartSurface4.configure({
|
|
1408
|
+
wasmUrl: DEFAULT_WASM_URL
|
|
1656
1409
|
});
|
|
1657
1410
|
isConfigured = true;
|
|
1658
1411
|
} catch {
|
|
@@ -1661,10 +1414,9 @@ function autoConfigureSciChart() {
|
|
|
1661
1414
|
autoConfigureSciChart();
|
|
1662
1415
|
function configureSciChart(options) {
|
|
1663
1416
|
try {
|
|
1664
|
-
const { SciChartSurface:
|
|
1665
|
-
|
|
1666
|
-
wasmUrl: options.wasmUrl || DEFAULT_WASM_URL
|
|
1667
|
-
dataUrl: options.dataUrl || DEFAULT_DATA_URL
|
|
1417
|
+
const { SciChartSurface: SciChartSurface4 } = chunkKATRK3C3_js.__require("scichart");
|
|
1418
|
+
SciChartSurface4.configure({
|
|
1419
|
+
wasmUrl: options.wasmUrl || DEFAULT_WASM_URL
|
|
1668
1420
|
});
|
|
1669
1421
|
isConfigured = true;
|
|
1670
1422
|
} catch {
|
|
@@ -1699,22 +1451,16 @@ Object.defineProperty(exports, "SciChartSurface", {
|
|
|
1699
1451
|
enumerable: true,
|
|
1700
1452
|
get: function () { return scichart.SciChartSurface; }
|
|
1701
1453
|
});
|
|
1702
|
-
exports.AreaChart = AreaChart;
|
|
1703
|
-
exports.BarChart = BarChart;
|
|
1704
1454
|
exports.BaseChart = BaseChart;
|
|
1705
1455
|
exports.Column3DChart = Column3DChart;
|
|
1706
|
-
exports.
|
|
1707
|
-
exports.LineChart = LineChart;
|
|
1456
|
+
exports.PRPDChart = PRPDChart;
|
|
1708
1457
|
exports.Surface3DChart = Surface3DChart;
|
|
1709
1458
|
exports.VERSION = VERSION;
|
|
1710
1459
|
exports.calculateDataRange = calculateDataRange;
|
|
1711
1460
|
exports.clamp = clamp;
|
|
1712
1461
|
exports.configureSciChart = configureSciChart;
|
|
1713
|
-
exports.createAreaChart = createAreaChart;
|
|
1714
|
-
exports.createBarChart = createBarChart;
|
|
1715
1462
|
exports.createColumn3DChart = createColumn3DChart;
|
|
1716
|
-
exports.
|
|
1717
|
-
exports.createLineChart = createLineChart;
|
|
1463
|
+
exports.createPRPDChart = createPRPDChart;
|
|
1718
1464
|
exports.createSurface3DChart = createSurface3DChart;
|
|
1719
1465
|
exports.debounce = debounce;
|
|
1720
1466
|
exports.deepMerge = deepMerge;
|