Browse Source

UI: Single switch widget improvements: Implement disabled state. Improve auto-scale.

pull/10132/head
Igor Kulikov 3 years ago
parent
commit
8262be6e64
  1. 11
      ui-ngx/src/app/modules/home/components/widget/config/basic/rpc/single-switch-basic-config.component.html
  2. 2
      ui-ngx/src/app/modules/home/components/widget/config/basic/rpc/single-switch-basic-config.component.ts
  3. 6
      ui-ngx/src/app/modules/home/components/widget/lib/rpc/single-switch-widget.component.html
  4. 8
      ui-ngx/src/app/modules/home/components/widget/lib/rpc/single-switch-widget.component.scss
  5. 54
      ui-ngx/src/app/modules/home/components/widget/lib/rpc/single-switch-widget.component.ts
  6. 17
      ui-ngx/src/app/modules/home/components/widget/lib/rpc/single-switch-widget.models.ts
  7. 11
      ui-ngx/src/app/modules/home/components/widget/lib/settings/control/single-switch-widget-settings.component.html
  8. 3
      ui-ngx/src/app/modules/home/components/widget/lib/settings/control/single-switch-widget-settings.component.ts
  9. 5
      ui-ngx/src/assets/locale/locale.constant-en_US.json

11
ui-ngx/src/app/modules/home/components/widget/config/basic/rpc/single-switch-basic-config.component.html

@ -52,6 +52,17 @@
[widgetType]="widgetType"
formControlName="offUpdateState"></tb-set-value-action-settings>
</div>
<div class="tb-form-row">
<div class="fixed-title-width" tb-hint-tooltip-icon="{{'widgets.rpc-state.disabled-state-hint' | translate}}" translate>widgets.rpc-state.disabled-state</div>
<tb-get-value-action-settings fxFlex
panelTitle="widgets.rpc-state.disabled-state"
[valueType]="valueType.BOOLEAN"
stateLabel="widgets.rpc-state.disabled"
[aliasController]="aliasController"
[targetDevice]="targetDevice"
[widgetType]="widgetType"
formControlName="disabledState"></tb-get-value-action-settings>
</div>
</div>
<div class="tb-form-panel">
<div class="tb-form-panel-title" translate>widget-config.appearance</div>

2
ui-ngx/src/app/modules/home/components/widget/config/basic/rpc/single-switch-basic-config.component.ts

@ -70,6 +70,7 @@ export class SingleSwitchBasicConfigComponent extends BasicWidgetConfigComponent
initialState: [settings.initialState, []],
onUpdateState: [settings.onUpdateState, []],
offUpdateState: [settings.offUpdateState, []],
disabledState: [settings.disabledState, []],
layout: [settings.layout, []],
autoScale: [settings.autoScale, []],
@ -120,6 +121,7 @@ export class SingleSwitchBasicConfigComponent extends BasicWidgetConfigComponent
this.widgetConfig.config.settings.initialState = config.initialState;
this.widgetConfig.config.settings.onUpdateState = config.onUpdateState;
this.widgetConfig.config.settings.offUpdateState = config.offUpdateState;
this.widgetConfig.config.settings.disabledState = config.disabledState;
this.widgetConfig.config.settings.layout = config.layout;
this.widgetConfig.config.settings.autoScale = config.autoScale;

6
ui-ngx/src/app/modules/home/components/widget/lib/rpc/single-switch-widget.component.html

@ -15,8 +15,8 @@
limitations under the License.
-->
<div #singleSwitchPanel class="tb-single-switch-panel" [style.pointer-events]="ctx.isEdit ? 'none' : 'all'" [style]="backgroundStyle$ | async">
<div class="tb-single-switch-overlay" [style]="overlayStyle"></div>
<div #singleSwitchPanel class="tb-single-switch-panel" [class.auto-scale]="autoScale" [style.pointer-events]="ctx.isEdit ? 'none' : 'all'" [style]="backgroundStyle$ | async">
<div class="tb-single-switch-overlay" [style]="overlayStyle" [style.inset]="overlayInset"></div>
<div class="tb-single-switch-title-panel">
<ng-container *ngTemplateOutlet="widgetTitlePanel"></ng-container>
</div>
@ -27,7 +27,7 @@
</div>
<div #singleSwitchToggleRow class="tb-single-switch-slide-toggle-row">
<div *ngIf="showOffLabel" [style]="offLabelStyle">{{ offLabel }}</div>
<mat-slide-toggle class="tb-single-switch-toggle" [disabled]="loading$ | async" [(ngModel)]="value" (click)="onToggleChange($event)">
<mat-slide-toggle class="tb-single-switch-toggle" [disabled]="disabled || (loading$ | async)" [(ngModel)]="value" (click)="!disabled && onToggleChange($event)">
</mat-slide-toggle>
<div *ngIf="showOnLabel" [style]="onLabelStyle">{{ onLabel }}</div>
</div>

8
ui-ngx/src/app/modules/home/components/widget/lib/rpc/single-switch-widget.component.scss

@ -29,15 +29,15 @@ $switchColorDisabled: var(--tb-single-switch-color-disabled, #D5D7E5);
align-items: center;
justify-content: center;
padding: 18px 24px;
&.auto-scale {
padding: 0;
}
> div:not(.tb-single-switch-overlay), > tb-icon {
z-index: 1;
}
.tb-single-switch-overlay {
position: absolute;
top: 12px;
left: 12px;
bottom: 12px;
right: 12px;
inset: 12px;
}
.tb-single-switch-progress {
position: absolute;

54
ui-ngx/src/app/modules/home/components/widget/lib/rpc/single-switch-widget.component.ts

@ -45,6 +45,7 @@ import { DomSanitizer } from '@angular/platform-browser';
import { ValueType } from '@shared/models/constants';
import { UtilsService } from '@core/services/utils.service';
const initialSwitchHeight = 60;
const horizontalLayoutPadding = 48;
const verticalLayoutPadding = 36;
@ -73,8 +74,10 @@ export class SingleSwitchWidgetComponent extends
backgroundStyle$: Observable<ComponentStyle>;
overlayStyle: ComponentStyle = {};
overlayInset = '12px';
value = false;
disabled = false;
layout: SingleSwitchLayout;
@ -159,6 +162,12 @@ export class SingleSwitchWidgetComponent extends
next: (value) => this.onValue(value)
});
const disabledStateSettings =
{...this.settings.disabledState, actionLabel: this.ctx.translate.instant('widgets.rpc-state.disabled-state')};
this.createValueGetter(disabledStateSettings, ValueType.BOOLEAN, {
next: (value) => this.onDisabled(value)
});
const onUpdateStateSettings = {...this.settings.onUpdateState,
actionLabel: this.ctx.translate.instant('widgets.rpc-state.turn-on')};
this.onValueSetter = this.createValueSetter(onUpdateStateSettings);
@ -216,20 +225,59 @@ export class SingleSwitchWidgetComponent extends
this.cd.markForCheck();
}
private onDisabled(value: boolean): void {
this.disabled = !!value;
if (this.disabled) {
if (this.showLabel) {
this.labelStyle = {...this.labelStyle, color: 'rgba(0, 0, 0, 0.38)'};
}
if (this.showIcon) {
this.iconStyle = {...this.iconStyle, color: 'rgba(0, 0, 0, 0.38)'};
}
if (this.showOnLabel) {
this.onLabelStyle = {...this.onLabelStyle, color: 'rgba(0, 0, 0, 0.38)'};
}
if (this.showOffLabel) {
this.offLabelStyle = {...this.offLabelStyle, color: 'rgba(0, 0, 0, 0.38)'};
}
} else {
if (this.showLabel) {
this.labelStyle = {...this.labelStyle, color: this.settings.labelColor};
}
if (this.showIcon) {
this.iconStyle = {...this.iconStyle, color: this.settings.iconColor};
}
if (this.showOnLabel) {
this.onLabelStyle = {...this.onLabelStyle, color: this.settings.onLabelColor};
}
if (this.showOffLabel) {
this.offLabelStyle = {...this.offLabelStyle, color: this.settings.offLabelColor};
}
}
this.cd.markForCheck();
}
private onResize() {
const panelWidth = this.singleSwitchPanel.nativeElement.getBoundingClientRect().width - horizontalLayoutPadding;
const panelHeight = this.singleSwitchPanel.nativeElement.getBoundingClientRect().height - verticalLayoutPadding;
const height = this.singleSwitchPanel.nativeElement.getBoundingClientRect().height;
const switchScale = height / initialSwitchHeight;
const paddingScale = Math.min(switchScale, 1);
const panelWidth = this.singleSwitchPanel.nativeElement.getBoundingClientRect().width - (horizontalLayoutPadding * paddingScale);
const panelHeight = this.singleSwitchPanel.nativeElement.getBoundingClientRect().height - (verticalLayoutPadding * paddingScale);
this.renderer.setStyle(this.singleSwitchContent.nativeElement, 'transform', `scale(1)`);
this.renderer.setStyle(this.singleSwitchContent.nativeElement, 'width', 'auto');
let contentWidth = this.singleSwitchToggleRow.nativeElement.getBoundingClientRect().width;
let contentHeight = this.singleSwitchToggleRow.nativeElement.getBoundingClientRect().height;
if (this.showIcon || this.showLabel) {
contentWidth += (8 + this.singleSwitchLabelRow.nativeElement.getBoundingClientRect().width);
contentHeight = Math.max(contentHeight, this.singleSwitchLabelRow.nativeElement.getBoundingClientRect().height);
}
const scale = Math.min(panelWidth / contentWidth, panelHeight / contentHeight);
const maxScale = Math.max(1, switchScale);
const scale = Math.min(Math.min(panelWidth / contentWidth, panelHeight / contentHeight), maxScale);
const width = panelWidth / scale;
this.renderer.setStyle(this.singleSwitchContent.nativeElement, 'width', width + 'px');
this.renderer.setStyle(this.singleSwitchContent.nativeElement, 'transform', `scale(${scale})`);
this.overlayInset = (Math.floor(12 * paddingScale * 100) / 100) + 'px';
this.cd.markForCheck();
}
}

17
ui-ngx/src/app/modules/home/components/widget/lib/rpc/single-switch-widget.models.ts

@ -51,6 +51,7 @@ export const singleSwitchLayoutImages = new Map<SingleSwitchLayout, string>(
export interface SingleSwitchWidgetSettings {
initialState: GetValueSettings<boolean>;
disabledState: GetValueSettings<boolean>;
onUpdateState: SetValueSettings;
offUpdateState: SetValueSettings;
layout: SingleSwitchLayout;
@ -104,6 +105,22 @@ export const singleSwitchDefaultSettings: SingleSwitchWidgetSettings = {
dataToValueFunction: '/* Should return boolean value */\nreturn data;'
}
},
disabledState: {
action: GetValueAction.DO_NOTHING,
defaultValue: false,
getAttribute: {
key: 'state',
scope: null
},
getTimeSeries: {
key: 'state'
},
dataToValue: {
type: DataToValueType.NONE,
compareToValue: true,
dataToValueFunction: '/* Should return boolean value */\nreturn data;'
}
},
onUpdateState: {
action: SetValueAction.EXECUTE_RPC,
executeRpc: {

11
ui-ngx/src/app/modules/home/components/widget/lib/settings/control/single-switch-widget-settings.component.html

@ -51,6 +51,17 @@
[widgetType]="widgetType"
formControlName="offUpdateState"></tb-set-value-action-settings>
</div>
<div class="tb-form-row">
<div class="fixed-title-width" tb-hint-tooltip-icon="{{'widgets.rpc-state.disabled-state-hint' | translate}}" translate>widgets.rpc-state.disabled-state</div>
<tb-get-value-action-settings fxFlex
panelTitle="widgets.rpc-state.disabled-state"
[valueType]="valueType.BOOLEAN"
stateLabel="widgets.rpc-state.disabled"
[aliasController]="aliasController"
[targetDevice]="targetDevice"
[widgetType]="widgetType"
formControlName="disabledState"></tb-get-value-action-settings>
</div>
</div>
<div class="tb-form-panel">
<div class="tb-form-panel-title" translate>widget-config.card-style</div>

3
ui-ngx/src/app/modules/home/components/widget/lib/settings/control/single-switch-widget-settings.component.ts

@ -69,6 +69,7 @@ export class SingleSwitchWidgetSettingsComponent extends WidgetSettingsComponent
initialState: [settings.initialState, []],
onUpdateState: [settings.onUpdateState, []],
offUpdateState: [settings.offUpdateState, []],
disabledState: [settings.disabledState, []],
layout: [settings.layout, []],
autoScale: [settings.autoScale, []],
@ -109,7 +110,7 @@ export class SingleSwitchWidgetSettingsComponent extends WidgetSettingsComponent
return ['showLabel', 'showIcon', 'showOnLabel', 'showOffLabel'];
}
protected updateValidators(emitEvent: boolean): void {
protected updateValidators(_emitEvent: boolean): void {
const showLabel: boolean = this.singleSwitchWidgetSettingsForm.get('showLabel').value;
const showIcon: boolean = this.singleSwitchWidgetSettingsForm.get('showIcon').value;
const showOnLabel: boolean = this.singleSwitchWidgetSettingsForm.get('showOnLabel').value;

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

@ -6522,12 +6522,15 @@
"rpc-state": {
"initial-state": "Initial state",
"initial-state-hint": "Action to get the initial value of the component.",
"disabled-state": "Disabled state",
"disabled-state-hint": "Condition under which the component is disabled.",
"turn-on": "Turn 'On'",
"turn-on-hint": "Action performed to turn ON the component.",
"turn-off": "Turn 'Off'",
"turn-off-hint": "Action performed to turn OFF the component.",
"on": "On",
"off": "Off"
"off": "Off",
"disabled": "Disabled"
},
"value-action": {
"do-nothing": "Do nothing",

Loading…
Cancel
Save