Skip to content

TableWidget: opt-in row background coloring (severity in events mode, threshold in data mode) #267

Description

@HanSur94

Problem / motivation

A TableWidget is a canonical dashboard tile — a tabular readout of recent alarm events (Mode='events') or recent sensor samples (Mode='data'). Today it is monochrome: nothing in the table signals which rows are out of range or high-severity, so the engineer has to read every number.

This is a verified gap. In events mode the widget already iterates the events and builds the Start/End/Label/Duration rows, but throws away each event's Severity (libs/Dashboard/TableWidget.m:99-108). A grep -niE "color|severity|threshold" over the file finds only the BackgroundColor theme calls (:50, :60) — there is no per-row coloring of any kind. This is the "alarm/threshold ergonomics" sensor-analysis gap applied to the tabular readout.

Proposed feature

Add an opt-in ColorRows flag that paints each row's background by its alarm status:

  • events mode → each row colored by its event severity (ok/warn/alarm).
  • data mode (bound to a Threshold/MonitorTag) → rows whose value violates the threshold get the alarm color; in-range rows keep the theme background.

Default false ⇒ the table renders exactly as it does today.

Rough sketch

Lib/class: libs/Dashboard/TableWidget.m (single file).

Two supporting primitives already ship in the repo — no new color logic:

  • severityColor(theme, severity) (libs/Dashboard/severityColor.m) maps 1/2/3 → ok/warn/alarm theme colors and is already used by EventTimelineWidget (EventTimelineWidget.m:221).
  • Event.Severity (1=ok/info, 2=warn, 3=alarm — libs/EventDetection/Event.m:35) is populated on every event.
  • data-mode threshold walk mirrors the StatusWidget precedent (StatusWidget.m:201-204).

Public API:

w = TableWidget('Sensor', monitorTag, 'Mode', 'events', 'EventStoreObj', store, ...
                'ColorRows', true);   % rows colored by event severity
  • ColorRows = false % new public prop; default = byte-identical to today

Render (portable): build an nRows x 3 RGB matrix and set(obj.hTable, 'BackgroundColor', M). Classical uitable maps a BackgroundColor matrix row-by-row (the standard striping mechanism), which is portable across MATLAB and Octave classical uitable — no uistyle/uifigure dependency. Uncolored rows fall back to the existing theme.WidgetBackground.

Serialize: emit s.colorRows in toStruct (TableWidget.m:162-176) only when true; read it in fromStruct (:180-212) defaulting to false when absent.

Value

High. Turns a tabular readout into an at-a-glance alarm panel: an engineer scanning recent events or recent samples sees out-of-range/high-severity rows immediately instead of reading every number. Reuses the exact severity→color mapping the timeline already uses, so it is visually consistent with the rest of the dashboard.

Constraints check

  • Toolbox-free:set('BackgroundColor', M) on a classical uitable + existing severityColor helper — no toolbox.
  • Backward-compatible: ✅ default ColorRows=false ⇒ current rendering; serialized field omitted unless true, so old saves load uncolored exactly as before.
  • Pure MATLAB/Octave: ✅ classical uitable BackgroundColor row-mapping is portable; no uifigure uistyle.
  • Widget contract: ✅ works entirely through the existing DashboardWidget interface — no base-class or layout change.

Effort estimate

S–M, single file: one public prop + an nRows x 3 color-matrix build in refresh (events branch reuses severityColor; data branch reuses the StatusWidget threshold walk) + a set('BackgroundColor', M) + a toStruct/fromStruct round-trip. One test: ColorRows=true in events mode paints a severity-3 row with severityColor(theme,3); default false leaves the table at theme background; the flag round-trips through serialization.


AI-proposed via /feature-scout — needs a human product decision before implementation.

Metadata

Metadata

Assignees

No one assigned

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions