Skip to content

Commit

Permalink
Merge branch 'big-ts-refactoring' into type-inference
Browse files Browse the repository at this point in the history
Signed-off-by: Bluefox <[email protected]>
  • Loading branch information
GermanBluefox authored Mar 12, 2024
2 parents 2ffc08a + b6bd813 commit 6c523ff
Show file tree
Hide file tree
Showing 10 changed files with 304 additions and 300 deletions.
6 changes: 4 additions & 2 deletions lib/updating.html
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
<html>
<head>
<title>Updating</title>
<link rel="shortcut icon" href="favicon.ico" />

<title>Updating</title>
<script>
let originalPageSize = 0;
function getMyself() {
Expand Down Expand Up @@ -95,4 +97,4 @@ <h4>The vis is updating just now...</h4>
</div>
</div>
</body>
</html>
</html>
2 changes: 1 addition & 1 deletion main.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
*
* iobroker vis-2 Adapter
*
* Copyright (c) 2021-2023, bluefox
* Copyright (c) 2021-2024, bluefox
*
* CC-NC-BY 4.0 License
*
Expand Down
2 changes: 1 addition & 1 deletion src/src/App.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -1498,7 +1498,7 @@ class App extends Runtime {
</IconButton>
</div>
</Tooltip> : null}
{this.state.hideAttributes ? <Tooltip title={I18n.t('Show palette')}>
{this.state.hideAttributes ? <Tooltip title={I18n.t('Show attributes')}>
<div className={this.props.classes.tabButton}>
<IconButton
size="small"
Expand Down
5 changes: 3 additions & 2 deletions src/src/Attributes/index.jsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import PropTypes from 'prop-types';
import { withStyles } from '@mui/styles';
import { useEffect, useState } from 'react';
import React, { useEffect, useState } from 'react';

import {
IconButton,
Expand All @@ -10,7 +10,7 @@ import {
import {
Clear as ClearIcon,
UnfoldMore as UnfoldMoreIcon,
UnfoldLess as UnfoldLessIcon,
UnfoldLess as UnfoldLessIcon, ListAlt as IconAttributes,
} from '@mui/icons-material';

import { I18n, Utils } from '@iobroker/adapter-react-v5';
Expand Down Expand Up @@ -69,6 +69,7 @@ const Attributes = props => {
height: 34,
}}
>
<IconAttributes style={{ marginTop: 4, marginRight: 4 }} />
{I18n.t('Attributes')}
<div style={{ flex: 1 }}></div>
{selected === 'View' || selected === 'Widget' ? <div style={{ textAlign: 'right' }}>
Expand Down
2 changes: 1 addition & 1 deletion src/src/Palette/index.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -269,7 +269,7 @@ const Palette = props => {
className={Utils.clsx(props.classes.blockHeader, props.classes.lightedPanel)}
style={{ display: 'flex', lineHeight: '34px' }}
>
<IconPalette />
<IconPalette style={{ marginTop: 4, marginRight: 4 }} />
<span style={{ verticalAlign: 'middle' }}>{I18n.t('Palette')}</span>
<div style={{ flex: 1 }} />
{!allOpened ? <Tooltip title={I18n.t('Expand all')}>
Expand Down
46 changes: 20 additions & 26 deletions src/src/Vis/visBaseWidget.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -93,11 +93,11 @@ export interface WidgetStyleState extends WidgetStyle {
_originalData?: string;
}

interface VisBaseWidgetStateUpdate {
data?: WidgetDataState | GroupDataState;
style?: WidgetStyleState;
export interface VisBaseWidgetState {
data: WidgetDataState | GroupDataState;
style: WidgetStyleState;
editMode: boolean;
rxStyle?: WidgetStyleState;
editMode?: boolean;
applyBindings?: false | true | { top: string | number; left: string | number };
multiViewWidget?: boolean;
selected?: boolean;
Expand All @@ -112,12 +112,6 @@ interface VisBaseWidgetStateUpdate {
showRelativeMoveMenu?: boolean;
}

export interface VisBaseWidgetState extends VisBaseWidgetStateUpdate {
data: WidgetDataState | GroupDataState;
style: WidgetStyleState;
editMode: boolean;
}

export interface VisBaseWidgetMovement {
top: number;
left: number;
Expand Down Expand Up @@ -158,40 +152,40 @@ class VisBaseWidget<TState extends Partial<VisBaseWidgetState> = VisBaseWidgetSt
static FORBIDDEN_CHARS = /[^._\-/ :!#$%&()+=@^{}|~]+/g; // from https://github.com/ioBroker/ioBroker.js-controller/blob/master/packages/common/lib/common/tools.js

/** We do not store the SVG Element in the state because it is cyclic */
relativeMoveMenu?: EventTarget & SVGSVGElement;
private relativeMoveMenu?: EventTarget & SVGSVGElement;

/** if currently resizing */
resize: Resize = false;
private resize: Resize = false;

readonly uuid = `${Date.now()}.${Math.round(Math.random() * 1_000_000)}`;
private readonly uuid = `${Date.now()}.${Math.round(Math.random() * 1_000_000)}`;

refService = React.createRef<HTMLDivElement>();
protected refService = React.createRef<HTMLDivElement>();

widDiv: null | HTMLDivElement = null;
protected widDiv: null | HTMLDivElement = null;

readonly onCommandBound: typeof this.onCommand;

onResize: undefined | (() => void);
private onResize: undefined | (() => void);

updateInterval?: ReturnType<typeof setTimeout>;
private updateInterval?: ReturnType<typeof setTimeout>;

pressTimeout?: ReturnType<typeof setTimeout>;
private pressTimeout?: ReturnType<typeof setTimeout>;

shadowDiv: any;
private shadowDiv: any;

stealCursor?: string;
private stealCursor?: string;

beforeIncludeColor?: string;
private beforeIncludeColor?: string;

lastClick?: number;
private lastClick?: number;

movement?: VisBaseWidgetMovement;
protected movement?: VisBaseWidgetMovement;

protected resizeLocked?: boolean;

visDynamicResizable: any;
protected visDynamicResizable: undefined | null | { default: boolean; desiredSize: { width: number; height: number } | boolean };

isCanWidget?: boolean;
protected isCanWidget?: boolean;

constructor(props: VisBaseWidgetProps) {
super(props);
Expand Down Expand Up @@ -373,7 +367,7 @@ class VisBaseWidget<TState extends Partial<VisBaseWidgetState> = VisBaseWidgetSt

static getDerivedStateFromProps(props: VisBaseWidgetProps, state: VisBaseWidgetState) {
const context = props.context;
let newState: VisBaseWidgetStateUpdate | null = null; // No change to state by default
let newState: Partial<VisBaseWidgetState> | null = null; // No change to state by default
let widget = context.views[props.view].widgets[props.id];
const gap = widget.style.position === 'relative' ?
(isVarFinite(context.views[props.view].settings?.rowGap) ? parseFloat(context.views[props.view].settings?.rowGap as string) : 0) : 0;
Expand Down
15 changes: 9 additions & 6 deletions src/src/Vis/visRxWidget.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ import { Connection, I18n, Icon } from '@iobroker/adapter-react-v5';

import {
Project, AnyWidgetId, RxWidgetInfo,
WidgetData, VisRxWidgetStateValues,
WidgetData, VisRxWidgetStateValues, RxWidgetInfoAttributes,
} from '@/types';
import { deepClone, calculateOverflow } from '@/Utils/utils';
// eslint-disable-next-line import/no-cycle
Expand Down Expand Up @@ -112,7 +112,7 @@ export interface CustomWidgetProperties {
export interface VisRxWidgetState extends VisBaseWidgetState {
rxData: RxData;
values: VisRxWidgetStateValues;
visible?: boolean;
visible: boolean;
disabled?: boolean;
}

Expand Down Expand Up @@ -155,7 +155,7 @@ class VisRxWidget<TRxData extends Record<string, any>, TState extends Partial<Vi
constructor(props: VisRxWidgetProps) {
super(props);

const options = this.getWidgetInfo();
const options: RxWidgetInfo = this.getWidgetInfo() as RxWidgetInfo;

const widgetAttrInfo: Record<string, any> = {};
// collect all attributes (only types)
Expand Down Expand Up @@ -191,9 +191,12 @@ class VisRxWidget<TRxData extends Record<string, any>, TState extends Partial<Vi

// find in fields visResizable name
// if resizable exists, take the resizable from data
this.visDynamicResizable = VisRxWidget.findField(options, 'visResizable');
if (this.visDynamicResizable) {
this.visDynamicResizable = { default: this.visDynamicResizable.default !== undefined ? this.visDynamicResizable.default : true, desiredSize: this.visDynamicResizable.desiredSize };
const visResizable = VisRxWidget.findField(options, 'visResizable');
if (visResizable) {
this.visDynamicResizable = {
default: visResizable.default !== undefined ? visResizable.default : true,
desiredSize: visResizable.desiredSize,
};
} else {
this.visDynamicResizable = null;
}
Expand Down
98 changes: 49 additions & 49 deletions src/src/allInOneTypes.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,37 +6,37 @@ import { AnyWidgetId, Project, WidgetData } from '@/types';
export type RxWidgetAttributeType = 'text' | 'delimiter' | 'help' | 'html' | 'json' | 'id' | 'instance' | 'select' | 'nselect' | 'auto' | 'checkbox' | 'number' | 'select-views' | 'custom' | 'image' | 'color' | 'password' | 'history' | 'hid' | 'icon' | 'dimension' | 'fontname' | 'groups' | 'class' | 'filters' | 'views' | 'style' | 'icon64' | string;

export interface RxWidgetInfoCustomComponentContext {
socket: Connection;
projectName: string;
instance: number;
adapterName: string;
views: Project;
};
readonly socket: Connection;
readonly projectName: string;
readonly instance: number;
readonly adapterName: string;
readonly views: Project;
}

export interface RxWidgetInfoCustomComponentProperties {
context: RxWidgetInfoCustomComponentContext;
selectedView: string;
selectedWidgets: AnyWidgetId[];
selectedWidget: AnyWidgetId;
readonly context: RxWidgetInfoCustomComponentContext;
readonly selectedView: string;
readonly selectedWidgets: AnyWidgetId[];
readonly selectedWidget: AnyWidgetId;
}

export type RxWidgetInfoAttributesField = {
/** Field type */
type?: RxWidgetAttributeType;
readonly type?: RxWidgetAttributeType;
/** Field default value */
default?: string | number | boolean;
readonly default?: string | number | boolean;
/** if true, no edit button will be shown. Default is true. */
noButton?: boolean;
readonly noButton?: boolean;
/** if true, the text will not be translated */
noTranslation?: boolean;
readonly noTranslation?: boolean;
/** this style will be applied to the text */
style?: React.CSSProperties;
readonly style?: React.CSSProperties;
/** show multi-line editor */
multiline?: boolean;
readonly multiline?: boolean;
/** Do not write 'nothing_selected' into the field by creation */
noInit?: boolean;
readonly noInit?: boolean;
/** Do not subscribe on changes of the object */
noSubscribe?: boolean;
readonly noSubscribe?: boolean;
/** Filter of objects (not JSON string, it is an object), like:
- `{common: {custom: true}}` - show only objects with some custom settings
- `{common: {custom: 'sql.0'}}` - show only objects with sql.0 custom settings (only of the specific instance)
Expand All @@ -46,69 +46,69 @@ export type RxWidgetInfoAttributesField = {
- `{type: ['channel', 'device']}` - show only channels and devices
- `{common: {type: 'number'}` - show only states of type 'number
- `{common: {type: ['number', 'string']}` - show only states of type 'number and string
- `{common: {role: 'switch']}` - show only states with roles starting from switch
- `{common: {role: 'switch'}` - show only states with roles starting from switch
- `{common: {role: ['switch', 'button]}` - show only states with roles starting from `switch` and `button`
*/
filter?: {
common?: {
custom?: true | string | '_dataSources';
type?: ioBroker.CommonType | ioBroker.CommonType[];
role?: string | string[];
readonly filter?: {
readonly common?: {
readonly custom?: true | string | '_dataSources';
readonly type?: ioBroker.CommonType | ioBroker.CommonType[];
readonly role?: string | string[];
};
type?: ioBroker.ObjectType | ioBroker.ObjectType[];
readonly type?: ioBroker.ObjectType | ioBroker.ObjectType[];
} | string;
/** Additionally, you can provide `adapter` to filter the instances of specific adapter. With special adapter name `_dataSources` you can get all adapters with flag `common.getHistory`. */
adapter?: string;
readonly adapter?: string;
/** In this case only instance number (like `0`) is shown and not `history.0`. It can be set to true only with non-empty `adapter` setting. */
iShort?: boolean;
readonly iShort?: boolean;
/** Options for select type */
options?: { value: string; label: string }[] | string[];
readonly options?: { readonly value: string; readonly label: string }[] | string[];
/** Number min value */
min?: number;
readonly min?: number;
/** Number max value */
max? : number;
readonly max?: number;
/** Number step */
step? : number;
readonly step?: number;
/** Slider marks?: array of possible marks. Like `[{value: 1, label: 'one'}, {value: 10}, {value: 100}] */
marks?: { value: number; label: string }[];
readonly marks?: { readonly value: number; readonly label: string }[];
/** Controls when the value label is displayed: `auto` the value label will display when the thumb is hovered or focused. `on` will display persistently. `off` will never display. */
valueLabelDisplay?: 'on' | 'off' | 'auto';
readonly valueLabelDisplay?: 'on' | 'off' | 'auto';
/** type of the widget, like `tplMaterial2Switches` */
tpl?: string;
readonly tpl?: string;
/** if true, all widgets of all views will be shown, not only from the current view. Default is false. */
all?: boolean;
readonly all?: boolean;
/** if true, grouped widgets will be shown too. Default is false. */
withGroups?: boolean;
readonly withGroups?: boolean;
/** if true, current widget will be shown in the list too. */
withSelf?: boolean;
readonly withSelf?: boolean;
/** if true, it will be checked if the widget is used somewhere else and user will be asked. */
checkUsage?: boolean;
readonly checkUsage?: boolean;
/** if true, only widgets will be shown, which are not used in some view. Default is false. */
hideUsed?: boolean;
readonly hideUsed?: boolean;
/** if false, only one view can be selected. Default is true. */
multiple?: boolean;
readonly multiple?: boolean;
/** if false, only one view can be selected. Default is true. */
component?: (
readonly component?: (
field: RxWidgetInfoAttributesField,
data: WidgetData,
onDataChange: (newData: WidgetData) => void,
props: RxWidgetInfoCustomComponentProperties,
) => React.JSX.Element | React.JSX.Element[] ;

/** Name of the widget field */
name: string;
readonly name: string;
/** Field label (i18n) */
label?: string;
readonly label?: string;
/** JS Function for conditional visibility */
hidden?: string | ((data: any) => boolean) | ((data: any, index: number) => boolean);
readonly hidden?: string | ((data: any) => boolean) | ((data: any, index: number) => boolean);
/** Tooltip (i18n) */
tooltip?: string;
readonly tooltip?: string;
/** JS Function for conditional disability */
disabled?: string | ((data: any) => boolean) | ((data: any, index: number) => boolean);
readonly disabled?: string | ((data: any) => boolean) | ((data: any, index: number) => boolean);
/** JS Function for error */
error?: string | ((data: any) => boolean) | ((data: any, index: number) => boolean);
readonly error?: string | ((data: any) => boolean) | ((data: any, index: number) => boolean);
/** Do not show binding symbol fot this field */
noBinding?: boolean;
readonly noBinding?: boolean;
/** Callback called if the field value changed */
onChange?: (field: WidgetAttributeInfo, data: Record<string, any>, changeData: (newData: Record<string, any>) => void, socket: Connection, index?: number) => Promise<void>;
readonly onChange?: (field: WidgetAttributeInfo, data: Record<string, any>, changeData: (newData: Record<string, any>) => void, socket: Connection, index?: number) => Promise<void>;
}
Loading

0 comments on commit 6c523ff

Please sign in to comment.