Watch a thing, get a probe, a colour and a curve. More...
| Import Statement: | import Clayground.Lab |
The plotted set is the WATCHED set: point at a part (a road, a resistor, a sensor), and it gains a Probe, a place in the legend and a colour it then wears everywhere - on the object, in the legend, on its card. Drop it by clicking its legend entry. Two labs had written this out in full before it moved here.
The lab supplies only what is domain-specific: what an id is worth right now (valueOf), what to call it (labelOf), and which quantities can be plotted (quantities). Everything else - probe lifecycle, stable names, colours, the one-quantity-per-axis rule - lives here.
One quantity per axis is deliberate, not a limitation: series that share an autoscaled axis must share a unit, or mixing mA with volts flattens the volts onto the baseline. The chip row switches which quantity the watched set is read as, and switching re-aims the whole set - the parts stay, the reading changes, and the samples go, because the old ones would draw a nonsense step across the change of unit.
Two quantities that must be compared get a strip each instead (traceIn): stacked charts on one shared time axis, so "the voltage dipped when the current spiked" is one picture and the rule still holds. Strips appear and disappear with the traces in them, ordered by the lab's quantities, at most maxStrips of them.
WatchMonitor { id: monitor anchors.right: parent.right; anchors.bottom: parent.bottom idPrefix: "road" quantities: [{ key: "flow", label: "quantity.flow", unit: "/min" }, { key: "load", label: "quantity.load", unit: "" }] valueOf: (id) => root.rateOf(id) labelOf: (id) => root.roadLabel(id) placeholder: LabLang.t("plot.empty") }
See also Probe, Plot2D, and LabTheme.
canWatch : var |
(id) -> bool: veto (a solder dot has no reading).
idPrefix : string |
Probe-name prefix; probes are <idPrefix><id>.
Id-based and therefore stable while the visible label changes under it - a lone BULB becomes BULB1 the moment a second one lands.
A trace pinned in a quantity other than the first of quantities appends .<key> (part7.V), because the same part traced as volts and as milliamps is two probes and they may not collide. The first quantity keeps the plain name - it is the one every lab, record and study already knows. See probeName.
labelOf : var |
(id) -> string: the legend/board label.
maxSeries : int |
Beyond this the colours would repeat.
Counted in watched things, not in curves: a part traced in two quantities wears one colour and spends one slot, which is what keeps its WatchMark recognisable in both strips.
maxStrips : int |
How many quantities may be stacked at once.
The strips divide the panel's height, so this is what stops it from growing without end. Three is the height at which the bottom-right slot still leaves the scene the room it is there for; a fourth trace in a fourth quantity is refused by traceIn rather than drawn too small to read.
placeholder : string |
Shown while nothing is watched.
plotHeight : real |
Chart height - the budget the strips divide.
One or two strips fit inside it (a two-channel stack is two half charts); a third takes the chart to the floor below which a curve stops being a shape, and only then does the panel grow. Bounded by maxStrips, so the bottom-right slot has a largest size and it is reached at three strips.
plotWidth : real |
Chart width.
quantities : var |
[{key, label, unit}].
quantity : string |
Active quantity key: what setWatched traces in, and what the chip row shows as chosen.
Switching it moves the traces that were being read as the old quantity over to the new one - the watched set is a set of parts, and the chips choose what the parts are read as. Traces pinned in another quantity with traceIn stay where they are and keep their strip.
revision : int |
Bump when labels change (ordinals, renames).
stripModel : var |
What the plot is drawing: one entry per traced quantity, in quantities order, as [{key, label, series}].
The order is the lab's declared order rather than the order the traces happened in, so a strip appearing does not move the ones already there.
tracedQuantities : var |
The quantity keys that currently have a strip, in quantities order.
unitText : string |
Unit of the active quantity.
valueOf : var |
(id, quantity) -> real: the current reading.
The second argument says which quantity is being asked for, and a lab has to declare it to get stacked strips: a callback that only takes the id is one that reads quantity itself - as the first labs all did - so traceIn refuses a second quantity rather than plotting the active reading under another unit's name. A plot that lies is worse than a strip that never appears.
watched : var |
The watched ids, in plot order - which is also colour order.
Derived from the traces: an id appears once however many quantities it is traced in, and leaves only when the last of them goes. The set is changed through setWatched, traceIn, watchOnly, clear and prune, never by assignment - a lab that wrote to it would be deciding half of a pair the monitor keeps consistent.
windowSeconds : real |
Plot window.
changed() |
The watched set changed.
Note: The corresponding handler is onChanged.
void clear() |
color colorOf(var id) |
The id's series colour, or transparent when it is not watched.
bool isFull() |
No colour left for another curve.
bool isTracedIn(string quantity, var id) |
The id has a curve on quantity's strip.
bool isWatched(var id) |
string probeName(var id, string quantity) |
The probe an id is sampled into for quantity (the active one when omitted).
void prune(var stillExists) |
Drops ids whose object is gone - deleted parts must not plot as zero.
void setWatched(var id, bool on) |
void toggle(var id) |
bool traceIn(string quantity, var id, bool on) |
Trace the id on quantity's strip, stacking a new one if that quantity has none yet.
Returns false when the trace was refused, and the three reasons it can be are all budgets: no colour left (maxSeries), no strip left (maxStrips), or a valueOf that cannot be asked for a quantity other than the active one. Refusing is the point - the alternative is a strip labelled volts with milliamps drawn on it.
void traceOnly(var list) |
Replace every trace with [{id, quantity}] - the restoring half of traces().
var traces() |
Every trace as [{id, quantity}], in the order they were made - a lab's viewState() serializes this.
string unitOf(string quantity) |
The unit declared for quantity, empty when it has none.
void watchOnly(var ids) |
Replace the set (presets seed it).