Skip to content
Snippets Groups Projects
Commit 96944582 authored by Loïc Correnson's avatar Loïc Correnson
Browse files

[dome/controls] meter controls

parent 79221590
No related branches found
No related tags found
No related merge requests found
......@@ -32,7 +32,6 @@
import React from 'react';
import { classes } from 'dome/misc/utils';
import { Icon } from './icons';
import { LabelProps } from './labels';
import './style.css';
interface EVENT {
......@@ -48,68 +47,6 @@ const TRIGGER = (onClick?: () => void) => (evt?: EVENT) => {
if (onClick) onClick();
};
// --------------------------------------------------------------------------
// --- LCD
// --------------------------------------------------------------------------
/** Button-like label. */
export function LCD(props: LabelProps) {
const className = classes(
'dome-xButton dome-xBoxButton dome-text-code dome-xButton-lcd ',
props.className,
);
return (
<label
className={className}
title={props.title}
style={props.style}
>
{props.icon && <Icon id={props.icon} />}
{props.label}
{props.children}
</label>
);
}
// --------------------------------------------------------------------------
// --- Led
// --------------------------------------------------------------------------
export type LEDstatus =
undefined | 'inactive' | 'active' | 'positive' | 'negative' | 'warning';
export interface LEDprops {
/**
Led status:
- `'inactive'`: off (default)
- `'active'`: blue color
- `'positive'`: green color
- `'negative'`: red color
- `'warning'`: orange color
*/
status?: LEDstatus;
/** Blinking Led (default: `false`). */
blink?: boolean;
/** Tooltip text. */
title?: string;
/** Additional CSS class. */
className?: string;
/** Additional CSS style. */
style?: React.CSSProperties;
}
export const LED = (props: LEDprops) => {
const className = classes(
'dome-xButton-led',
`dome-xButton-led-${props.status || 'inactive'}`,
props.blink && 'dome-xButton-blink',
props.className,
);
return (
<div className={className} title={props.title} style={props.style} />
);
};
// --------------------------------------------------------------------------
// --- Button
// --------------------------------------------------------------------------
......
/* ************************************************************************ */
/* */
/* This file is part of Frama-C. */
/* */
/* Copyright (C) 2007-2021 */
/* CEA (Commissariat à l'énergie atomique et aux énergies */
/* alternatives) */
/* */
/* you can redistribute it and/or modify it under the terms of the GNU */
/* Lesser General Public License as published by the Free Software */
/* Foundation, version 2.1. */
/* */
/* It is distributed in the hope that it will be useful, */
/* but WITHOUT ANY WARRANTY; without even the implied warranty of */
/* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the */
/* GNU Lesser General Public License for more details. */
/* */
/* See the GNU Lesser General Public License version 2.1 */
/* for more details (enclosed in the file licenses/LGPLv2.1). */
/* */
/* ************************************************************************ */
// --------------------------------------------------------------------------
// --- LEDs, LCD, meters, etc.
// --------------------------------------------------------------------------
/**
@packageDocumentation
@module dome/controls/displays
*/
import React from 'react';
import { classes } from 'dome/misc/utils';
import { Icon } from './icons';
import { LabelProps } from './labels';
import './style.css';
// --------------------------------------------------------------------------
// --- LCD
// --------------------------------------------------------------------------
/** Button-like label. */
export function LCD(props: LabelProps) {
const className = classes(
'dome-xButton dome-xBoxButton dome-text-code dome-xButton-lcd ',
props.className,
);
return (
<label
className={className}
title={props.title}
style={props.style}
>
{props.icon && <Icon id={props.icon} />}
{props.label}
{props.children}
</label>
);
}
// --------------------------------------------------------------------------
// --- Led
// --------------------------------------------------------------------------
export type LEDstatus =
undefined | 'inactive' | 'active' | 'positive' | 'negative' | 'warning';
export interface LEDprops {
/**
Led status:
- `'inactive'`: off (default)
- `'active'`: blue color
- `'positive'`: green color
- `'negative'`: red color
- `'warning'`: orange color
*/
status?: LEDstatus;
/** Blinking Led (default: `false`). */
blink?: boolean;
/** Tooltip text. */
title?: string;
/** Additional CSS class. */
className?: string;
/** Additional CSS style. */
style?: React.CSSProperties;
}
export const LED = (props: LEDprops) => {
const className = classes(
'dome-xButton-led',
`dome-xButton-led-${props.status || 'inactive'}`,
props.blink && 'dome-xButton-blink',
props.className,
);
return (
<div className={className} title={props.title} style={props.style} />
);
};
// --------------------------------------------------------------------------
// --- Metter
// --------------------------------------------------------------------------
export interface MeterProps {
/** Additional CSS class. */
className?: string;
/** Additional CSS style. */
style?: React.CSSProperties;
/** Disabled control. */
/** Meter value. Undefined means disabled. */
value: number; /** default is undefined */
min?: number; /** default is 0.0 */
low?: number; /** default is 0.0 */
high?: number; /** default is 1.0 */
max?: number; /** default is 1.0 */
optimum?: number | 'LOW' | 'MEDIUM' | 'HIGH'; /** default is undefined */
}
export const Meter = (props: MeterProps) => {
const { className, style, value, optimum, ...ms } = props;
const min = props.min ?? 0.0;
const max = props.max ?? 1.0;
const low = props.low ?? min;
const hight = props.high ?? max;
const theClass = classes('dome-xMeter', className);
let opt: number | undefined;
if (value !== undefined)
switch (optimum) {
case 'LOW': opt = (min + low) / 2; break;
case 'MEDIUM': opt = (low + hight) / 2; break;
case 'HIGH': opt = (hight + max) / 2; break;
default: opt = optimum;
}
const mv = value === undefined ? min : Math.min(max, Math.max(min, value));
return (
<meter
className={theClass}
style={style}
value={mv}
optimum={opt}
{...ms} />
);
};
// --------------------------------------------------------------------------
......@@ -248,6 +248,38 @@
background: radial-gradient( circle at center , #ffc749 , #ecd44f );
}
/* -------------------------------------------------------------------------- */
/* --- Styling Meters --- */
/* -------------------------------------------------------------------------- */
meter.dome-xMeter {
background: white;
border-radius: 5px;
box-shadow:
0 0 4px 4px rgba(0,0,0,0.15) inset;
height: 16px;
width: 70px;
}
meter.dome-xMeter::-webkit-meter-bar {
background: transparent;
border-radius: 5px;
height: 14px;
}
meter.dome-xMeter::-webkit-meter-optimum-value {
background: linear-gradient(to bottom, #4a0 0%, #8f0 20%, #4a0 100%);
}
meter.dome-xMeter::-webkit-meter-suboptimum-value {
background: linear-gradient(to bottom, #aa0 0%, #ff0 20%, #aa0 100%);
}
meter.dome-xMeter::-webkit-meter-even-less-good-value {
background: linear-gradient(to bottom, #a40 0%, #f80 20%, #a40 100%);
}
/* -------------------------------------------------------------------------- */
/* --- Styling Checkbox --- */
/* -------------------------------------------------------------------------- */
......
......@@ -26,7 +26,8 @@
import React from 'react';
import { Code } from 'dome/controls/labels';
import { LED, IconButton } from 'dome/controls/buttons';
import { IconButton } from 'dome/controls/buttons';
import { LED } from 'dome/controls/displays';
import { Icon } from 'dome/controls/icons';
import * as Toolbars from 'dome/frame/toolbars';
import { GlobalState, useGlobalState } from 'dome/data/states';
......
......@@ -21,6 +21,7 @@
/* ************************************************************************ */
import React from 'react';
import { Meter } from 'dome/controls/displays';
export interface CoverageProps {
reachable: number;
......@@ -37,12 +38,12 @@ export default function(props: { coverage: CoverageProps }) {
const total = reachable + dead;
return (
<meter
<Meter
min={0}
max={total}
low={0.50 * total}
high={0.85 * total}
optimum={total}
optimum='HIGH'
value={reachable}
/>
);
......
......@@ -22,12 +22,11 @@
// React & Dome
import React from 'react';
import { LED } from 'dome/controls/displays';
import * as Ivette from 'ivette';
import * as States from 'frama-c/states';
import * as Eva from 'frama-c/api/plugins/eva/general';
import { LED } from 'dome/controls/buttons';
import CoverageMeter, { percent } from './CoverageMeter';
import './summary.css';
......@@ -143,10 +142,10 @@ function Alarms(data: Eva.programStatsType,
</tbody>
</table>
{invalid > 0 && (
<div>
{invalid} of them {invalid === 1 ? 'is a' : 'are'} sure
alarm{plural(invalid)}.
</div>
<div>
{invalid} of them {invalid === 1 ? 'is a' : 'are'} sure
alarm{plural(invalid)}.
</div>
)}
</>
);
......
......@@ -30,7 +30,8 @@ import * as Json from 'dome/data/json';
import * as Settings from 'dome/data/settings';
import * as Toolbars from 'dome/frame/toolbars';
import { LED, LEDstatus, IconButton } from 'dome/controls/buttons';
import { IconButton } from 'dome/controls/buttons';
import { LED, LEDstatus } from 'dome/controls/displays';
import { Label, Code } from 'dome/controls/labels';
import { RichTextBuffer } from 'dome/text/buffers';
import { Text } from 'dome/text/editors';
......
......@@ -67,32 +67,3 @@
}
/* -------------------------------------------------------------------------- */
/* --- Meters --- */
/* -------------------------------------------------------------------------- */
meter {
background: white;
border-radius: 5px;
box-shadow:
0 0 4px 4px rgba(0,0,0,0.15) inset;
height: 16px;
width: 70px;
}
meter::-webkit-meter-bar {
background: transparent;
border-radius: 5px;
height: 14px;
}
meter::-webkit-meter-optimum-value {
background: linear-gradient(to bottom, #4a0 0%, #8f0 20%, #4a0 100%);
}
meter::-webkit-meter-suboptimum-value {
background: linear-gradient(to bottom, #aa0 0%, #ff0 20%, #aa0 100%);
}
meter::-webkit-meter-even-less-good-value {
background: linear-gradient(to bottom, #a40 0%, #f80 20%, #a40 100%);
}
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment