Browse Source

UI: Improve aggregated value card widget. Improve data key aggregation config form.

feature/basic-widget-config
Igor Kulikov 3 years ago
parent
commit
1422558ac6
  1. 3
      ui-ngx/src/app/modules/home/components/widget/config/basic/cards/aggregated-data-key-row.component.html
  2. 15
      ui-ngx/src/app/modules/home/components/widget/config/basic/cards/aggregated-data-key-row.component.scss
  3. 26
      ui-ngx/src/app/modules/home/components/widget/config/basic/cards/aggregated-data-key-row.component.ts
  4. 1
      ui-ngx/src/app/modules/home/components/widget/config/basic/cards/aggregated-data-keys-panel.component.html
  5. 13
      ui-ngx/src/app/modules/home/components/widget/config/basic/cards/aggregated-data-keys-panel.component.scss
  6. 35
      ui-ngx/src/app/modules/home/components/widget/config/basic/cards/aggregated-value-card-basic-config.component.html
  7. 15
      ui-ngx/src/app/modules/home/components/widget/config/basic/cards/aggregated-value-card-basic-config.component.ts
  8. 121
      ui-ngx/src/app/modules/home/components/widget/config/data-key-config.component.html
  9. 2
      ui-ngx/src/app/modules/home/components/widget/config/datasources.component.scss
  10. 4
      ui-ngx/src/app/modules/home/components/widget/lib/cards/aggregated-value-card-widget.component.html
  11. 26
      ui-ngx/src/app/modules/home/components/widget/lib/cards/aggregated-value-card-widget.component.ts
  12. 16
      ui-ngx/src/app/modules/home/components/widget/lib/cards/aggregated-value-card.models.ts
  13. 2
      ui-ngx/src/app/modules/home/pages/admin/mail-server.component.scss
  14. 2
      ui-ngx/src/app/modules/home/pages/notification/inbox/inbox-table-header.component.scss
  15. 1
      ui-ngx/src/app/modules/home/pages/notification/recipient/recipient-notification-dialog.component.scss
  16. 1
      ui-ngx/src/app/modules/home/pages/notification/rule/rule-notification-dialog.component.scss
  17. 1
      ui-ngx/src/app/modules/home/pages/notification/sent/sent-notification-dialog.component.scss
  18. 2
      ui-ngx/src/app/shared/components/button/copy-button.component.scss
  19. 10
      ui-ngx/src/app/shared/components/color-picker/color-picker.component.ts
  20. 12
      ui-ngx/src/app/shared/components/material-icons.component.html
  21. 4
      ui-ngx/src/app/shared/components/material-icons.component.scss
  22. 1
      ui-ngx/src/app/shared/components/toggle-header.component.scss
  23. 6
      ui-ngx/src/app/shared/models/widget-settings.models.ts
  24. 1
      ui-ngx/src/assets/locale/locale.constant-en_US.json
  25. 48
      ui-ngx/src/form.scss
  26. 7
      ui-ngx/src/scss/constants.scss
  27. 6
      ui-ngx/src/theme.scss

3
ui-ngx/src/app/modules/home/components/widget/config/basic/cards/aggregated-data-key-row.component.html

@ -64,6 +64,9 @@
<tb-color-settings formControlName="color"> <tb-color-settings formControlName="color">
</tb-color-settings> </tb-color-settings>
</div> </div>
<div class="tb-arrow-field">
<mat-checkbox formControlName="showArrow"></mat-checkbox>
</div>
<div class="tb-form-table-row-cell-buttons"> <div class="tb-form-table-row-cell-buttons">
<button type="button" <button type="button"
mat-icon-button mat-icon-button

15
ui-ngx/src/app/modules/home/components/widget/config/basic/cards/aggregated-data-key-row.component.scss

@ -49,10 +49,10 @@
.tb-aggregation-field { .tb-aggregation-field {
flex: 1; flex: 1;
min-width: 150px; min-width: 120px;
} }
.tb-units-field, .tb-decimals-field, .tb-font-field, .tb-color-field { .tb-units-field, .tb-decimals-field, .tb-font-field, .tb-color-field, tb-arrow-field {
display: flex; display: flex;
flex-direction: row; flex-direction: row;
place-content: center; place-content: center;
@ -69,14 +69,13 @@
min-width: 60px; min-width: 60px;
} }
.tb-font-field { .tb-font-field, .tb-color-field, .tb-arrow-field {
width: 40px;
min-width: 40px;
}
.tb-color-field {
width: 40px; width: 40px;
min-width: 40px; min-width: 40px;
display: none;
@media #{$mat-gt-xs} {
display: block;
}
} }
.tb-units-field, .tb-decimals-field { .tb-units-field, .tb-decimals-field {

26
ui-ngx/src/app/modules/home/components/widget/config/basic/cards/aggregated-data-key-row.component.ts

@ -33,7 +33,7 @@ import {
ComparisonResultType, ComparisonResultType,
DataKey, DataKey,
DataKeyConfigMode, DataKeyConfigMode,
DatasourceType, Widget, DatasourceType, JsonSettingsSchema, Widget,
widgetType widgetType
} from '@shared/models/widget.models'; } from '@shared/models/widget.models';
import { DataKeyType } from '@shared/models/telemetry/telemetry.models'; import { DataKeyType } from '@shared/models/telemetry/telemetry.models';
@ -104,6 +104,14 @@ export class AggregatedDataKeyRowComponent implements ControlValueAccessor, OnIn
return this.widgetConfigComponent.widget; return this.widgetConfigComponent.widget;
} }
get latestDataKeySettingsSchema(): JsonSettingsSchema {
return this.widgetConfigComponent.modelValue?.latestDataKeySettingsSchema;
}
get latestDataKeySettingsDirective(): string {
return this.widgetConfigComponent.modelValue?.latestDataKeySettingsDirective;
}
get isEntityDatasource(): boolean { get isEntityDatasource(): boolean {
return [DatasourceType.device, DatasourceType.entity].includes(this.datasourceType); return [DatasourceType.device, DatasourceType.entity].includes(this.datasourceType);
} }
@ -124,7 +132,8 @@ export class AggregatedDataKeyRowComponent implements ControlValueAccessor, OnIn
units: [null, []], units: [null, []],
decimals: [null, []], decimals: [null, []],
font: [null, []], font: [null, []],
color: [null, []] color: [null, []],
showArrow: [null, []]
}); });
this.keyRowFormGroup.valueChanges.subscribe( this.keyRowFormGroup.valueChanges.subscribe(
() => this.updateModel() () => this.updateModel()
@ -172,7 +181,8 @@ export class AggregatedDataKeyRowComponent implements ControlValueAccessor, OnIn
units: value?.units, units: value?.units,
decimals: value?.decimals, decimals: value?.decimals,
font: settings.font, font: settings.font,
color: settings.color color: settings.color,
showArrow: settings.showArrow
}, {emitEvent: false} }, {emitEvent: false}
); );
this.cd.markForCheck(); this.cd.markForCheck();
@ -190,8 +200,8 @@ export class AggregatedDataKeyRowComponent implements ControlValueAccessor, OnIn
data: { data: {
dataKey: deepClone(this.modelValue), dataKey: deepClone(this.modelValue),
dataKeyConfigMode: DataKeyConfigMode.general, dataKeyConfigMode: DataKeyConfigMode.general,
dataKeySettingsSchema: null, dataKeySettingsSchema: this.latestDataKeySettingsSchema,
dataKeySettingsDirective: null, dataKeySettingsDirective: this.latestDataKeySettingsDirective,
dashboard: null, dashboard: null,
aliasController: null, aliasController: null,
widget: this.widget, widget: this.widget,
@ -207,6 +217,11 @@ export class AggregatedDataKeyRowComponent implements ControlValueAccessor, OnIn
}).afterClosed().subscribe((updatedDataKey) => { }).afterClosed().subscribe((updatedDataKey) => {
if (updatedDataKey) { if (updatedDataKey) {
this.modelValue = updatedDataKey; this.modelValue = updatedDataKey;
const settings: AggregatedValueCardKeySettings = (this.modelValue.settings || {});
this.keyRowFormGroup.get('position').patchValue(settings.position, {emitEvent: false});
this.keyRowFormGroup.get('font').patchValue(settings.font, {emitEvent: false});
this.keyRowFormGroup.get('color').patchValue(settings.color, {emitEvent: false});
this.keyRowFormGroup.get('showArrow').patchValue(settings.showArrow, {emitEvent: false});
this.keyRowFormGroup.get('units').patchValue(this.modelValue.units, {emitEvent: false}); this.keyRowFormGroup.get('units').patchValue(this.modelValue.units, {emitEvent: false});
this.keyRowFormGroup.get('decimals').patchValue(this.modelValue.decimals, {emitEvent: false}); this.keyRowFormGroup.get('decimals').patchValue(this.modelValue.decimals, {emitEvent: false});
this.updateModel(); this.updateModel();
@ -220,6 +235,7 @@ export class AggregatedDataKeyRowComponent implements ControlValueAccessor, OnIn
this.modelValue.settings.position = value.position; this.modelValue.settings.position = value.position;
this.modelValue.settings.font = value.font; this.modelValue.settings.font = value.font;
this.modelValue.settings.color = value.color; this.modelValue.settings.color = value.color;
this.modelValue.settings.showArrow = value.showArrow;
this.modelValue.units = value.units; this.modelValue.units = value.units;
this.modelValue.decimals = value.decimals; this.modelValue.decimals = value.decimals;
this.propagateChange(this.modelValue); this.propagateChange(this.modelValue);

1
ui-ngx/src/app/modules/home/components/widget/config/basic/cards/aggregated-data-keys-panel.component.html

@ -25,6 +25,7 @@
<div class="tb-form-table-header-cell tb-decimals-header" translate>widget-config.decimals-short</div> <div class="tb-form-table-header-cell tb-decimals-header" translate>widget-config.decimals-short</div>
<div class="tb-form-table-header-cell tb-font-header" translate>widgets.aggregated-value-card.font</div> <div class="tb-form-table-header-cell tb-font-header" translate>widgets.aggregated-value-card.font</div>
<div class="tb-form-table-header-cell tb-color-header" translate>widgets.aggregated-value-card.color</div> <div class="tb-form-table-header-cell tb-color-header" translate>widgets.aggregated-value-card.color</div>
<div class="tb-form-table-header-cell tb-arrow-header" translate>widgets.aggregated-value-card.arrow</div>
<div class="tb-form-table-header-cell tb-actions-header"></div> <div class="tb-form-table-header-cell tb-actions-header"></div>
</div> </div>
<div *ngIf="keysFormArray().controls.length; else noKeys" class="tb-form-table-body"> <div *ngIf="keysFormArray().controls.length; else noKeys" class="tb-form-table-body">

13
ui-ngx/src/app/modules/home/components/widget/config/basic/cards/aggregated-data-keys-panel.component.scss

@ -25,7 +25,7 @@
&.tb-aggregation-header { &.tb-aggregation-header {
flex: 1; flex: 1;
min-width: 150px; min-width: 120px;
} }
&.tb-units-header { &.tb-units-header {
@ -38,14 +38,13 @@
min-width: 60px; min-width: 60px;
} }
&.tb-font-header { &.tb-font-header, &.tb-color-header, &.tb-arrow-header {
width: 40px;
min-width: 40px;
}
&.tb-color-header {
width: 40px; width: 40px;
min-width: 40px; min-width: 40px;
display: none;
@media #{$mat-gt-xs} {
display: block;
}
} }
&.tb-actions-header { &.tb-actions-header {

35
ui-ngx/src/app/modules/home/components/widget/config/basic/cards/aggregated-value-card-basic-config.component.html

@ -29,7 +29,7 @@
</tb-datasources> </tb-datasources>
<div class="tb-form-panel"> <div class="tb-form-panel">
<div class="tb-form-panel-title" translate>widget-config.appearance</div> <div class="tb-form-panel-title" translate>widget-config.appearance</div>
<div class="tb-form-row"> <div class="tb-form-row column-xs">
<mat-slide-toggle class="mat-slide fixed-title-width" formControlName="showTitle"> <mat-slide-toggle class="mat-slide fixed-title-width" formControlName="showTitle">
{{ 'widget-config.title' | translate }} {{ 'widget-config.title' | translate }}
</mat-slide-toggle> </mat-slide-toggle>
@ -48,7 +48,7 @@
</tb-color-input> </tb-color-input>
</div> </div>
</div> </div>
<div class="tb-form-row"> <div class="tb-form-row column-xs">
<mat-slide-toggle class="mat-slide fixed-title-width" formControlName="showIcon"> <mat-slide-toggle class="mat-slide fixed-title-width" formControlName="showIcon">
{{ 'widgets.value-card.icon' | translate }} {{ 'widgets.value-card.icon' | translate }}
</mat-slide-toggle> </mat-slide-toggle>
@ -68,7 +68,7 @@
</tb-color-input> </tb-color-input>
</div> </div>
</div> </div>
<div class="tb-form-row"> <div class="tb-form-row column-xs">
<mat-slide-toggle class="mat-slide fixed-title-width" formControlName="showSubtitle"> <mat-slide-toggle class="mat-slide fixed-title-width" formControlName="showSubtitle">
{{ 'widgets.aggregated-value-card.subtitle' | translate }} {{ 'widgets.aggregated-value-card.subtitle' | translate }}
</mat-slide-toggle> </mat-slide-toggle>
@ -80,8 +80,10 @@
clearButton clearButton
[previewText]="aggregatedValueCardWidgetConfigForm.get('subtitle').value"> [previewText]="aggregatedValueCardWidgetConfigForm.get('subtitle').value">
</tb-font-settings> </tb-font-settings>
<tb-color-settings formControlName="subtitleColor"> <tb-color-input asBoxInput
</tb-color-settings> colorClearButton
formControlName="subtitleColor">
</tb-color-input>
</div> </div>
</div> </div>
<div class="tb-form-row column-xs"> <div class="tb-form-row column-xs">
@ -93,16 +95,27 @@
<tb-font-settings formControlName="dateFont" <tb-font-settings formControlName="dateFont"
[previewText]="datePreviewFn"> [previewText]="datePreviewFn">
</tb-font-settings> </tb-font-settings>
<tb-color-settings formControlName="dateColor"> <tb-color-input asBoxInput
</tb-color-settings> colorClearButton
formControlName="dateColor">
</tb-color-input>
</div> </div>
</div> </div>
<div class="tb-form-row space-between"> <div class="tb-form-row column-xs">
<mat-slide-toggle class="mat-slide" formControlName="showChart"> <mat-slide-toggle class="mat-slide fixed-title-width" formControlName="showChart">
{{ 'widgets.aggregated-value-card.chart' | translate }} {{ 'widgets.aggregated-value-card.chart' | translate }}
</mat-slide-toggle> </mat-slide-toggle>
<tb-color-settings formControlName="chartColor"> <div fxFlex fxLayout="row" fxLayoutAlign="start center" fxLayoutGap="8px">
</tb-color-settings> <tb-unit-input class="flex" formControlName="chartUnits"></tb-unit-input>
<mat-form-field appearance="outline" class="flex number" subscriptSizing="dynamic">
<input matInput formControlName="chartDecimals" type="number" min="0" max="15" step="1" placeholder="{{ 'widget-config.set' | translate }}">
<div matSuffix fxHide.lt-md translate>widget-config.decimals-suffix</div>
</mat-form-field>
<tb-color-input asBoxInput
colorClearButton
formControlName="chartColor">
</tb-color-input>
</div>
</div> </div>
</div> </div>
<tb-aggregated-data-keys-panel <tb-aggregated-data-keys-panel

15
ui-ngx/src/app/modules/home/components/widget/config/basic/cards/aggregated-value-card-basic-config.component.ts

@ -90,7 +90,7 @@ export class AggregatedValueCardBasicConfigComponent extends BasicWidgetConfigCo
protected setupDefaults(configData: WidgetConfigComponentData) { protected setupDefaults(configData: WidgetConfigComponentData) {
this.setupDefaultDatasource(configData, [ this.setupDefaultDatasource(configData, [
{ name: 'watermeter', label: 'Watermeter', type: DataKeyType.timeseries } { name: 'watermeter', label: 'Watermeter', type: DataKeyType.timeseries, units: 'm³', decimals: 0 }
], ],
createDefaultAggregatedValueLatestDataKeys('watermeter', 'm³') createDefaultAggregatedValueLatestDataKeys('watermeter', 'm³')
); );
@ -141,6 +141,8 @@ export class AggregatedValueCardBasicConfigComponent extends BasicWidgetConfigCo
dateColor: [settings.dateColor, []], dateColor: [settings.dateColor, []],
showChart: [settings.showChart, []], showChart: [settings.showChart, []],
chartUnits: [dataKey?.units, []],
chartDecimals: [dataKey?.decimals, []],
chartColor: [settings.chartColor, []], chartColor: [settings.chartColor, []],
values: [this.getValues(configData.config.datasources, keyName), []], values: [this.getValues(configData.config.datasources, keyName), []],
@ -181,6 +183,13 @@ export class AggregatedValueCardBasicConfigComponent extends BasicWidgetConfigCo
this.widgetConfig.config.settings.dateColor = config.dateColor; this.widgetConfig.config.settings.dateColor = config.dateColor;
this.widgetConfig.config.settings.showChart = config.showChart; this.widgetConfig.config.settings.showChart = config.showChart;
const dataKey = getDataKey(this.widgetConfig.config.datasources);
if (dataKey) {
dataKey.units = config.chartUnits;
dataKey.decimals = config.chartDecimals;
}
this.widgetConfig.config.settings.chartColor = config.chartColor; this.widgetConfig.config.settings.chartColor = config.chartColor;
this.setValues(config.values, this.widgetConfig.config.datasources); this.setValues(config.values, this.widgetConfig.config.datasources);
@ -253,8 +262,12 @@ export class AggregatedValueCardBasicConfigComponent extends BasicWidgetConfigCo
} }
if (showChart) { if (showChart) {
this.aggregatedValueCardWidgetConfigForm.get('chartUnits').enable();
this.aggregatedValueCardWidgetConfigForm.get('chartDecimals').enable();
this.aggregatedValueCardWidgetConfigForm.get('chartColor').enable(); this.aggregatedValueCardWidgetConfigForm.get('chartColor').enable();
} else { } else {
this.aggregatedValueCardWidgetConfigForm.get('chartUnits').disable();
this.aggregatedValueCardWidgetConfigForm.get('chartDecimals').disable();
this.aggregatedValueCardWidgetConfigForm.get('chartColor').disable(); this.aggregatedValueCardWidgetConfigForm.get('chartColor').disable();
} }
} }

121
ui-ngx/src/app/modules/home/components/widget/config/data-key-config.component.html

@ -78,76 +78,87 @@
</tb-js-func> </tb-js-func>
</section> </section>
<ng-container *ngIf="widgetType === widgetTypes.latest && modelValue.type === dataKeyTypes.timeseries"> <ng-container *ngIf="widgetType === widgetTypes.latest && modelValue.type === dataKeyTypes.timeseries">
<mat-form-field subscriptSizing="dynamic"> <div class="tb-form-row column">
<mat-label translate>datakey.aggregation</mat-label> <div class="tb-form-row space-between no-border no-padding">
<mat-select formControlName="aggregationType" style="min-width: 150px;"> <div>{{ 'datakey.aggregation' | translate }}</div>
<mat-option *ngFor="let aggregation of aggregations" [value]="aggregation"> <mat-form-field class="medium-width" subscriptSizing="dynamic" appearance="outline">
{{ aggregationTypesTranslations.get(aggregationTypes[aggregation]) | translate }} <mat-select formControlName="aggregationType">
</mat-option> <mat-option *ngFor="let aggregation of aggregations" [value]="aggregation">
</mat-select> {{ aggregationTypesTranslations.get(aggregationTypes[aggregation]) | translate }}
</mat-form-field> </mat-option>
<div class="tb-hint after-fields"> </mat-select>
{{ dataKeyFormGroup.get('aggregationType').value ? (dataKeyAggregationTypeHintTranslations.get(aggregationTypes[dataKeyFormGroup.get('aggregationType').value]) | translate) : '' }} </mat-form-field>
<section *ngIf="dataKeyFormGroup.get('aggregationType').value !== aggregationTypes.NONE"> </div>
{{ 'datakey.aggregation-type-hint-common' | translate }} <div class="tb-form-hint tb-primary-fill">
</section> {{ dataKeyFormGroup.get('aggregationType').value ? (dataKeyAggregationTypeHintTranslations.get(aggregationTypes[dataKeyFormGroup.get('aggregationType').value]) | translate) : '' }}
<section *ngIf="dataKeyFormGroup.get('aggregationType').value !== aggregationTypes.NONE">
{{ 'datakey.aggregation-type-hint-common' | translate }}
</section>
</div>
</div> </div>
</ng-container> </ng-container>
</div> </div>
<div *ngIf="dataKeyFormGroup.get('aggregationType').value && dataKeyFormGroup.get('aggregationType').value !== aggregationTypes.NONE" <div *ngIf="dataKeyFormGroup.get('aggregationType').value && dataKeyFormGroup.get('aggregationType').value !== aggregationTypes.NONE"
class="tb-form-panel tb-slide-toggle"> class="tb-form-panel">
<div class="tb-form-panel-title" translate>datakey.delta-calculation</div> <div class="tb-form-panel-title" translate>datakey.delta-calculation</div>
<mat-expansion-panel class="tb-settings" [expanded]="dataKeyFormGroup.get('comparisonEnabled').value" [disabled]="!dataKeyFormGroup.get('comparisonEnabled').value"> <div class="tb-form-panel stroked tb-slide-toggle">
<mat-expansion-panel class="tb-settings" [expanded]="dataKeyFormGroup.get('comparisonEnabled').value" [disabled]="!dataKeyFormGroup.get('comparisonEnabled').value">
<mat-expansion-panel-header fxLayout="row wrap"> <mat-expansion-panel-header fxLayout="row wrap">
<mat-panel-title fxLayout="column" fxLayoutAlign="center start"> <mat-panel-title fxLayout="column" fxLayoutAlign="center start" fxLayoutGap="8px">
<mat-slide-toggle class="mat-slide" formControlName="comparisonEnabled" (click)="$event.stopPropagation()"> <mat-slide-toggle class="mat-slide" formControlName="comparisonEnabled" (click)="$event.stopPropagation()">
{{ 'datakey.enable-delta-calculation' | translate }} {{ 'datakey.enable-delta-calculation' | translate }}
</mat-slide-toggle> </mat-slide-toggle>
<mat-hint class="tb-hint" style="line-height: 15px; padding-left: 52px;">{{ 'datakey.enable-delta-calculation-hint' | translate }}</mat-hint> <mat-hint class="tb-form-hint tb-primary-fill">{{ 'datakey.enable-delta-calculation-hint' | translate }}</mat-hint>
</mat-panel-title> </mat-panel-title>
</mat-expansion-panel-header> </mat-expansion-panel-header>
<ng-template matExpansionPanelContent> <ng-template matExpansionPanelContent>
<section fxLayout="column" *ngIf="dataKeyFormGroup.get('comparisonEnabled').value"> <ng-container *ngIf="dataKeyFormGroup.get('comparisonEnabled').value">
<mat-form-field fxFlex class="mat-block"> <div class="tb-form-row space-between">
<mat-label translate>widgets.chart.time-for-comparison</mat-label> <div>{{ 'widgets.chart.time-for-comparison' | translate }}</div>
<mat-select formControlName="timeForComparison"> <mat-form-field class="medium-width" subscriptSizing="dynamic" appearance="outline">
<mat-option [value]="'previousInterval'"> <mat-select formControlName="timeForComparison">
{{ 'widgets.chart.time-for-comparison-previous-interval' | translate }} <mat-option [value]="'previousInterval'">
</mat-option> {{ 'widgets.chart.time-for-comparison-previous-interval' | translate }}
<mat-option [value]="'days'"> </mat-option>
{{ 'widgets.chart.time-for-comparison-days' | translate }} <mat-option [value]="'days'">
</mat-option> {{ 'widgets.chart.time-for-comparison-days' | translate }}
<mat-option [value]="'weeks'"> </mat-option>
{{ 'widgets.chart.time-for-comparison-weeks' | translate }} <mat-option [value]="'weeks'">
</mat-option> {{ 'widgets.chart.time-for-comparison-weeks' | translate }}
<mat-option [value]="'months'"> </mat-option>
{{ 'widgets.chart.time-for-comparison-months' | translate }} <mat-option [value]="'months'">
</mat-option> {{ 'widgets.chart.time-for-comparison-months' | translate }}
<mat-option [value]="'years'"> </mat-option>
{{ 'widgets.chart.time-for-comparison-years' | translate }} <mat-option [value]="'years'">
</mat-option> {{ 'widgets.chart.time-for-comparison-years' | translate }}
<mat-option [value]="'customInterval'"> </mat-option>
{{ 'widgets.chart.time-for-comparison-custom-interval' | translate }} <mat-option [value]="'customInterval'">
</mat-option> {{ 'widgets.chart.time-for-comparison-custom-interval' | translate }}
</mat-select> </mat-option>
</mat-form-field> </mat-select>
<mat-form-field *ngIf="dataKeyFormGroup.get('timeForComparison').value === 'customInterval'" fxFlex class="mat-block"> </mat-form-field>
<mat-label translate>widgets.chart.custom-interval-value</mat-label> </div>
<input required matInput type="number" min="0" formControlName="comparisonCustomIntervalValue"> <div *ngIf="dataKeyFormGroup.get('timeForComparison').value === 'customInterval'" class="tb-form-row space-between">
</mat-form-field> <div>{{ 'widgets.chart.custom-interval-value' | translate }}</div>
<mat-form-field style="padding-bottom: 16px;"> <mat-form-field class="medium-width number" subscriptSizing="dynamic" appearance="outline">
<mat-label translate>datakey.delta-calculation-result</mat-label> <input required matInput type="number" min="0" formControlName="comparisonCustomIntervalValue">
<mat-select formControlName="comparisonResultType" style="min-width: 150px;"> </mat-form-field>
<mat-option *ngFor="let comparisonResultType of comparisonResults" [value]="comparisonResultType"> </div>
{{ comparisonResultTypeTranslations.get(comparisonResultTypes[comparisonResultType]) | translate }} <div class="tb-form-row space-between">
</mat-option> <div>{{ 'datakey.delta-calculation-result' | translate }}</div>
</mat-select> <mat-form-field class="medium-width" subscriptSizing="dynamic" appearance="outline">
</mat-form-field> <mat-select formControlName="comparisonResultType" style="min-width: 150px;">
</section> <mat-option *ngFor="let comparisonResultType of comparisonResults" [value]="comparisonResultType">
{{ comparisonResultTypeTranslations.get(comparisonResultTypes[comparisonResultType]) | translate }}
</mat-option>
</mat-select>
</mat-form-field>
</div>
</ng-container>
</ng-template> </ng-template>
</mat-expansion-panel> </mat-expansion-panel>
</div>
</div> </div>
<div class="tb-form-panel tb-slide-toggle" <div class="tb-form-panel tb-slide-toggle"
*ngIf="(modelValue.type === dataKeyTypes.timeseries || modelValue.type === dataKeyTypes.attribute || modelValue.type === dataKeyTypes.count) && showPostProcessing"> *ngIf="(modelValue.type === dataKeyTypes.timeseries || modelValue.type === dataKeyTypes.attribute || modelValue.type === dataKeyTypes.count) && showPostProcessing">
<mat-expansion-panel class="tb-settings" [expanded]="dataKeyFormGroup.get('usePostProcessing').value" [disabled]="!dataKeyFormGroup.get('usePostProcessing').value"> <mat-expansion-panel class="tb-settings" [expanded]="dataKeyFormGroup.get('usePostProcessing').value" [disabled]="!dataKeyFormGroup.get('usePostProcessing').value">

2
ui-ngx/src/app/modules/home/components/widget/config/datasources.component.scss

@ -13,7 +13,7 @@
* See the License for the specific language governing permissions and * See the License for the specific language governing permissions and
* limitations under the License. * limitations under the License.
*/ */
@import "../../../../../../theme"; @import "../../../../../../scss/constants";
.tb-datasource-list-item { .tb-datasource-list-item {
&.mat-mdc-list-item { &.mat-mdc-list-item {

4
ui-ngx/src/app/modules/home/components/widget/lib/cards/aggregated-value-card-widget.component.html

@ -28,7 +28,7 @@
<ng-template #subtitleTpl> <ng-template #subtitleTpl>
<div *ngIf="showSubtitle" class="tb-aggregated-value-card-subtitle" <div *ngIf="showSubtitle" class="tb-aggregated-value-card-subtitle"
[style]="subtitleStyle" [style.color]="subtitleColor.color">{{ subtitle$ | async }}</div> [style]="subtitleStyle" [style.color]="subtitleColor">{{ subtitle$ | async }}</div>
</ng-template> </ng-template>
<ng-template #valuesTpl> <ng-template #valuesTpl>
<div *ngIf="showValues" class="tb-aggregated-value-card-values"> <div *ngIf="showValues" class="tb-aggregated-value-card-values">
@ -73,7 +73,7 @@
</div> </div>
</ng-template> </ng-template>
<ng-template #dateTpl> <ng-template #dateTpl>
<div *ngIf="showDate" [style]="dateStyle" [style.color]="dateColor.color" [innerHTML]="dateFormat.formatted"></div> <div *ngIf="showDate" [style]="dateStyle" [style.color]="dateColor" [innerHTML]="dateFormat.formatted"></div>
</ng-template> </ng-template>
<ng-template #valueTpl let-value="value"> <ng-template #valueTpl let-value="value">
<div class="tb-aggregated-value-card-value" [style]="value.style" [style.color]="value.color.color"> <div class="tb-aggregated-value-card-value" [style]="value.style" [style.color]="value.color.color">

26
ui-ngx/src/app/modules/home/components/widget/lib/cards/aggregated-value-card-widget.component.ts

@ -36,9 +36,9 @@ import { WidgetContext } from '@home/models/widget-component.models';
import { Observable } from 'rxjs'; import { Observable } from 'rxjs';
import { import {
backgroundStyle, backgroundStyle,
ColorProcessor,
ComponentStyle, ComponentStyle,
DateFormatProcessor, getDataKey, DateFormatProcessor,
getDataKey,
getLatestSingleTsValue, getLatestSingleTsValue,
overlayStyle, overlayStyle,
textStyle textStyle
@ -47,7 +47,7 @@ import { DatePipe } from '@angular/common';
import { TbFlot } from '@home/components/widget/lib/flot-widget'; import { TbFlot } from '@home/components/widget/lib/flot-widget';
import { TbFlotKeySettings, TbFlotSettings } from '@home/components/widget/lib/flot-widget.models'; import { TbFlotKeySettings, TbFlotSettings } from '@home/components/widget/lib/flot-widget.models';
import { DataKey } from '@shared/models/widget.models'; import { DataKey } from '@shared/models/widget.models';
import { formatNumberValue, formatValue, isDefined, isNumeric } from '@core/utils'; import { formatNumberValue, formatValue, isDefined } from '@core/utils';
import { map } from 'rxjs/operators'; import { map } from 'rxjs/operators';
@Component({ @Component({
@ -72,19 +72,19 @@ export class AggregatedValueCardWidgetComponent implements OnInit, AfterViewInit
showSubtitle = true; showSubtitle = true;
subtitle$: Observable<string>; subtitle$: Observable<string>;
subtitleStyle: ComponentStyle = {}; subtitleStyle: ComponentStyle = {};
subtitleColor: ColorProcessor; subtitleColor: string;
showValues = false; showValues = false;
values: {[key: string]: AggregatedValueCardValue} = {}; values: {[key: string]: AggregatedValueCardValue} = {};
showChart = true; showChart = true;
chartColor: ColorProcessor; chartColor: string;
showDate = true; showDate = true;
dateFormat: DateFormatProcessor; dateFormat: DateFormatProcessor;
dateStyle: ComponentStyle = {}; dateStyle: ComponentStyle = {};
dateColor: ColorProcessor; dateColor: string;
backgroundStyle: ComponentStyle = {}; backgroundStyle: ComponentStyle = {};
overlayStyle: ComponentStyle = {}; overlayStyle: ComponentStyle = {};
@ -108,7 +108,7 @@ export class AggregatedValueCardWidgetComponent implements OnInit, AfterViewInit
const subtitle = this.settings.subtitle; const subtitle = this.settings.subtitle;
this.subtitle$ = this.ctx.registerLabelPattern(subtitle, this.subtitle$); this.subtitle$ = this.ctx.registerLabelPattern(subtitle, this.subtitle$);
this.subtitleStyle = textStyle(this.settings.subtitleFont, '0.25px'); this.subtitleStyle = textStyle(this.settings.subtitleFont, '0.25px');
this.subtitleColor = ColorProcessor.fromSettings(this.settings.subtitleColor); this.subtitleColor = this.settings.subtitleColor;
const dataKey = getDataKey(this.ctx.defaultSubscription.datasources); const dataKey = getDataKey(this.ctx.defaultSubscription.datasources);
if (dataKey?.name && this.ctx.defaultSubscription.firstDatasource?.latestDataKeys?.length) { if (dataKey?.name && this.ctx.defaultSubscription.firstDatasource?.latestDataKeys?.length) {
@ -123,7 +123,7 @@ export class AggregatedValueCardWidgetComponent implements OnInit, AfterViewInit
} }
this.showChart = this.settings.showChart; this.showChart = this.settings.showChart;
this.chartColor = ColorProcessor.fromSettings(this.settings.chartColor); this.chartColor = this.settings.chartColor;
if (this.showChart) { if (this.showChart) {
if (this.ctx.defaultSubscription.firstDatasource?.dataKeys?.length) { if (this.ctx.defaultSubscription.firstDatasource?.dataKeys?.length) {
this.flotDataKey = this.ctx.defaultSubscription.firstDatasource?.dataKeys[0]; this.flotDataKey = this.ctx.defaultSubscription.firstDatasource?.dataKeys[0];
@ -132,14 +132,14 @@ export class AggregatedValueCardWidgetComponent implements OnInit, AfterViewInit
showLines: true, showLines: true,
lineWidth: 2 lineWidth: 2
} as TbFlotKeySettings; } as TbFlotKeySettings;
this.flotDataKey.color = this.chartColor.color; this.flotDataKey.color = this.chartColor;
} }
} }
this.showDate = this.settings.showDate; this.showDate = this.settings.showDate;
this.dateFormat = DateFormatProcessor.fromSettings(this.ctx.$injector, this.settings.dateFormat); this.dateFormat = DateFormatProcessor.fromSettings(this.ctx.$injector, this.settings.dateFormat);
this.dateStyle = textStyle(this.settings.dateFont, '0.25px'); this.dateStyle = textStyle(this.settings.dateFont, '0.25px');
this.dateColor = ColorProcessor.fromSettings(this.settings.dateColor); this.dateColor = this.settings.dateColor;
this.backgroundStyle = backgroundStyle(this.settings.background); this.backgroundStyle = backgroundStyle(this.settings.background);
this.overlayStyle = overlayStyle(this.settings.background.overlay); this.overlayStyle = overlayStyle(this.settings.background.overlay);
@ -188,17 +188,11 @@ export class AggregatedValueCardWidgetComponent implements OnInit, AfterViewInit
public onDataUpdated() { public onDataUpdated() {
const tsValue = getLatestSingleTsValue(this.ctx.data); const tsValue = getLatestSingleTsValue(this.ctx.data);
let ts; let ts;
let value;
if (tsValue) { if (tsValue) {
ts = tsValue[0]; ts = tsValue[0];
value = tsValue[1];
} }
this.subtitleColor.update(value);
this.dateColor.update(value);
if (this.showChart) { if (this.showChart) {
this.chartColor.update(value);
this.flot.updateSeriesColor(this.chartColor.color);
this.flot.update(); this.flot.update();
} }

16
ui-ngx/src/app/modules/home/components/widget/lib/cards/aggregated-value-card.models.ts

@ -24,7 +24,6 @@ import {
constantColor, constantColor,
DateFormatSettings, DateFormatSettings,
Font, Font,
iconStyle,
lastUpdateAgoDateFormat, lastUpdateAgoDateFormat,
textStyle textStyle
} from '@shared/models/widget-settings.models'; } from '@shared/models/widget-settings.models';
@ -36,13 +35,13 @@ export interface AggregatedValueCardWidgetSettings {
showSubtitle: boolean; showSubtitle: boolean;
subtitle: string; subtitle: string;
subtitleFont: Font; subtitleFont: Font;
subtitleColor: ColorSettings; subtitleColor: string;
showDate: boolean; showDate: boolean;
dateFormat: DateFormatSettings; dateFormat: DateFormatSettings;
dateFont: Font; dateFont: Font;
dateColor: ColorSettings; dateColor: string;
showChart: boolean; showChart: boolean;
chartColor: ColorSettings; chartColor: string;
background: BackgroundSettings; background: BackgroundSettings;
} }
@ -83,7 +82,8 @@ export interface AggregatedValueCardValue {
downArrow: boolean; downArrow: boolean;
} }
export const computeAggregatedCardValue = (dataKeys: DataKey[], keyName: string, position: AggregatedValueCardKeyPosition): AggregatedValueCardValue => { export const computeAggregatedCardValue =
(dataKeys: DataKey[], keyName: string, position: AggregatedValueCardKeyPosition): AggregatedValueCardValue => {
const key = dataKeys.find(dataKey => ( dataKey.name === keyName && (dataKey.settings?.position === position || const key = dataKeys.find(dataKey => ( dataKey.name === keyName && (dataKey.settings?.position === position ||
(!dataKey.settings?.position && position === AggregatedValueCardKeyPosition.center)) )); (!dataKey.settings?.position && position === AggregatedValueCardKeyPosition.center)) ));
if (key) { if (key) {
@ -123,7 +123,7 @@ export const aggregatedValueCardDefaultSettings: AggregatedValueCardWidgetSettin
weight: '400', weight: '400',
lineHeight: '16px' lineHeight: '16px'
}, },
subtitleColor: constantColor('rgba(0, 0, 0, 0.38)'), subtitleColor: 'rgba(0, 0, 0, 0.38)',
showDate: true, showDate: true,
dateFormat: lastUpdateAgoDateFormat(), dateFormat: lastUpdateAgoDateFormat(),
dateFont: { dateFont: {
@ -134,9 +134,9 @@ export const aggregatedValueCardDefaultSettings: AggregatedValueCardWidgetSettin
weight: '400', weight: '400',
lineHeight: '16px' lineHeight: '16px'
}, },
dateColor: constantColor('rgba(0, 0, 0, 0.38)'), dateColor: 'rgba(0, 0, 0, 0.38)',
showChart: true, showChart: true,
chartColor: constantColor('rgba(0, 0, 0, 0.87)'), chartColor: 'rgba(0, 0, 0, 0.87)',
background: { background: {
type: BackgroundType.color, type: BackgroundType.color,
color: '#fff', color: '#fff',

2
ui-ngx/src/app/modules/home/pages/admin/mail-server.component.scss

@ -13,7 +13,7 @@
* See the License for the specific language governing permissions and * See the License for the specific language governing permissions and
* limitations under the License. * limitations under the License.
*/ */
@import "../../../../../theme"; @import "../../../../../scss/constants";
:host { :host {
.fields-group { .fields-group {

2
ui-ngx/src/app/modules/home/pages/notification/inbox/inbox-table-header.component.scss

@ -13,7 +13,7 @@
* See the License for the specific language governing permissions and * See the License for the specific language governing permissions and
* limitations under the License. * limitations under the License.
*/ */
@import "../../../../../../theme"; @import "../../../../../../scss/constants";
:host ::ng-deep { :host ::ng-deep {
.mat-button-toggle-group.tb-notification-unread-toggle-group { .mat-button-toggle-group.tb-notification-unread-toggle-group {

1
ui-ngx/src/app/modules/home/pages/notification/recipient/recipient-notification-dialog.component.scss

@ -14,7 +14,6 @@
* limitations under the License. * limitations under the License.
*/ */
@import "../../../../../../scss/constants"; @import "../../../../../../scss/constants";
@import "../../../../../../theme";
:host { :host {
form.tb-dialog-container { form.tb-dialog-container {

1
ui-ngx/src/app/modules/home/pages/notification/rule/rule-notification-dialog.component.scss

@ -13,7 +13,6 @@
* See the License for the specific language governing permissions and * See the License for the specific language governing permissions and
* limitations under the License. * limitations under the License.
*/ */
@import "../../../../../../theme";
@import "../../../../../../scss/constants"; @import "../../../../../../scss/constants";
:host { :host {

1
ui-ngx/src/app/modules/home/pages/notification/sent/sent-notification-dialog.component.scss

@ -14,7 +14,6 @@
* limitations under the License. * limitations under the License.
*/ */
@import "../../../../../../scss/constants"; @import "../../../../../../scss/constants";
@import "../../../../../../theme";
:host-context(.tb-fullscreen-dialog .mat-mdc-dialog-container) { :host-context(.tb-fullscreen-dialog .mat-mdc-dialog-container) {
width: 820px; width: 820px;

2
ui-ngx/src/app/shared/components/button/copy-button.component.scss

@ -13,7 +13,7 @@
* See the License for the specific language governing permissions and * See the License for the specific language governing permissions and
* limitations under the License. * limitations under the License.
*/ */
@import "../../../../theme"; @import "../../../../scss/constants";
:host { :host {
.mini-button { .mini-button {

10
ui-ngx/src/app/shared/components/color-picker/color-picker.component.ts

@ -18,6 +18,7 @@ import { Component, forwardRef, OnDestroy } from '@angular/core';
import { Color, ColorPickerControl } from '@iplab/ngx-color-picker'; import { Color, ColorPickerControl } from '@iplab/ngx-color-picker';
import { Subscription } from 'rxjs'; import { Subscription } from 'rxjs';
import { ControlValueAccessor, NG_VALUE_ACCESSOR, UntypedFormControl } from '@angular/forms'; import { ControlValueAccessor, NG_VALUE_ACCESSOR, UntypedFormControl } from '@angular/forms';
import { isString } from '@core/utils';
export enum ColorType { export enum ColorType {
hex = 'hex', hex = 'hex',
@ -87,8 +88,9 @@ export class ColorPickerComponent implements ControlValueAccessor, OnDestroy {
} }
writeValue(value: string): void { writeValue(value: string): void {
this.setValue = !!value; const valid = this.isValidColorValue(value);
this.control.setValueFrom(value || '#fff'); this.setValue = valid;
this.control.setValueFrom(valid ? value : '#fff');
this.modelValue = value; this.modelValue = value;
if (this.control.initType === ColorType.hexa) { if (this.control.initType === ColorType.hexa) {
@ -101,6 +103,10 @@ export class ColorPickerComponent implements ControlValueAccessor, OnDestroy {
this.presentationControl.patchValue(this.presentations.indexOf(this.control.initType), {emitEvent: false}); this.presentationControl.patchValue(this.presentations.indexOf(this.control.initType), {emitEvent: false});
} }
private isValidColorValue(value: string): boolean {
return value && isString(value) && value.trim().length > 0;
}
private updateModel() { private updateModel() {
const color: string = this.getValueByType(this.control.value, this.presentations[this.presentationControl.value]); const color: string = this.getValueByType(this.control.value, this.presentations[this.presentationControl.value]);
if (this.modelValue !== color) { if (this.modelValue !== color) {

12
ui-ngx/src/app/shared/components/material-icons.component.html

@ -53,22 +53,24 @@
</ng-container> </ng-container>
</div> </div>
</cdk-virtual-scroll-viewport> </cdk-virtual-scroll-viewport>
<button *ngIf="!showAllSubject.value" class="tb-material-icons-show-more" mat-button color="primary" (click)="showAllSubject.next(true)">
{{ 'action.show-more' | translate }}
</button>
<ng-container *ngIf="notFound"> <ng-container *ngIf="notFound">
<div class="tb-no-data-available" [ngStyle]="{width: iconsPanelWidth}"> <div class="tb-no-data-available" [ngStyle]="{width: iconsPanelWidth}">
<div class="tb-no-data-bg"></div> <div class="tb-no-data-bg"></div>
<div class="tb-no-data-text">{{ 'icon.no-icons-found' | translate:{iconSearch: searchIconControl.value} }}</div> <div class="tb-no-data-text">{{ 'icon.no-icons-found' | translate:{iconSearch: searchIconControl.value} }}</div>
</div> </div>
</ng-container> </ng-container>
<div *ngIf="iconClearButton" class="tb-material-icons-panel-buttons"> <div class="tb-material-icons-panel-buttons" *ngIf="iconClearButton || !showAllSubject.value">
<button mat-button <button *ngIf="iconClearButton"
mat-button
color="primary" color="primary"
type="button" type="button"
(click)="clearIcon()" (click)="clearIcon()"
[disabled]="!selectedIcon"> [disabled]="!selectedIcon">
{{ 'action.clear' | translate }} {{ 'action.clear' | translate }}
</button> </button>
<span fxFlex></span>
<button *ngIf="!showAllSubject.value" class="tb-material-icons-show-more" mat-button color="primary" (click)="showAllSubject.next(true)">
{{ 'action.show-more' | translate }}
</button>
</div> </div>
</div> </div>

4
ui-ngx/src/app/shared/components/material-icons.component.scss

@ -26,7 +26,7 @@
letter-spacing: 0.25px; letter-spacing: 0.25px;
color: rgba(0, 0, 0, 0.87); color: rgba(0, 0, 0, 0.87);
} }
.tb-material-icons-title, .tb-material-icons-search, .tb-material-icons-show-more { .tb-material-icons-title, .tb-material-icons-search {
width: 100%; width: 100%;
} }
.tb-material-icons-viewport { .tb-material-icons-viewport {
@ -64,6 +64,6 @@
flex-direction: row; flex-direction: row;
gap: 16px; gap: 16px;
align-items: flex-start; align-items: flex-start;
align-self: flex-start; align-self: stretch;
} }
} }

1
ui-ngx/src/app/shared/components/toggle-header.component.scss

@ -14,7 +14,6 @@
* limitations under the License. * limitations under the License.
*/ */
@import "../../../theme";
@import "../../../scss/constants"; @import "../../../scss/constants";
:host { :host {

6
ui-ngx/src/app/shared/models/widget-settings.models.ts

@ -149,7 +149,7 @@ type ValueColorFunction = (value: any) => string;
export abstract class ColorProcessor { export abstract class ColorProcessor {
static fromSettings(color: ColorSettings): ColorProcessor { static fromSettings(color: ColorSettings): ColorProcessor {
const settings = color || constantColor('rgba(0, 0, 0, 0.87)'); const settings = color || constantColor(null);
switch (settings.type) { switch (settings.type) {
case ColorType.constant: case ColorType.constant:
return new ConstantColorProcessor(settings); return new ConstantColorProcessor(settings);
@ -192,7 +192,7 @@ class RangeColorProcessor extends ColorProcessor {
if (this.settings.rangeList?.length && isDefinedAndNotNull(value) && isNumeric(value)) { if (this.settings.rangeList?.length && isDefinedAndNotNull(value) && isNumeric(value)) {
const num = Number(value); const num = Number(value);
for (const range of this.settings.rangeList) { for (const range of this.settings.rangeList) {
if (this.constantRange(range) && range.from === num) { if (RangeColorProcessor.constantRange(range) && range.from === num) {
return range.color; return range.color;
} else if ((!isNumber(range.from) || num >= range.from) && (!isNumber(range.to) || num < range.to)) { } else if ((!isNumber(range.from) || num >= range.from) && (!isNumber(range.to) || num < range.to)) {
return range.color; return range.color;
@ -202,7 +202,7 @@ class RangeColorProcessor extends ColorProcessor {
return this.settings.color; return this.settings.color;
} }
private constantRange(range: ColorRange): boolean { private static constantRange(range: ColorRange): boolean {
return isNumber(range.from) && isNumber(range.to) && range.from === range.to; return isNumber(range.from) && isNumber(range.to) && range.from === range.to;
} }
} }

1
ui-ngx/src/assets/locale/locale.constant-en_US.json

@ -5756,6 +5756,7 @@
"position-left-bottom": "Left bottom", "position-left-bottom": "Left bottom",
"font": "Font", "font": "Font",
"color": "Color", "color": "Color",
"arrow": "Arrow",
"display-up-down-arrow": "Display Up/Down arrow", "display-up-down-arrow": "Display Up/Down arrow",
"add-value": "Add value", "add-value": "Add value",
"remove-value": "Remove value", "remove-value": "Remove value",

48
ui-ngx/src/form.scss

@ -16,12 +16,16 @@
@import './scss/constants'; @import './scss/constants';
@mixin form-row-column($breakpoint) { @mixin form-row-column() {
flex-direction: column;
align-items: stretch;
gap: 12px;
padding: 12px 7px 12px 16px;
}
@mixin form-row-column-breakpoint($breakpoint) {
@media #{$breakpoint} { @media #{$breakpoint} {
flex-direction: column; @include form-row-column;
align-items: stretch;
gap: 12px;
padding: 12px 7px 12px 16px;
.mat-mdc-form-field, tb-unit-input { .mat-mdc-form-field, tb-unit-input {
width: auto; width: auto;
&.medium-width { &.medium-width {
@ -132,6 +136,16 @@
font-size: 12px; font-size: 12px;
color: #808080; color: #808080;
} }
.tb-form-hint {
padding: 12px 16px;
font-size: var(--mdc-typography-caption-font-size, 12px);
line-height: var(--mdc-typography-caption-line-height, 20px);
font-weight: var(--mdc-typography-caption-font-weight, 400);
letter-spacing: var(--mdc-typography-caption-letter-spacing, 0.0333333333em);
color: rgba(0, 0, 0, 0.6);
white-space: normal;
border-radius: 6px;
}
.tb-form-row { .tb-form-row {
height: 100%; height: 100%;
display: flex; display: flex;
@ -142,11 +156,12 @@
border: 1px solid rgba(0, 0, 0, 0.12); border: 1px solid rgba(0, 0, 0, 0.12);
border-radius: 6px; border-radius: 6px;
&.column { &.column {
@include form-row-column;
&-xs { &-xs {
@include form-row-column($mat-xs) @include form-row-column-breakpoint($mat-xs)
} }
&-lt-md { &-lt-md {
@include form-row-column($mat-lt-md) @include form-row-column-breakpoint($mat-lt-md)
} }
} }
&.no-border { &.no-border {
@ -450,7 +465,7 @@
left: 0; left: 0;
right: 0; right: 0;
bottom: 0; bottom: 0;
background: #305680; background: $tb-primary-color;
mask-image: url(/assets/home/no_data_folder_bg.svg); mask-image: url(/assets/home/no_data_folder_bg.svg);
mask-repeat: no-repeat; mask-repeat: no-repeat;
mask-size: contain; mask-size: contain;
@ -470,6 +485,23 @@
} }
} }
.tb-primary-fill {
position: relative;
overflow: hidden;
&:before {
display: block;
height: auto;
content: "";
position: absolute;
top: 0;
bottom: 0;
left: 0;
right: 0;
background: $tb-primary-color;
opacity: 0.04;
}
}
button.mat-mdc-button-base.tb-box-button, .tb-form-table-row-cell-buttons button.mat-mdc-icon-button.mat-mdc-button-base { button.mat-mdc-button-base.tb-box-button, .tb-form-table-row-cell-buttons button.mat-mdc-icon-button.mat-mdc-button-base {
width: 40px; width: 40px;
min-width: 40px; min-width: 40px;

7
ui-ngx/src/scss/constants.scss

@ -30,3 +30,10 @@ $mat-gt-xl: "screen and (min-width: 1920px)";
$mat-md-lg: "screen and (min-width: 960px) and (max-width: 1819px)"; $mat-md-lg: "screen and (min-width: 960px) and (max-width: 1819px)";
$primary-hue-3: rgb(207, 216, 220) !default; $primary-hue-3: rgb(207, 216, 220) !default;
$tb-primary-color: #305680;
$tb-secondary-color: #527dad;
$tb-hue3-color: #a7c1de;
$tb-dark-primary-color: #9fa8da;

6
ui-ngx/src/theme.scss

@ -21,12 +21,6 @@
@include mat.all-component-typographies(); @include mat.all-component-typographies();
@include mat.core(); @include mat.core();
$tb-primary-color: #305680;
$tb-secondary-color: #527dad;
$tb-hue3-color: #a7c1de;
$tb-dark-primary-color: #9fa8da;
$tb-mat-indigo: ( $tb-mat-indigo: (
50: #e8eaf6, 50: #e8eaf6,
100: #c5cae9, 100: #c5cae9,

Loading…
Cancel
Save