UNPKG

50.1 kBJavaScriptView Raw
1import { a as __extends, _ as __assign } from './tslib.es6-863e3717.js';
2import { U as Utils } from './Utils-5f9f1f09.js';
3import { event, select, mouse } from 'd3';
4import { G as Grid } from './Grid-545284f2.js';
5import { E as EllipsisMenu } from './EllipsisMenu-8802ae90.js';
6import { C as ChartComponent } from './ChartComponent-63d99ac0.js';
7import { C as ChartDataOptions } from './ChartDataOptions-a1b69faa.js';
8import { L as LineChart } from './LineChart-a4a8bc66.js';
9import { T as TimezonePicker } from './TimezonePicker-b2aec6ea.js';
10import { D as DateTimePicker } from './DateTimePicker-5f40200d.js';
11import { D as DateTimeButtonRange } from './DateTimeButtonRange-8bea4bb3.js';
12import { P as PieChart } from './PieChart-6dd4aaac.js';
13import { S as Slider } from './Slider-e28a6a90.js';
14import { S as ScatterPlot } from './ScatterPlot-ba6e7434.js';
15import { G as GroupedBarChart } from './GroupedBarChart-5531ab17.js';
16import { H as Hierarchy } from './Hierarchy-e68459cc.js';
17import { H as Heatmap } from './Heatmap-ffb63db7.js';
18import { E as EventsTable } from './EventsTable-eefee9ae.js';
19import { M as ModelAutocomplete } from './ModelAutocomplete-6a9a44cd.js';
20import { M as ModelSearch } from './ModelSearch-1a2d1b0d.js';
21import { H as HierarchyNavigation } from './HierarchyNavigation-0cd4ef85.js';
22import { S as SingleDateTimePicker } from './SingleDateTimePicker-634d46bc.js';
23import { D as DateTimeButtonSingle } from './DateTimeButtonSingle-569f0da2.js';
24import { P as PlaybackControls } from './PlaybackControls-9a839502.js';
25import { P as ProcessGraphic } from './ProcessGraphic-5c6b405b.js';
26import { C as ColorPicker } from './ColorPicker-a8667b57.js';
27import { G as GeoProcessGraphic } from './GeoProcessGraphic-b41d2d2a.js';
28
29var AvailabilityChart = /** @class */ (function (_super) {
30 __extends(AvailabilityChart, _super);
31 function AvailabilityChart(renderTarget) {
32 var _this = _super.call(this, renderTarget) || this;
33 _this.minBrushWidth = 5;
34 _this.minGhostWidth = 2;
35 _this.margins = {
36 left: 10,
37 right: 10
38 };
39 _this.uxClient = new UXClient();
40 return _this;
41 }
42 //the most zoomed in possible
43 AvailabilityChart.prototype.getMinZoomedRange = function () {
44 var maxZoomFactor = (this.sparkLineChart.x.range()[1] - this.sparkLineChart.x.range()[0]) / this.minBrushWidth;
45 var totalTimeRange = this.toMillis - this.fromMillis;
46 return totalTimeRange / maxZoomFactor;
47 };
48 AvailabilityChart.prototype.zoom = function (direction, xPos) {
49 if (this.chartOptions.isCompact)
50 return;
51 var range = Math.max(this.getMinZoomedRange(), (this.zoomedToMillis - this.zoomedFromMillis));
52 var percentile = (xPos - this.sparkLineChart.x.range()[0]) /
53 (this.sparkLineChart.x.range()[1] - this.sparkLineChart.x.range()[0]);
54 var leftImpact = percentile * .2 * range;
55 var rightImpact = (1 - percentile) * .2 * range;
56 if (direction == 'out') {
57 this.zoomedFromMillis = Math.max(this.zoomedFromMillis - leftImpact, this.fromMillis);
58 this.zoomedToMillis = Math.min(this.zoomedToMillis + rightImpact, this.toMillis);
59 }
60 else {
61 var prospectiveFromMillis = Math.max(this.zoomedFromMillis + leftImpact, this.fromMillis);
62 var prospectiveToMillis = Math.min(this.zoomedToMillis - rightImpact, this.toMillis);
63 if (prospectiveToMillis - prospectiveFromMillis >= this.getMinZoomedRange()) {
64 this.zoomedFromMillis = prospectiveFromMillis;
65 this.zoomedToMillis = prospectiveToMillis;
66 }
67 else {
68 var offBy = this.getMinZoomedRange() - (prospectiveToMillis - prospectiveFromMillis);
69 this.zoomedFromMillis = prospectiveFromMillis - (percentile * offBy);
70 this.zoomedToMillis = prospectiveToMillis + ((1 - percentile) * offBy);
71 }
72 }
73 this.setAvailabilityRange(this.zoomedFromMillis, this.zoomedToMillis);
74 this.sparkLineChart.setBrushEndTime(new Date(this.zoomedToMillis));
75 this.sparkLineChart.setBrushStartTime(new Date(this.zoomedFromMillis));
76 this.sparkLineChart.setBrush();
77 this.timePickerLineChart.drawBrushRange();
78 event.preventDefault && event.preventDefault();
79 };
80 AvailabilityChart.prototype.setChartOptions = function (chartOptions) {
81 this.chartOptions.setOptions(__assign(__assign({}, chartOptions), {
82 keepBrush: true,
83 isArea: true,
84 noAnimate: true,
85 minutesForTimeLabels: true,
86 aggTopMargin: 0,
87 yAxisHidden: true,
88 focusHidden: true,
89 singleLineXAxisLabel: false
90 }));
91 };
92 AvailabilityChart.prototype.dateTimePickerAction = function (fromMillis, toMillis) {
93 this.setBrush(fromMillis, toMillis, true);
94 this.chartOptions.brushMoveEndAction(new Date(fromMillis), new Date(toMillis), this.chartOptions.offset);
95 this.setTicks();
96 this.dateTimePickerContainer.style("display", "none");
97 };
98 //transformation of buckets created by the UX client to buckets for the availabilityChart
99 AvailabilityChart.prototype.createDisplayBuckets = function (fromMillis, toMillis) {
100 var _this = this;
101 var keysInRange = Object.keys(this.transformedAvailability[0].availabilityCount[""]).reduce(function (inRangeObj, timestamp, i, timestamps) {
102 var currTSMillis = (new Date(timestamp)).valueOf();
103 var nextTSMillis = currTSMillis + _this.bucketSize;
104 if (currTSMillis >= fromMillis && currTSMillis <= toMillis) {
105 inRangeObj[(new Date(currTSMillis)).toISOString()] = _this.transformedAvailability[0].availabilityCount[""][timestamp];
106 return inRangeObj;
107 }
108 if (currTSMillis < fromMillis && nextTSMillis > fromMillis) {
109 inRangeObj[(new Date(fromMillis)).toISOString()] = _this.transformedAvailability[0].availabilityCount[""][timestamp];
110 return inRangeObj;
111 }
112 return inRangeObj;
113 }, {});
114 var rawBucketCount = Math.ceil((toMillis - fromMillis) / this.bucketSize);
115 var bucketMultiplier = Math.ceil(rawBucketCount / this.maxBuckets);
116 var computedBucketSize = this.bucketSize * bucketMultiplier;
117 var createKey = function (millis) { return Math.round(Math.floor(millis / computedBucketSize) * computedBucketSize); };
118 var firstBucket = createKey(fromMillis);
119 var lastBucket = createKey(toMillis);
120 var buckets = [];
121 for (var i = firstBucket; i <= lastBucket; i += computedBucketSize) {
122 buckets[(new Date(i)).toISOString()] = { count: 0 };
123 }
124 Object.keys(keysInRange).sort().forEach(function (ts, i) {
125 var tsMillis = (new Date(ts)).valueOf();
126 var computedKey = createKey(tsMillis);
127 buckets[(new Date(computedKey)).toISOString()].count += (keysInRange[ts].count / bucketMultiplier);
128 });
129 if (fromMillis !== null && firstBucket !== null) {
130 buckets[(new Date(fromMillis)).toISOString()] = buckets[(new Date(firstBucket)).toISOString()];
131 }
132 if (toMillis !== null && lastBucket !== null) {
133 buckets[(new Date(toMillis)).toISOString()] = buckets[(new Date(lastBucket)).toISOString()];
134 }
135 // delete the bucket before the from time
136 if (firstBucket < fromMillis) {
137 delete buckets[(new Date(firstBucket)).toISOString()];
138 }
139 return [{ "availabilityCount": { "": buckets } }];
140 };
141 AvailabilityChart.prototype.setRangeVariables = function (rawAvailability) {
142 if (Utils.safeNotNullOrUndefined(function () { return rawAvailability.range.from || rawAvailability.range.to || rawAvailability.intervalSize; })) {
143 this.fromMillis = (new Date(rawAvailability.range.from)).valueOf();
144 this.toMillis = (new Date(rawAvailability.range.to)).valueOf();
145 this.bucketSize = Utils.parseTimeInput(rawAvailability.intervalSize);
146 }
147 else {
148 this.fromMillis = null;
149 this.toMillis = null;
150 this.bucketSize = null;
151 }
152 };
153 AvailabilityChart.prototype.render = function (transformedAvailability, chartOptions, rawAvailability) {
154 var _this = this;
155 if (rawAvailability === void 0) { rawAvailability = {}; }
156 this.setChartOptions(chartOptions);
157 this.rawAvailability = rawAvailability;
158 this.transformedAvailability = transformedAvailability;
159 this.color = this.chartOptions.color ? this.chartOptions.color : 'teal';
160 this.maxBuckets = (this.chartOptions.maxBuckets) ? this.chartOptions.maxBuckets : 500;
161 this.setRangeVariables(rawAvailability);
162 var startBucket = (this.fromMillis !== null && this.bucketSize !== null) ?
163 Math.round(Math.floor(this.fromMillis / this.bucketSize) * this.bucketSize) : null;
164 var endBucket = (this.toMillis !== null && this.bucketSize !== null) ?
165 Math.round(Math.floor(this.toMillis / this.bucketSize) * this.bucketSize) : null;
166 if (startBucket !== null && startBucket === endBucket) {
167 this.fromMillis = Math.floor(this.fromMillis / this.bucketSize) * this.bucketSize;
168 this.toMillis = this.fromMillis + this.bucketSize;
169 this.bucketSize = this.bucketSize / 60;
170 }
171 this.ae = [new this.uxClient.AggregateExpression({ predicateString: "" }, { property: 'Count', type: "Double" }, ['count'], { from: new Date(this.fromMillis), to: new Date(this.toMillis) }, null, 'grey', 'Availability')];
172 this.targetElement = select(this.renderTarget)
173 .classed("tsi-availabilityChart", true)
174 .classed("tsi-compact", this.chartOptions.isCompact)
175 .classed("tsi-withButton", this.chartOptions.persistDateTimeButtonRange);
176 this.chartOptions.yAxisHidden = true;
177 this.chartOptions.focusHidden = true;
178 this.chartOptions.singleLineXAxisLabel = true;
179 this.chartOptions.suppressResizeListener = true;
180 this.chartOptions.brushClearable = false;
181 this.chartOptions.minBrushWidth = 1;
182 this.chartOptions.brushHandlesVisible = true;
183 this.chartOptions.hideChartControlPanel = true;
184 var brushMoveAction = this.chartOptions.brushMoveAction;
185 this.chartOptions.brushMoveAction = function (from, to) {
186 _this.setFromAndToTimes(from.valueOf(), to.valueOf());
187 _this.drawGhost();
188 if (_this.chartOptions.isCompact) {
189 _this.buildCompactFromAndTo();
190 }
191 if (brushMoveAction != null)
192 brushMoveAction(from, to);
193 };
194 _super.prototype.themify.call(this, this.targetElement, chartOptions.theme);
195 if (this.timePickerContainer == null) {
196 this.targetElement.html("");
197 this.timePickerContainer = this.targetElement.append("div")
198 .classed("tsi-timePickerContainer", true);
199 this.timePickerChart = this.timePickerContainer.append("div").classed("tsi-timePickerChart", true);
200 var sparkLineContainer = this.targetElement.append("div").classed("tsi-sparklineContainer", true);
201 this.timePickerTextContainer = this.targetElement.append("div").classed("tsi-timePickerTextContainer", true)
202 .style("margin-left", this.chartOptions.availabilityLeftMargin + this.margins.left);
203 this.timePickerLineChart = new LineChart(this.timePickerChart.node());
204 this.timePickerLineChart.chartMargins.left = (this.chartOptions.availabilityLeftMargin - this.margins.left);
205 this.buildFromAndToContainer();
206 this.sparkLineChart = new LineChart(sparkLineContainer.node());
207 this.sparkLineChart.chartMargins.left = (this.chartOptions.availabilityLeftMargin - this.margins.left);
208 this.dateTimePickerContainer = this.targetElement.append("div").classed("tsi-dateTimePickerContainer", true);
209 this.dateTimePicker = new DateTimePicker(this.dateTimePickerContainer.node());
210 window.addEventListener('resize', function () {
211 _this.timePickerLineChart.draw();
212 _this.setTicks();
213 _this.drawWarmRange();
214 if (_this.chartOptions.isCompact)
215 _this.buildCompactFromAndTo();
216 setTimeout(function () {
217 _this.drawGhost();
218 }, 100);
219 });
220 var pickerContainerAndContent = this.targetElement.selectAll(".tsi-dateTimePickerContainer, .tsi-dateTimePickerContainer *");
221 }
222 //clear the date time picker
223 this.dateTimePickerContainer.style("display", "none");
224 this.timePickerContainer.selectAll('.tsi-compactFromTo').remove();
225 if (this.chartOptions.isCompact) {
226 this.targetElement.select('.tsi-sparklineContainer').style("display", 'none');
227 if (!this.chartOptions.persistDateTimeButtonRange)
228 this.targetElement.select(".tsi-timePickerTextContainer").style('display', 'none');
229 this.targetElement.select('.tsi-zoomButtonContainer').style('display', 'none');
230 this.targetElement.select('.tsi-timePickerContainer').style('max-height', '68px').style('top', this.chartOptions.persistDateTimeButtonRange ? '6px' : '20px');
231 }
232 else {
233 this.targetElement.select('.tsi-sparklineContainer').style("display", 'flex');
234 this.targetElement.select(".tsi-timePickerTextContainer").style('display', 'inherit');
235 this.targetElement.select('.tsi-zoomButtonContainer').style('display', 'flex');
236 this.targetElement.select('.tsi-timePickerContainer').style('max-height', 'none').style('top', '0px');
237 }
238 var sparkLineOptions = this.createSparkLineOptions(chartOptions);
239 var visibileAvailability = this.createDisplayBuckets(this.fromMillis, this.toMillis);
240 this.sparkLineChart.render(visibileAvailability, sparkLineOptions, this.ae);
241 this.timePickerLineChart.render(visibileAvailability, this.chartOptions, this.ae);
242 this.setTicks();
243 this.drawWarmRange();
244 if (!this.chartOptions.preserveAvailabilityState) {
245 this.zoomedToMillis = this.toMillis;
246 this.zoomedFromMillis = this.chartOptions.defaultAvailabilityZoomRangeMillis ? Math.max(this.fromMillis, this.toMillis - this.chartOptions.defaultAvailabilityZoomRangeMillis) : this.fromMillis;
247 this.sparkLineChart.setBrushStartTime(new Date(this.zoomedFromMillis));
248 this.sparkLineChart.setBrushEndTime(new Date(this.zoomedToMillis));
249 this.setFromAndToTimes(Math.max(this.fromMillis, this.toMillis - (24 * 60 * 60 * 1000)), this.toMillis);
250 this.setBrush(Math.max(this.fromMillis, this.toMillis - (24 * 60 * 60 * 1000)), this.toMillis);
251 }
252 else {
253 if (this.zoomedFromMillis == null)
254 this.zoomedFromMillis = this.chartOptions.defaultAvailabilityZoomRangeMillis ? Math.max(this.fromMillis, this.toMillis - this.chartOptions.defaultAvailabilityZoomRangeMillis) : this.fromMillis;
255 if (this.zoomedToMillis == null)
256 this.zoomedToMillis = this.toMillis;
257 if (this.sparkLineChart.brushStartTime == null)
258 this.sparkLineChart.setBrushStartTime(new Date(this.zoomedFromMillis));
259 if (this.sparkLineChart.brushEndTime == null)
260 this.sparkLineChart.setBrushEndTime(new Date(this.zoomedToMillis));
261 if (this.selectedFromMillis == null || this.selectedToMillis == null)
262 this.setFromAndToTimes(this.toMillis - (24 * 60 * 60 * 1000), this.toMillis);
263 this.drawGhost();
264 this.setBrush(this.selectedFromMillis, this.selectedToMillis);
265 }
266 this.sparkLineChart.setBrush();
267 var self = this;
268 this.timePickerChart.select(".brushElem").on("wheel.zoom", function (d) {
269 var direction = event.deltaY > 0 ? 'out' : 'in';
270 var xPos = (mouse(this)[0]);
271 self.zoom(direction, xPos);
272 });
273 if (!this.chartOptions.isCompact) {
274 this.buildZoomButtons();
275 }
276 else {
277 this.timePickerChart.select('.brushElem').select('.selection');
278 }
279 this.setAvailabilityRange(this.zoomedFromMillis, this.zoomedToMillis);
280 if (this.chartOptions.isCompact) {
281 this.buildCompactFromAndTo();
282 }
283 this.timePickerLineChart.drawBrushRange();
284 };
285 AvailabilityChart.prototype.buildZoomButtons = function () {
286 var _this = this;
287 this.targetElement.selectAll(".tsi-zoomButtonContainer").remove();
288 var midpoint = (this.sparkLineChart.x.range()[1] - this.sparkLineChart.x.range()[0]) / 2;
289 var buttonsDiv = this.targetElement.append("div")
290 .classed("tsi-zoomButtonContainer", true);
291 buttonsDiv.append("button")
292 .attr("class", "tsi-zoomButton tsi-zoomButtonIn")
293 .attr('aria-label', this.getString('zoom in'))
294 .attr('title', this.getString('zoom in'))
295 .on("click", function () {
296 _this.zoom("in", midpoint);
297 });
298 buttonsDiv.append("button")
299 .attr("class", "tsi-zoomButton tsi-zoomButtonOut")
300 .attr('aria-label', this.getString('zoom out'))
301 .attr('title', this.getString('zoom out'))
302 .on("click", function () {
303 _this.zoom("out", midpoint);
304 });
305 };
306 AvailabilityChart.prototype.setSelectedMillis = function (fromMillis, toMillis) {
307 this.selectedFromMillis = fromMillis;
308 this.selectedToMillis = toMillis;
309 this.timePickerLineChart.drawBrushRange();
310 };
311 AvailabilityChart.prototype.renderDateTimeButton = function () {
312 var _this = this;
313 var minMillis = this.fromMillis + (Utils.getOffsetMinutes(this.chartOptions.offset, this.fromMillis) * 60 * 1000);
314 var maxMillis = this.toMillis + (Utils.getOffsetMinutes(this.chartOptions.offset, this.toMillis) * 60 * 1000);
315 var startMillis = this.selectedFromMillis + (Utils.getOffsetMinutes(this.chartOptions.offset, this.selectedFromMillis) * 60 * 1000);
316 var endMillis = this.selectedToMillis + (Utils.getOffsetMinutes(this.chartOptions.offset, this.selectedFromMillis) * 60 * 1000);
317 this.dateTimeButton.render(this.chartOptions, this.fromMillis, this.toMillis, this.selectedFromMillis, this.selectedToMillis, function (fromMillis, toMillis, offset) {
318 _this.chartOptions.offset = offset;
319 _this.timePickerLineChart.chartOptions.offset = offset;
320 _this.sparkLineChart.chartOptions.offset = offset;
321 _this.dateTimePickerAction(fromMillis, toMillis);
322 select(_this.renderTarget).select(".tsi-dateTimeContainer").node().focus();
323 }, function () {
324 _this.dateTimePickerContainer.style("display", "none");
325 select(_this.renderTarget).select(".tsi-dateTimeContainer").node().focus();
326 });
327 };
328 AvailabilityChart.prototype.setFromAndToTimes = function (fromMillis, toMillis, isFromButton) {
329 if (isFromButton === void 0) { isFromButton = false; }
330 var timezone = Utils.parseTimezoneName(this.chartOptions.offset);
331 var timezoneAbbreviation = Utils.timezoneAbbreviation(timezone);
332 this.setSelectedMillis(fromMillis, toMillis);
333 if (!isFromButton) {
334 this.renderDateTimeButton();
335 }
336 };
337 AvailabilityChart.prototype.drawGhost = function () {
338 var svgGroup = this.targetElement.select('.tsi-sparklineContainer').select(".tsi-lineChartSVG").select(".svgGroup");
339 svgGroup.selectAll(".ghostRect").remove();
340 svgGroup.append("rect")
341 .classed("ghostRect", true)
342 .attr("x", Math.max(this.sparkLineChart.x.range()[0], this.sparkLineChart.x(new Date(this.selectedFromMillis))))
343 .attr("y", 0)
344 .attr("width", Math.min(Math.max(this.minGhostWidth, this.sparkLineChart.x(new Date(this.selectedToMillis)) - this.sparkLineChart.x(new Date(this.selectedFromMillis))), this.sparkLineChart.x.range()[1] - this.sparkLineChart.x.range()[0]))
345 .attr("height", 8)
346 .attr("fill", this.chartOptions.color ? this.chartOptions.color : 'dark-grey')
347 .attr("fill-opacity", .3)
348 .attr("pointer-events", "none");
349 };
350 AvailabilityChart.prototype.drawWarmRange = function () {
351 var svgGroup = this.targetElement.select('.tsi-timePickerContainer').select(".tsi-lineChartSVG").select(".svgGroup");
352 if (svgGroup.select('.tsi-warmRect').empty()) {
353 svgGroup.append("rect")
354 .classed("tsi-warmRect", true);
355 svgGroup.select('.brushElem').raise();
356 }
357 var warmRect = svgGroup.select(".tsi-warmRect");
358 var outOfRange = true;
359 if (this.chartOptions.warmStoreRange) {
360 var warmStart = new Date(this.chartOptions.warmStoreRange[0]);
361 var boundedWarmStart = new Date(Math.max(warmStart.valueOf(), this.zoomedFromMillis));
362 var warmEnd = new Date(this.chartOptions.warmStoreRange.length === 2 ? this.chartOptions.warmStoreRange[1] : this.toMillis);
363 var boundedWarmEnd = new Date(Math.min(warmEnd.valueOf(), this.zoomedToMillis));
364 if (boundedWarmStart < boundedWarmEnd) {
365 outOfRange = false;
366 warmRect.attr("x", Math.max(this.timePickerLineChart.x(boundedWarmStart)))
367 .attr("y", this.chartOptions.isCompact ? 12 : -8)
368 .attr("width", this.timePickerLineChart.x(boundedWarmEnd) - this.timePickerLineChart.x(boundedWarmStart))
369 .attr("height", this.chartOptions.isCompact ? 4 : Math.max((this.targetElement.select('.tsi-timePickerContainer').select(".tsi-lineChartSVG").node().getBoundingClientRect().height - 44), 0))
370 .attr("fill-opacity", this.chartOptions.isCompact ? .8 : .08)
371 .attr('stroke-opacity', this.chartOptions.isCompact ? 0 : .5)
372 .attr("pointer-events", "none");
373 }
374 }
375 if (outOfRange || this.chartOptions.warmStoreRange === null) {
376 warmRect.style('display', 'none');
377 }
378 else {
379 warmRect.style('display', 'block');
380 }
381 };
382 AvailabilityChart.prototype.buildCompactFromAndTo = function () {
383 this.timePickerContainer.selectAll('.tsi-compactFromTo').remove();
384 // if the view is compact and there is a datetimebuttonrange present, we don't need compact from and to
385 if (this.chartOptions.persistDateTimeButtonRange)
386 return;
387 var brushPositions = this.timePickerLineChart.getBrushPositions();
388 var leftTimeText = null;
389 var rightTimeText = null;
390 if (this.selectedFromMillis != null && this.selectedToMillis != null) {
391 leftTimeText = this.timePickerContainer.append('div')
392 .classed('tsi-compactFromTo', true)
393 .style('left', (brushPositions.leftPos != null ? Math.max(brushPositions.leftPos, 5) : 5) + 'px')
394 .text(Utils.timeFormat(false, false, this.chartOptions.offset, this.chartOptions.is24HourTime, null, null, this.chartOptions.dateLocale)(new Date(this.selectedFromMillis)));
395 var timezoneAbbreviation = ' (' + Utils.createTimezoneAbbreviation(this.chartOptions.offset) + ')';
396 rightTimeText = this.timePickerContainer.append('div')
397 .attr('class', 'tsi-compactFromTo')
398 .style('right', brushPositions.rightPos != null ? 'calc(100% - ' + brushPositions.rightPos + 'px)' : '5px')
399 .style('left', 'auto')
400 .text(Utils.timeFormat(false, false, this.chartOptions.offset, this.chartOptions.is24HourTime, null, null, this.chartOptions.dateLocale)(new Date(this.selectedToMillis)) + timezoneAbbreviation);
401 }
402 if (leftTimeText && rightTimeText) {
403 var rightSideOfLeft = leftTimeText.node().getBoundingClientRect().left + leftTimeText.node().getBoundingClientRect().width;
404 var leftSideOfRight = rightTimeText.node().getBoundingClientRect().left;
405 var totalWidth = this.timePickerContainer.node().getBoundingClientRect().width;
406 var minOffset = 40;
407 if (leftSideOfRight - rightSideOfLeft < minOffset) { // if there is overlap (or near overlap), correction needed
408 var correction = (rightSideOfLeft - leftSideOfRight + minOffset) / 2;
409 //if the correction puts either side off the edge of the container, weight the correction to the other side
410 var leftWeight = 1;
411 var rightWeight = 1;
412 var padding = 32;
413 if ((brushPositions.leftPos - correction) < padding) {
414 leftWeight = 1 - ((padding - (brushPositions.leftPos - correction)) / correction);
415 rightWeight = 2 - leftWeight;
416 }
417 if ((brushPositions.rightPos + correction) > (totalWidth - padding)) {
418 rightWeight = 1 - (padding - (totalWidth - brushPositions.rightPos - correction)) / correction;
419 leftWeight = 2 - rightWeight;
420 }
421 rightTimeText.style('right', 'calc(100% - ' + Math.round((brushPositions.rightPos + (rightWeight * correction))) + 'px)')
422 .style('left', 'auto');
423 leftTimeText.style('left', (brushPositions.leftPos - (leftWeight * correction)) + 'px');
424 }
425 }
426 };
427 AvailabilityChart.prototype.offsetUTC = function (date) {
428 date.setTime(date.getTime() + date.getTimezoneOffset() * 60 * 1000);
429 return date;
430 };
431 AvailabilityChart.prototype.buildFromAndToContainer = function () {
432 var dateTimeContainer = this.timePickerTextContainer.append('div').classed('tsi-dateTimeContainer', true);
433 var timeframeLabel = dateTimeContainer.append("label").text(this.getString("Timeframe"));
434 var dateTimeButtonContainer = dateTimeContainer.append("div")
435 .classed('tsi-dateTimeButtonContainer', true);
436 this.dateTimeButton = new DateTimeButtonRange(dateTimeButtonContainer.node());
437 };
438 AvailabilityChart.prototype.setTicks = function () {
439 this.timePickerLineChart.updateXAxis();
440 var forceFirst = (this.timePickerLineChart.zoomedFromMillis == this.timePickerLineChart.fromMillis) && (this.zoomedFromMillis == this.fromMillis);
441 var forceLast = (this.timePickerLineChart.zoomedToMillis == this.timePickerLineChart.toMillis) && (this.zoomedToMillis == this.toMillis);
442 this.timePickerLineChart.updateXAxis(forceFirst, forceLast);
443 var ticks = this.timePickerContainer.select('.tsi-timePickerChart')
444 .select('.xAxis')
445 .selectAll('.tick');
446 ticks.each(function (d, i) {
447 var elt = select(this);
448 elt.classed((i === 0 && forceFirst ? 'tsi-fromTick' : (i === ticks.size() - 1 && forceLast ? 'tsi-toTick' : '')), true);
449 });
450 };
451 AvailabilityChart.prototype.setAvailabilityRange = function (fromMillis, toMillis) {
452 this.zoomedFromMillis = fromMillis;
453 this.zoomedToMillis = toMillis;
454 var visibileAvailability = this.createDisplayBuckets(fromMillis, toMillis);
455 this.chartOptions.keepBrush = true;
456 var aeWithNewTimeSpan = __assign(__assign({}, this.ae[0]), { searchSpan: {
457 from: (new Date(fromMillis)),
458 to: (new Date(toMillis))
459 } });
460 this.timePickerLineChart.render(visibileAvailability, this.chartOptions, [aeWithNewTimeSpan]);
461 this.setTicks();
462 this.drawWarmRange();
463 this.timePickerLineChart.setBrush();
464 };
465 AvailabilityChart.prototype.setBrush = function (fromMillis, toMillis, isFromButton) {
466 if (isFromButton === void 0) { isFromButton = false; }
467 this.timePickerLineChart.setBrushEndTime(new Date(toMillis));
468 this.timePickerLineChart.setBrushStartTime(new Date(fromMillis));
469 this.timePickerLineChart.setBrush();
470 this.setFromAndToTimes(fromMillis, toMillis, isFromButton);
471 this.drawGhost();
472 if (this.chartOptions.isCompact)
473 this.buildCompactFromAndTo();
474 };
475 AvailabilityChart.prototype.createSparkLineOptions = function (chartOptions) {
476 var _this = this;
477 return {
478 aggTopMargin: 0,
479 theme: chartOptions.theme,
480 grid: false,
481 tooltip: false,
482 legend: "hidden",
483 brushContextMenuActions: [],
484 snapBrush: false,
485 keepBrush: false,
486 xAxisHidden: true,
487 yAxisHidden: true,
488 focusHidden: true,
489 minBrushWidth: 5,
490 color: null,
491 brushHandlesVisible: true,
492 brushMoveAction: function (from, to) {
493 _this.setAvailabilityRange(from.valueOf(), to.valueOf());
494 },
495 brushClearable: false,
496 hideChartControlPanel: true,
497 brushRangeVisible: false,
498 isArea: true
499 };
500 };
501 return AvailabilityChart;
502}(ChartComponent));
503
504var MAXCARD = 150000;
505var AggregateExpression = /** @class */ (function (_super) {
506 __extends(AggregateExpression, _super);
507 function AggregateExpression(predicateObject, measureObject, measureTypes, searchSpan, splitByObject, colorOrOptionsObject, alias, contextMenu) {
508 if (splitByObject === void 0) { splitByObject = null; }
509 var _this = _super.call(this, (typeof (colorOrOptionsObject) === 'object' && !!colorOrOptionsObject) ? __assign(__assign({}, colorOrOptionsObject), { searchSpan: searchSpan, measureTypes: measureTypes }) : { color: colorOrOptionsObject, searchSpan: searchSpan, measureTypes: measureTypes, alias: alias, contextMenu: contextMenu }) || this;
510 _this.visibleSplitByCap = 10;
511 _this.predicate = predicateObject;
512 _this.splitByObject = splitByObject;
513 _this.measureObject = ((measureTypes.length == 1 && measureTypes[0] == 'count') || measureObject.property == 'Events Count') ? { count: {} } : { input: measureObject };
514 return _this;
515 }
516 AggregateExpression.prototype.toTsx = function (roundFromTo) {
517 var _this = this;
518 if (roundFromTo === void 0) { roundFromTo = false; }
519 var tsx = {};
520 var shiftMillis = Utils.parseShift(this.timeShift, this.startAt, this.searchSpan);
521 var fromMillis = this.searchSpan.from.valueOf() + shiftMillis;
522 var toMillis = this.searchSpan.to.valueOf() + shiftMillis;
523 var bucketSizeInMillis = Utils.parseTimeInput(this.searchSpan.bucketSize);
524 var roundedFromMillis = Math.floor((fromMillis + 62135596800000) / (bucketSizeInMillis)) * (bucketSizeInMillis) - 62135596800000;
525 var roundedToMillis = Math.ceil((toMillis + 62135596800000) / (bucketSizeInMillis)) * (bucketSizeInMillis) - 62135596800000;
526 if (roundFromTo) {
527 fromMillis = roundedFromMillis;
528 toMillis = roundedToMillis;
529 }
530 tsx['searchSpan'] = { from: (new Date(fromMillis)).toISOString(), to: (new Date(toMillis)).toISOString() };
531 // create aggregates
532 var measures = (this.measureObject.hasOwnProperty('count')) ? [{ count: {} }]
533 : this.measureTypes.reduce(function (p, c) {
534 var measureObject = {};
535 if (c == 'count')
536 measureObject = { count: {} };
537 else
538 measureObject[c] = _this['measureObject'];
539 p.push(measureObject);
540 return p;
541 }, []);
542 var aggregateObject = {};
543 var dimensionObject = { dateHistogram: { input: { builtInProperty: "$ts" }, breaks: { size: this.searchSpan.bucketSize } } };
544 if (this.splitByObject != null) {
545 var bucketsCeil = Math.ceil((roundedToMillis - roundedFromMillis) / bucketSizeInMillis);
546 aggregateObject['dimension'] = { uniqueValues: { input: this.splitByObject, take: Math.floor(MAXCARD / bucketsCeil) } };
547 aggregateObject['aggregate'] = { dimension: dimensionObject, measures: measures };
548 }
549 else {
550 aggregateObject['dimension'] = dimensionObject;
551 aggregateObject['measures'] = measures;
552 }
553 var aggregates = [aggregateObject];
554 tsx['aggregates'] = aggregates;
555 // create predicate
556 var predicate;
557 if (!this.measureObject.hasOwnProperty('count'))
558 predicate = { and: [this.predicate, { not: { eq: { left: this.measureObject.input, right: { 'double': null } } } }] };
559 else
560 predicate = this.predicate;
561 tsx['predicate'] = predicate;
562 return tsx;
563 };
564 return AggregateExpression;
565}(ChartDataOptions));
566
567var TsqExpression = /** @class */ (function (_super) {
568 __extends(TsqExpression, _super);
569 function TsqExpression(instanceObject, variableObject, searchSpan, colorOrOptionsObject, alias, contextMenu) {
570 var _this = this;
571 // This constructor should be called with the following parameters:
572 // new TsqExpression(instanceObject, variableObject, searchSpan, optionsObject)
573 // where the optionsObject should contain properties for color, alias, and contextMenu.
574 //
575 // However, to maintain backwards compatibility with older code, the constructor still
576 // accepts the older set of parameters:
577 // new TsqExpression(instanceObject, variableObject, searchSpan, color, alias, contextMenu)
578 // Here we differentiate between both and call the parent class's constructor as appropriate.
579 var optionsObject = (typeof (colorOrOptionsObject) === 'object' && !!colorOrOptionsObject)
580 ? __assign(__assign({}, colorOrOptionsObject), { searchSpan: searchSpan, measureTypes: Object.keys(variableObject) }) : {
581 color: colorOrOptionsObject,
582 searchSpan: searchSpan,
583 measureTypes: Object.keys(variableObject),
584 alias: alias,
585 contextMenu: contextMenu
586 };
587 _this = _super.call(this, optionsObject) || this;
588 _this.instanceObject = instanceObject;
589 _this.variableObject = variableObject;
590 return _this;
591 }
592 TsqExpression.prototype.toTsq = function (roundFromTo, getEvents, getSeries) {
593 if (roundFromTo === void 0) { roundFromTo = false; }
594 if (getEvents === void 0) { getEvents = false; }
595 if (getSeries === void 0) { getSeries = false; }
596 var tsq = {};
597 var shiftMillis = Utils.parseShift(this.timeShift, this.startAt, this.searchSpan);
598 var fromMillis = this.searchSpan.from.valueOf() + shiftMillis;
599 var toMillis = this.searchSpan.to.valueOf() + shiftMillis;
600 if (roundFromTo) {
601 var bucketSizeInMillis = Utils.parseTimeInput(this.searchSpan.bucketSize);
602 var roundedFromMillis = Math.floor((fromMillis + 62135596800000) / (bucketSizeInMillis)) * (bucketSizeInMillis) - 62135596800000;
603 var roundedToMillis = Math.ceil((toMillis + 62135596800000) / (bucketSizeInMillis)) * (bucketSizeInMillis) - 62135596800000;
604 fromMillis = roundedFromMillis;
605 toMillis = roundedToMillis;
606 }
607 tsq['searchSpan'] = { from: (new Date(fromMillis)).toISOString(), to: (new Date(toMillis)).toISOString() };
608 tsq['timeSeriesId'] = this.instanceObject.timeSeriesId;
609 if (getEvents) {
610 return { getEvents: tsq };
611 }
612 else if (getSeries) {
613 tsq['inlineVariables'] = __assign({}, this.variableObject);
614 tsq['projectedVariables'] = Object.keys(this.variableObject);
615 return { getSeries: tsq };
616 }
617 else {
618 tsq['interval'] = Utils.bucketSizeToTsqInterval(this.searchSpan.bucketSize);
619 tsq['inlineVariables'] = __assign({}, this.variableObject);
620 tsq['projectedVariables'] = Object.keys(this.variableObject);
621 return { aggregateSeries: tsq };
622 }
623 };
624 // This method will create an API query payload for the variable statistics of the first inline variable
625 // of this object, for numeric dataTypes. Categorical types work as expected.
626 TsqExpression.prototype.toStatsTsq = function (fromMillis, toMillis) {
627 var tsq = this.toTsq();
628 var shiftMillis = Utils.parseShift(this.timeShift);
629 fromMillis += shiftMillis;
630 toMillis += shiftMillis;
631 tsq.aggregateSeries['searchSpan'] = { from: (new Date(fromMillis)).toISOString(), to: (new Date(toMillis)).toISOString() };
632 tsq.aggregateSeries['interval'] = 'P1000Y';
633 if (this.dataType === 'numeric') {
634 var inlineVariables_1 = { min: {}, max: {}, avg: {}, stDev: {} };
635 var firstVariable_1 = tsq.aggregateSeries['inlineVariables'][Object.keys(tsq.aggregateSeries['inlineVariables'])[0]];
636 Object.keys(inlineVariables_1).forEach(function (k) {
637 inlineVariables_1[k] = JSON.parse(JSON.stringify(firstVariable_1));
638 inlineVariables_1[k].aggregation.tsx = k + "($value)";
639 delete inlineVariables_1[k]['interpolation'];
640 });
641 tsq.aggregateSeries['inlineVariables'] = inlineVariables_1;
642 tsq.aggregateSeries['projectedVariables'] = Object.keys(inlineVariables_1);
643 }
644 return tsq;
645 };
646 return TsqExpression;
647}(ChartDataOptions));
648
649var transformTsqResultsForVisualization = function (tsqResults, options) {
650 var result = [];
651 tsqResults.forEach(function (tsqr, i) {
652 var transformedAggregate = {};
653 var aggregatesObject = {};
654 transformedAggregate[options[i].alias] = { '': aggregatesObject };
655 if (tsqr.hasOwnProperty('__tsiError__'))
656 transformedAggregate[''] = {};
657 else {
658 tsqr.timestamps.forEach(function (ts, j) {
659 aggregatesObject[ts] = tsqr.properties.reduce(function (p, c) {
660 p[c.name] = aggregatesObject[ts] && aggregatesObject[ts][c.name] !== null ? aggregatesObject[ts][c.name] : c['values'][j];
661 return p;
662 }, {});
663 });
664 }
665 result.push(transformedAggregate);
666 });
667 return result;
668};
669
670var UXClient = /** @class */ (function () {
671 function UXClient() {
672 // Public facing components have class constructors exposed as public UXClient members.
673 // This allows for typings to be bundled while maintaining 'new Component()' syntax
674 this.DateTimePicker = DateTimePicker;
675 this.PieChart = PieChart;
676 this.ScatterPlot = ScatterPlot;
677 this.BarChart = GroupedBarChart;
678 this.LineChart = LineChart;
679 this.AvailabilityChart = AvailabilityChart;
680 this.Grid = Grid;
681 this.Slider = Slider;
682 this.Hierarchy = Hierarchy;
683 this.AggregateExpression = AggregateExpression;
684 this.TsqExpression = TsqExpression;
685 this.Heatmap = Heatmap;
686 this.EventsTable = EventsTable;
687 this.ModelSearch = ModelSearch;
688 this.ModelAutocomplete = ModelAutocomplete;
689 this.HierarchyNavigation = HierarchyNavigation;
690 this.TimezonePicker = TimezonePicker;
691 this.EllipsisMenu = EllipsisMenu;
692 this.SingleDateTimePicker = SingleDateTimePicker;
693 this.DateTimeButtonSingle = DateTimeButtonSingle;
694 this.DateTimeButtonRange = DateTimeButtonRange;
695 this.ProcessGraphic = ProcessGraphic;
696 this.PlaybackControls = PlaybackControls;
697 this.ColorPicker = ColorPicker;
698 this.GeoProcessGraphic = GeoProcessGraphic;
699 this.transformTsqResultsForVisualization = transformTsqResultsForVisualization;
700 }
701 UXClient.prototype.UXClient = function () {
702 };
703 UXClient.prototype.transformTsxToEventsArray = function (events, options) {
704 var timezoneOffset = options.timezoneOffset ? options.timezoneOffset : 0;
705 var rows = [];
706 var eventSourceProperties = {};
707 var nameToStrippedPropName = {};
708 var valueToStrippedValueMap = {};
709 var _loop_1 = function () {
710 if (events[eventIdx].hasOwnProperty('schema')) {
711 eventSourceProperties[events[eventIdx].schema.rid] = {};
712 eventSourceProperties[events[eventIdx].schema.rid].propertyNames = events[eventIdx].schema.properties.reduce(function (prev, curr) {
713 prev.push({ name: curr.name, type: curr.type });
714 return prev;
715 }, []);
716 eventSourceProperties[events[eventIdx].schema.rid].eventSourceName = events[eventIdx].schema['$esn'];
717 eventSourceId = events[eventIdx].schema.rid;
718 }
719 else {
720 eventSourceId = events[eventIdx].schemaRid;
721 }
722 timeStamp = (new Date((new Date(events[eventIdx]['$ts'])).valueOf() - timezoneOffset)).toISOString().slice(0, -1).replace('T', ' ');
723 event = { 'timestamp ($ts)': timeStamp };
724 // lts logic
725 lts = events[eventIdx]['$lts'] ? events[eventIdx]['$lts'] : null;
726 if (lts) {
727 event['LocalTimestamp_DateTime'] = {
728 value: lts.replace('T', ' '),
729 name: 'LocalTimestamp',
730 type: 'DateTime'
731 };
732 }
733 event["EventSourceName_String"] = {
734 value: eventSourceProperties[eventSourceId].eventSourceName,
735 name: 'EventSourceName',
736 type: 'String'
737 };
738 for (var propIdx in eventSourceProperties[eventSourceId].propertyNames) {
739 name = eventSourceProperties[eventSourceId].propertyNames[propIdx].name;
740 if (!nameToStrippedPropName.hasOwnProperty(name))
741 nameToStrippedPropName[name] = Utils.stripForConcat(name);
742 strippedName = nameToStrippedPropName[name];
743 type = eventSourceProperties[eventSourceId].propertyNames[propIdx].type;
744 columnNameAndType = strippedName + "_" + type;
745 if (!valueToStrippedValueMap.hasOwnProperty(String(events[eventIdx].values[propIdx])))
746 valueToStrippedValueMap[String(events[eventIdx].values[propIdx])] = Utils.stripForConcat(String(events[eventIdx].values[propIdx]));
747 eventObject = {
748 value: valueToStrippedValueMap[String(events[eventIdx].values[propIdx])],
749 name: strippedName,
750 type: type
751 };
752 event[columnNameAndType] = eventObject;
753 }
754 if (events[eventIdx].hasOwnProperty('$op')) {
755 var defaultType_1 = 'String';
756 var otherProps_1 = JSON.parse(events[eventIdx]['$op']);
757 Object.keys(otherProps_1).forEach(function (propNameRaw) {
758 var strippedNameOP = Utils.stripForConcat(propNameRaw);
759 var columnNameAndTypeOP = strippedNameOP + '_String';
760 event[columnNameAndTypeOP] = {
761 value: otherProps_1[propNameRaw],
762 name: strippedNameOP,
763 type: defaultType_1
764 };
765 });
766 }
767 rows.push(event);
768 };
769 var eventSourceId, timeStamp, event, lts, name, strippedName, type, columnNameAndType, eventObject;
770 for (var eventIdx in events) {
771 _loop_1();
772 }
773 return rows;
774 };
775 UXClient.prototype.toISONoMillis = function (dateTime) {
776 return dateTime.toISOString().slice(0, -5) + "Z";
777 };
778 //specifiedRange gives the subset of availability buckets to be returned. If not included, will return all buckets
779 UXClient.prototype.transformAvailabilityForVisualization = function (availabilityTsx) {
780 var _this = this;
781 var from = new Date(availabilityTsx.range.from);
782 var to = new Date(availabilityTsx.range.to);
783 var rawBucketSize = Utils.parseTimeInput(availabilityTsx.intervalSize);
784 var buckets = {};
785 var startBucket = Math.round(Math.floor(from.valueOf() / rawBucketSize) * rawBucketSize);
786 var firstKey = this.toISONoMillis(new Date(startBucket));
787 var firstCount = availabilityTsx.distribution[firstKey] ? availabilityTsx.distribution[firstKey] : 0;
788 // reset first key if greater than the availability range from
789 if (startBucket < (new Date(availabilityTsx.range.from)).valueOf())
790 firstKey = this.toISONoMillis(new Date(availabilityTsx.range.from));
791 buckets[firstKey] = { count: firstCount };
792 Object.keys(availabilityTsx.distribution).forEach(function (key) {
793 var formattedISO = _this.toISONoMillis(new Date(key));
794 buckets[formattedISO] = { count: availabilityTsx.distribution[key] };
795 });
796 //set end time value
797 var lastBucket = Math.round(Math.floor(to.valueOf() / rawBucketSize) * rawBucketSize);
798 // pad out if range is less than one bucket;
799 if (startBucket == lastBucket) {
800 for (var i = startBucket; i <= startBucket + rawBucketSize; i += (rawBucketSize / 60)) {
801 if (buckets[this.toISONoMillis(new Date(i))] == undefined)
802 buckets[this.toISONoMillis(new Date(i))] = { count: 0 };
803 }
804 //reset startBucket to count 0 if not the start time
805 if (startBucket != from.valueOf()) {
806 buckets[this.toISONoMillis(new Date(startBucket))] = { count: 0 };
807 }
808 }
809 return [{ "availabilityCount": { "": buckets } }];
810 };
811 UXClient.prototype.transformAggregatesForVisualization = function (aggregates, options) {
812 var result = [];
813 aggregates.forEach(function (agg, i) {
814 var transformedAggregate = {};
815 var aggregatesObject = {};
816 transformedAggregate[options[i].alias] = aggregatesObject;
817 if (agg.hasOwnProperty('__tsiError__'))
818 transformedAggregate[''] = {};
819 else if (agg.hasOwnProperty('aggregate')) {
820 agg.dimension.forEach(function (d, j) {
821 var dateTimeToValueObject = {};
822 aggregatesObject[d] = dateTimeToValueObject;
823 agg.aggregate.dimension.forEach(function (dt, k) {
824 var measuresObject = {};
825 dateTimeToValueObject[dt] = measuresObject;
826 options[i].measureTypes.forEach(function (t, l) {
827 if (agg.aggregate.measures[j][k] != null && agg.aggregate.measures[j][k] != undefined &&
828 agg.aggregate.measures[j][k][l] != null && agg.aggregate.measures[j][k][l] != undefined)
829 measuresObject[t] = agg.aggregate.measures[j][k][l];
830 else
831 measuresObject[t] = null;
832 });
833 });
834 });
835 }
836 else {
837 var dateTimeToValueObject = {};
838 aggregatesObject[''] = dateTimeToValueObject;
839 agg.dimension.forEach(function (dt, j) {
840 var measuresObject = {};
841 dateTimeToValueObject[dt] = measuresObject;
842 options[i].measureTypes.forEach(function (t, l) {
843 measuresObject[t] = agg.measures[j][l];
844 });
845 });
846 }
847 result.push(transformedAggregate);
848 });
849 return result;
850 };
851 // exposed publicly to use for highlighting elements in the well on hover/focus
852 UXClient.prototype.createEntityKey = function (aggName, aggIndex) {
853 if (aggIndex === void 0) { aggIndex = 0; }
854 return Utils.createEntityKey(aggName, aggIndex);
855 };
856 UXClient.prototype.transformTsqResultsToEventsArray = function (results) {
857 var flattenedResults = [];
858 results.forEach(function (tsqr) {
859 tsqr.timestamps.forEach(function (ts, idx) {
860 var event = {};
861 event['timestamp ($ts)'] = ts;
862 tsqr.properties.forEach(function (p) {
863 event[p.name + "_" + p.type] = { name: p.name, type: p.type, value: p.values[idx] };
864 });
865 flattenedResults.push(event);
866 });
867 });
868 return flattenedResults.sort(function (a, b) { return (new Date(a['timestamp ($ts)'])).valueOf() < (new Date(b['timestamp ($ts)'])).valueOf() ? -1 : 1; });
869 };
870 return UXClient;
871}());
872
873export { AvailabilityChart as A, UXClient as U };