diff options
| author | Tyler Schicke <tyler_schicke@brown.edu> | 2019-04-05 01:41:22 -0400 |
|---|---|---|
| committer | Tyler Schicke <tyler_schicke@brown.edu> | 2019-04-05 01:41:22 -0400 |
| commit | 0fb53a4b5fb430e67ef4af2323c886e77985ca52 (patch) | |
| tree | ca2826992a817d9944ab0163717c7644b1216d69 /src/client/northstar/utils | |
| parent | 8faacc6b8da0082823ec92cb1c862b6373596264 (diff) | |
| parent | 4fde212cd00bd2f8fc2fa122309af3bb71bba2fd (diff) | |
Merge branch 'master' of github-tsch-brown:browngraphicslab/Dash-Web
Diffstat (limited to 'src/client/northstar/utils')
| -rw-r--r-- | src/client/northstar/utils/Extensions.ts | 9 | ||||
| -rw-r--r-- | src/client/northstar/utils/LABColor.ts | 90 | ||||
| -rw-r--r-- | src/client/northstar/utils/MathUtil.ts | 13 | ||||
| -rw-r--r-- | src/client/northstar/utils/SizeConverter.ts | 99 | ||||
| -rw-r--r-- | src/client/northstar/utils/StyleContants.ts | 95 |
5 files changed, 302 insertions, 4 deletions
diff --git a/src/client/northstar/utils/Extensions.ts b/src/client/northstar/utils/Extensions.ts index 71bcadf89..7c2b7fc9d 100644 --- a/src/client/northstar/utils/Extensions.ts +++ b/src/client/northstar/utils/Extensions.ts @@ -1,5 +1,6 @@ interface String { ReplaceAll(toReplace: string, replacement: string): string; + Truncate(length: number, replacement: string): String; } String.prototype.ReplaceAll = function (toReplace: string, replacement: string): string { @@ -7,6 +8,14 @@ String.prototype.ReplaceAll = function (toReplace: string, replacement: string): return target.split(toReplace).join(replacement); } +String.prototype.Truncate = function (length: number, replacement: string): String { + var target = this; + if (target.length >= length) { + target = target.slice(0, Math.max(0, length - replacement.length)) + replacement; + } + return target; +} + interface Math { log10(val: number): number; } diff --git a/src/client/northstar/utils/LABColor.ts b/src/client/northstar/utils/LABColor.ts new file mode 100644 index 000000000..72e46fb7f --- /dev/null +++ b/src/client/northstar/utils/LABColor.ts @@ -0,0 +1,90 @@ + +export class LABColor { + public L: number; + public A: number; + public B: number; + + // constructor - takes three floats for lightness and color-opponent dimensions + constructor(l: number, a: number, b: number) { + this.L = l; + this.A = a; + this.B = b; + } + + // static function for linear interpolation between two LABColors + public static Lerp(a: LABColor, b: LABColor, t: number): LABColor { + return new LABColor(LABColor.LerpNumber(a.L, b.L, t), LABColor.LerpNumber(a.A, b.A, t), LABColor.LerpNumber(a.B, b.B, t)); + } + + public static LerpNumber(a: number, b: number, percent: number): number { + return a + percent * (b - a); + } + + static hexToRGB(hex: number, alpha: number): number[] { + var r = (hex & (0xff << 16)) >> 16; + var g = (hex & (0xff << 8)) >> 8; + var b = (hex & (0xff << 0)) >> 0; + return [r, g, b]; + } + static RGBtoHex(red: number, green: number, blue: number): number { + return blue | (green << 8) | (red << 16); + } + + public static RGBtoHexString(rgb: number): string { + let str = "#" + this.hex((rgb & (0xff << 16)) >> 16) + this.hex((rgb & (0xff << 8)) >> 8) + this.hex((rgb & (0xff << 0)) >> 0); + return str; + } + + static hex(x: number): string { + var hexDigits = new Array + ("0", "1", "2", "3", "4", "5", "6", "7", "8", "9", "a", "b", "c", "d", "e", "f"); + return isNaN(x) ? "00" : hexDigits[(x - x % 16) / 16] + hexDigits[x % 16]; + } + + public static FromColor(c: number): LABColor { + var rgb = LABColor.hexToRGB(c, 0); + var r = LABColor.d3_rgb_xyz(rgb[0] * 255); + var g = LABColor.d3_rgb_xyz(rgb[1] * 255); + var b = LABColor.d3_rgb_xyz(rgb[2] * 255); + + var x = LABColor.d3_xyz_lab((0.4124564 * r + 0.3575761 * g + 0.1804375 * b) / LABColor.d3_lab_X); + var y = LABColor.d3_xyz_lab((0.2126729 * r + 0.7151522 * g + 0.0721750 * b) / LABColor.d3_lab_Y); + var z = LABColor.d3_xyz_lab((0.0193339 * r + 0.1191920 * g + 0.9503041 * b) / LABColor.d3_lab_Z); + var lab = new LABColor(116 * y - 16, 500 * (x - y), 200 * (y - z)); + return lab; + } + + private static d3_lab_X: number = 0.950470; + private static d3_lab_Y: number = 1; + private static d3_lab_Z: number = 1.088830; + + public static d3_lab_xyz(x: number): number { + return x > 0.206893034 ? x * x * x : (x - 4 / 29) / 7.787037; + } + + public static d3_xyz_rgb(r: number): number { + return Math.round(255 * (r <= 0.00304 ? 12.92 * r : 1.055 * Math.pow(r, 1 / 2.4) - 0.055)); + } + + public static d3_rgb_xyz(r: number): number { + return (r /= 255) <= 0.04045 ? r / 12.92 : Math.pow((r + 0.055) / 1.055, 2.4); + } + + public static d3_xyz_lab(x: number): number { + return x > 0.008856 ? Math.pow(x, 1 / 3) : 7.787037 * x + 4 / 29; + } + + public static ToColor(lab: LABColor): number { + var y = (lab.L + 16) / 116; + var x = y + lab.A / 500; + var z = y - lab.B / 200; + x = LABColor.d3_lab_xyz(x) * LABColor.d3_lab_X; + y = LABColor.d3_lab_xyz(y) * LABColor.d3_lab_Y; + z = LABColor.d3_lab_xyz(z) * LABColor.d3_lab_Z; + + return LABColor.RGBtoHex( + LABColor.d3_xyz_rgb(3.2404542 * x - 1.5371385 * y - 0.4985314 * z) / 255, + LABColor.d3_xyz_rgb(-0.9692660 * x + 1.8760108 * y + 0.0415560 * z) / 255, + LABColor.d3_xyz_rgb(0.0556434 * x - 0.2040259 * y + 1.0572252 * z) / 255); + } +}
\ No newline at end of file diff --git a/src/client/northstar/utils/MathUtil.ts b/src/client/northstar/utils/MathUtil.ts index 3ed8628ee..bb7e73871 100644 --- a/src/client/northstar/utils/MathUtil.ts +++ b/src/client/northstar/utils/MathUtil.ts @@ -1,13 +1,17 @@ export class PIXIPoint { - public x: number; - public y: number; + public get x() { return this.coords[0]; } + public get y() { return this.coords[1]; } + public set x(value: number) { this.coords[0] = value; } + public set y(value: number) { this.coords[1] = value; } + public coords: number[] = [0, 0]; constructor(x: number, y: number) { - this.x = x; - this.y = y; + this.coords[0] = x; + this.coords[1] = y; } } + export class PIXIRectangle { public x: number; public y: number; @@ -17,6 +21,7 @@ export class PIXIRectangle { public get right() { return this.x + this.width; } public get top() { return this.y } public get bottom() { return this.top + this.height } + public static get EMPTY() { return new PIXIRectangle(0, 0, -1, -1); } constructor(x: number, y: number, width: number, height: number) { this.x = x; this.y = y; diff --git a/src/client/northstar/utils/SizeConverter.ts b/src/client/northstar/utils/SizeConverter.ts new file mode 100644 index 000000000..bb91ed4a7 --- /dev/null +++ b/src/client/northstar/utils/SizeConverter.ts @@ -0,0 +1,99 @@ +import { PIXIPoint } from "./MathUtil"; +import { VisualBinRange } from "../model/binRanges/VisualBinRange"; +import { Bin, DoubleValueAggregateResult, AggregateKey } from "../model/idea/idea"; +import { ModelHelpers } from "../model/ModelHelpers"; +import { observable, action, computed } from "mobx"; + +export class SizeConverter { + public DataMins: Array<number> = new Array<number>(2); + public DataMaxs: Array<number> = new Array<number>(2); + public DataRanges: Array<number> = new Array<number>(2); + public MaxLabelSizes: Array<PIXIPoint> = new Array<PIXIPoint>(2); + public RenderDimension: number = 300; + + @observable _leftOffset: number = 40; + @observable _rightOffset: number = 20; + @observable _topOffset: number = 20; + @observable _bottomOffset: number = 45; + @observable _labelAngle: number = 0; + @observable _isSmall: boolean = false; + @observable public Initialized = 0; + + @action public SetIsSmall(isSmall: boolean) { this._isSmall = isSmall; } + @action public SetLabelAngle(angle: number) { this._labelAngle = angle; } + @computed public get IsSmall() { return this._isSmall; } + @computed public get LabelAngle() { return this._labelAngle; } + @computed public get LeftOffset() { return this.IsSmall ? 5 : this._leftOffset; } + @computed public get RightOffset() { return this.IsSmall ? 5 : !this._labelAngle ? this._bottomOffset : Math.max(this._rightOffset, Math.cos(this._labelAngle) * (this.MaxLabelSizes[0].x + 18)); } + @computed public get TopOffset() { return this.IsSmall ? 5 : this._topOffset; } + @computed public get BottomOffset() { return this.IsSmall ? 25 : !this._labelAngle ? this._bottomOffset : Math.max(this._bottomOffset, Math.sin(this._labelAngle) * (this.MaxLabelSizes[0].x + 18)) + 18; } + + public SetVisualBinRanges(visualBinRanges: Array<VisualBinRange>) { + this.Initialized++; + var xLabels = visualBinRanges[0].GetLabels(); + var yLabels = visualBinRanges[1].GetLabels(); + var xLabelStrings = xLabels.map(l => l.label!).sort(function (a, b) { return b.length - a.length }); + var yLabelStrings = yLabels.map(l => l.label!).sort(function (a, b) { return b.length - a.length }); + + var metricsX = { width: 75 }; // RenderUtils.MeasureText(FontStyles.Default.fontFamily.toString(), 12, // FontStyles.AxisLabel.fontSize as number, + //xLabelStrings[0]!.slice(0, 20)) // StyleConstants.MAX_CHAR_FOR_HISTOGRAM_LABELS)); + var metricsY = { width: 22 }; // RenderUtils.MeasureText(FontStyles.Default.fontFamily.toString(), 12, // FontStyles.AxisLabel.fontSize as number, + // yLabelStrings[0]!.slice(0, 20)); // StyleConstants.MAX_CHAR_FOR_HISTOGRAM_LABELS)); + this.MaxLabelSizes[0] = new PIXIPoint(metricsX.width, 12);// FontStyles.AxisLabel.fontSize as number); + this.MaxLabelSizes[1] = new PIXIPoint(metricsY.width, 12); // FontStyles.AxisLabel.fontSize as number); + + this._leftOffset = Math.max(10, metricsY.width + 10 + 20); + + this.DataMins[0] = xLabels.map(l => l.minValue!).reduce((m, c) => Math.min(m, c), Number.MAX_VALUE); + this.DataMins[1] = yLabels.map(l => l.minValue!).reduce((m, c) => Math.min(m, c), Number.MAX_VALUE); + this.DataMaxs[0] = xLabels.map(l => l.maxValue!).reduce((m, c) => Math.max(m, c), Number.MIN_VALUE); + this.DataMaxs[1] = yLabels.map(l => l.maxValue!).reduce((m, c) => Math.max(m, c), Number.MIN_VALUE); + + this.DataRanges[0] = this.DataMaxs[0] - this.DataMins[0]; + this.DataRanges[1] = this.DataMaxs[1] - this.DataMins[1]; + } + + public DataToScreenNormalizedRange(dataValue: number, normalization: number, axis: number, binBrushMaxAxis: number) { + var value = normalization != 1 - axis || binBrushMaxAxis == 0 ? dataValue : (dataValue - 0) / (binBrushMaxAxis - 0) * this.DataRanges[axis]; + var from = this.DataToScreenCoord(Math.min(0, value), axis); + var to = this.DataToScreenCoord(Math.max(0, value), axis); + return [from, value, to]; + } + + public DataToScreenPointRange(axis: number, bin: Bin, aggregateKey: AggregateKey) { + var value = ModelHelpers.GetAggregateResult(bin, aggregateKey) as DoubleValueAggregateResult; + if (value && value.hasResult) + return [this.DataToScreenCoord(value.result!, axis) - 5, + this.DataToScreenCoord(value.result!, axis) + 5]; + return [undefined, undefined]; + } + + public DataToScreenXAxisRange(visualBinRanges: VisualBinRange[], index: number, bin: Bin) { + var value = visualBinRanges[0].GetValueFromIndex(bin.binIndex!.indices![index]); + return [this.DataToScreenX(value), this.DataToScreenX(visualBinRanges[index].AddStep(value))] + } + public DataToScreenYAxisRange(visualBinRanges: VisualBinRange[], index: number, bin: Bin) { + var value = visualBinRanges[1].GetValueFromIndex(bin.binIndex!.indices![index]); + return [this.DataToScreenY(value), this.DataToScreenY(visualBinRanges[index].AddStep(value))] + } + + public DataToScreenX(x: number): number { + return ((x - this.DataMins[0]) / this.DataRanges[0]) * this.RenderDimension; + } + public DataToScreenY(y: number, flip: boolean = true) { + var retY = ((y - this.DataMins[1]) / this.DataRanges[1]) * this.RenderDimension; + return flip ? (this.RenderDimension) - retY : retY; + } + public DataToScreenCoord(v: number, axis: number) { + if (axis == 0) + return this.DataToScreenX(v); + return this.DataToScreenY(v); + } + public DataToScreenRange(minVal: number, maxVal: number, axis: number) { + let xFrom = this.DataToScreenX(axis === 0 ? minVal : this.DataMins[0]); + let xTo = this.DataToScreenX(axis === 0 ? maxVal : this.DataMaxs[0]); + let yFrom = this.DataToScreenY(axis === 1 ? minVal : this.DataMins[1]); + let yTo = this.DataToScreenY(axis === 1 ? maxVal : this.DataMaxs[1]); + return { xFrom, yFrom, xTo, yTo } + } +}
\ No newline at end of file diff --git a/src/client/northstar/utils/StyleContants.ts b/src/client/northstar/utils/StyleContants.ts new file mode 100644 index 000000000..ac8617e3b --- /dev/null +++ b/src/client/northstar/utils/StyleContants.ts @@ -0,0 +1,95 @@ +import { PIXIPoint } from "./MathUtil"; + +export class StyleConstants { + + static DEFAULT_FONT: string = "Roboto Condensed"; + + static MENU_SUBMENU_WIDTH: number = 85; + static MENU_SUBMENU_HEIGHT: number = 400; + static MENU_BOX_SIZE: PIXIPoint = new PIXIPoint(80, 35); + static MENU_BOX_PADDING: number = 10; + + static OPERATOR_MENU_LARGE: number = 35; + static OPERATOR_MENU_SMALL: number = 25; + static BRUSH_PALETTE: number[] = [0x42b43c, 0xfa217f, 0x6a9c75, 0xfb5de7, 0x25b8ea, 0x9b5bc4, 0xda9f63, 0xe23209, 0xfb899b, 0x94a6fd] + static GAP: number = 3; + + static BACKGROUND_COLOR: number = 0xF3F3F3; + static TOOL_TIP_BACKGROUND_COLOR: number = 0xffffff; + static LIGHT_TEXT_COLOR: number = 0xffffff; + static LIGHT_TEXT_COLOR_STR: string = StyleConstants.HexToHexString(StyleConstants.LIGHT_TEXT_COLOR); + static DARK_TEXT_COLOR: number = 0x282828; + static HIGHLIGHT_TEXT_COLOR: number = 0xffcc00; + static FPS_TEXT_COLOR: number = StyleConstants.DARK_TEXT_COLOR; + static CORRELATION_LABEL_TEXT_COLOR_STR: string = StyleConstants.HexToHexString(StyleConstants.DARK_TEXT_COLOR); + static LOADING_SCREEN_TEXT_COLOR_STR: string = StyleConstants.HexToHexString(StyleConstants.DARK_TEXT_COLOR); + static ERROR_COLOR: number = 0x540E25; + static WARNING_COLOR: number = 0xE58F24; + static LOWER_THAN_NAIVE_COLOR: number = 0xee0000; + static HIGHLIGHT_COLOR: number = 0x82A8D9; + static HIGHLIGHT_COLOR_STR: string = StyleConstants.HexToHexString(StyleConstants.HIGHLIGHT_COLOR); + static OPERATOR_BACKGROUND_COLOR: number = 0x282828; + static LOADING_ANIMATION_COLOR: number = StyleConstants.OPERATOR_BACKGROUND_COLOR; + static MENU_COLOR: number = 0x282828; + static MENU_FONT_COLOR: number = StyleConstants.LIGHT_TEXT_COLOR; + static MENU_SELECTED_COLOR: number = StyleConstants.HIGHLIGHT_COLOR; + static MENU_SELECTED_FONT_COLOR: number = StyleConstants.LIGHT_TEXT_COLOR; + static BRUSH_COLOR: number = 0xff0000; + static DROP_ACCEPT_COLOR: number = StyleConstants.HIGHLIGHT_COLOR; + static SELECTED_COLOR: number = 0xffffff; + static SELECTED_COLOR_STR: string = StyleConstants.HexToHexString(StyleConstants.SELECTED_COLOR); + static PROGRESS_BACKGROUND_COLOR: number = 0x595959; + static GRID_LINES_COLOR: number = 0x3D3D3D; + static GRID_LINES_COLOR_STR: string = StyleConstants.HexToHexString(StyleConstants.GRID_LINES_COLOR); + + static MAX_CHAR_FOR_HISTOGRAM_LABELS: number = 20; + + static OVERLAP_COLOR: number = 0x0000ff;//0x540E25; + static BRUSH_COLORS: Array<number> = new Array<number>( + 0xFFDA7E, 0xFE8F65, 0xDA5655, 0x8F2240 + ); + + static MIN_VALUE_COLOR: number = 0x373d43; //32343d, 373d43, 3b4648 + static MARGIN_BARS_COLOR: number = 0xffffff; + static MARGIN_BARS_COLOR_STR: string = StyleConstants.HexToHexString(StyleConstants.MARGIN_BARS_COLOR); + + static HISTOGRAM_WIDTH: number = 200; + static HISTOGRAM_HEIGHT: number = 150; + static PREDICTOR_WIDTH: number = 150; + static PREDICTOR_HEIGHT: number = 100; + static RAWDATA_WIDTH: number = 150; + static RAWDATA_HEIGHT: number = 100; + static FREQUENT_ITEM_WIDTH: number = 180; + static FREQUENT_ITEM_HEIGHT: number = 100; + static CORRELATION_WIDTH: number = 555; + static CORRELATION_HEIGHT: number = 390; + static PROBLEM_FINDER_WIDTH: number = 450; + static PROBLEM_FINDER_HEIGHT: number = 150; + static PIPELINE_OPERATOR_WIDTH: number = 300; + static PIPELINE_OPERATOR_HEIGHT: number = 120; + static SLICE_WIDTH: number = 150; + static SLICE_HEIGHT: number = 45; + static BORDER_MENU_ITEM_WIDTH: number = 50; + static BORDER_MENU_ITEM_HEIGHT: number = 30; + + + static SLICE_BG_COLOR: string = StyleConstants.HexToHexString(StyleConstants.OPERATOR_BACKGROUND_COLOR); + static SLICE_EMPTY_COLOR: number = StyleConstants.OPERATOR_BACKGROUND_COLOR; + static SLICE_OCCUPIED_COLOR: number = 0xffffff; + static SLICE_OCCUPIED_BG_COLOR: string = StyleConstants.HexToHexString(StyleConstants.OPERATOR_BACKGROUND_COLOR); + static SLICE_HOVER_BG_COLOR: string = StyleConstants.HexToHexString(StyleConstants.HIGHLIGHT_COLOR); + static SLICE_HOVER_COLOR: number = 0xffffff; + + static HexToHexString(hex: number): string { + if (hex === undefined) { + return "#000000"; + } + var s = hex.toString(16); + while (s.length < 6) { + s = "0" + s; + } + return "#" + s; + } + + +} |
