This is a simple tutorial which simulates real-time monitoring using the Time Series Widget.
# Real-Time Monitoring
import { Group } from "@int/geotoolkit/scene/Group.ts";
import { Rect } from "@int/geotoolkit/util/Rect.ts";
import { TimeSeriesWidget } from "@int/geotoolkit/widgets/TimeSeriesWidget.ts";
import { FillDirection } from "@int/geotoolkit/widgets/timeseries/FillDirection.ts";
import { FillType } from "@int/geotoolkit/widgets/timeseries/FillType.ts";
import { Plot } from "@int/geotoolkit/plot/Plot.ts";
import { KnownColors } from "@int/geotoolkit/util/ColorUtil.ts";
import { Range } from "@int/geotoolkit/util/Range.ts";
import { PatternFactory } from "@int/geotoolkit/attributes/PatternFactory.ts";
import { DataTable } from "@int/geotoolkit/data/DataTable.ts";
import { DataTableView } from "@int/geotoolkit/data/DataTableView.ts";
import { data } from "/src/code/TimeSeries/data.ts";
let interval;
function createScene(canvas) {
const MAX_INDEX = 1e3;
const startDate = new Date().getTime();
const data1 = data[0];
const data2 = data[1];
const data3 = data[2];
const MAX_DATA_LENGTH = 350;
let index = 0;
let counter = 0;
const dataTables = [
getDataTableView([], "", [], ""),
getDataTableView([], "", [], ""),
getDataTableView([], "", [], "")
];
const colors = [KnownColors.Orange, KnownColors.Blue, KnownColors.Green];
const names = ["CALI", "DLT", "GR"];
const units = ["INS", "US/FT", "API"];
const customPattern = PatternFactory.getInstance().createPattern("data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAADAAAAAQCAYAAABQrvyxAAAABGdBTUEAALGPC/xhBQAAAAlwSFlzAAAScwAAEnMBjCK5BwAAABp0RVh0U29mdHdhcmUAUGFpbnQuTkVUIHYzLjUuMTAw9HKhAAAAo0lEQVRIS81WQQ6AIAzj/5/GaAIq26DVQDmYYEJ1XVtGyjmn8qR0Lu93dq3Am+K/FlFwq/EXgfanbBFKvCm+ZyePWEQW3fsbj/pcZZG2oUZthIDSIiOL1xBHRBiJvW/Mxg8JIAop9xgC7AnUFr8a/yKwa1B7CodTmO2kKujuIGOvFrODCimABpFVZnZGqFNox4zABFQej+xcm4lYR+lxbxI/SR1oUFAhMA7PXAAAAABJRU5ErkJggg==");
const fillStyles = [
"rgba(21,101,192,0.5)",
"rgba(239,108,0,0.5)",
"rgba(253,216,53,0.25)",
{
"color": "rgba(21,101,192,0.25)",
"pattern": customPattern,
"foreground": "rgba(21,101,192,0.5)"
}
];
function getDataTableView(values, valueUnit, indices, indexUnit) {
const dataTable = new DataTable({
"cols": [
{ "type": "number", "data": indices.slice() },
{ "type": "number", "data": values.slice() }
]
});
dataTable.getColumn(0).setUnit(indexUnit);
dataTable.getColumn(1).setUnit(valueUnit);
const dataTableView = new DataTableView(dataTable);
return {
"datatable": dataTable,
"datatableview": dataTableView
};
}
function configTools(widget2) {
widget2.getToolByName("picking").setEnabled(false);
widget2.getToolByName("cursor").setEnabled(false);
widget2.getToolByName("scroll").setEnabled(false);
widget2.disconnectTool(widget2.getToolByName("picking"));
widget2.disconnectTool(widget2.getToolByName("cursor"));
widget2.disconnectTool(widget2.getToolByName("scroll"));
}
function addCurves(widget2) {
dataTables.forEach((dataTable, index2) => {
widget2.addCurve({
"name": names[index2],
"uri": "//test//" + names[index2].toLowerCase(),
"data": dataTable["datatableview"],
"properties": {
"autoscale": true,
"unit": units[index2],
"linestyle": {
"color": colors[index2],
"width": 1.5
}
}
});
});
}
function addFills(widget2) {
widget2.addFill(
"//test//dlt",
"//test//gr",
fillStyles[0],
FillType.CurveToCurve,
FillDirection.Top
);
widget2.addFill(
"//test//dlt",
"//test//gr",
fillStyles[3],
FillType.CurveToCurve,
FillDirection.Bottom
);
}
function createRealtimeWidget() {
const options = {
"model": new Group().setModelLimits(new Rect(startDate - 5 * 60 * 1e3, 0, startDate, 1)),
"title": {
"text": "Real-time Monitoring"
},
"legends": {
"height": 25
},
"scrollbar": {
"visible": false
},
"viewcache": true,
"intervalbuttons": {
"visible": true,
"intervals": {
"30s": 1e3 * 30,
"1m": 1e3 * 60,
"5m": 1e3 * 60 * 5
}
}
};
return new TimeSeriesWidget(options);
}
const range = new Range(startDate - 5 * 60 * 1e3, startDate);
const widget = createRealtimeWidget();
configTools(widget);
addCurves(widget);
addFills(widget);
widget.setVisibleRange(range);
const updateHandler = () => {
const _index = startDate + counter * 1e3;
const cd1 = data1[index];
const cd2 = data2[index];
const cd3 = data3[index];
const currentRange = widget.getVisibleRange();
range.setRange(_index - 5 * 60 * 1e3, _index);
dataTables[0]["datatable"].addRow([_index, cd1]);
dataTables[1]["datatable"].addRow([_index, cd2]);
dataTables[2]["datatable"].addRow([_index, cd3]);
dataTables.forEach((dataTable) => {
const length = dataTable["datatableview"].getNumberOfRows();
if (length > MAX_DATA_LENGTH) {
dataTable["datatable"].removeRows(0);
}
});
widget.setRange(range);
widget.setVisibleRange(new Range(_index - (currentRange.getHigh() - currentRange.getLow()), _index));
++index;
if (index >= MAX_INDEX) {
index = 0;
}
++counter;
};
interval = window.setInterval(updateHandler, 100);
return new Plot({
"canvaselement": canvas,
"root": widget
});
}
function dispose() {
clearInterval(interval);
}
export { createScene, dispose };
createScene(document.querySelector('[ref="plot"]'));