Table Widget
The Table widget renders a scrollable, sortable data table. Rows are received from the device as JSON and stored in the time-series DB. Each row includes an automatic timestamp. Ideal for event logs, sensor readings with multiple columns, calibration records, or audit trails.
Default size: 4 × 3 grid cells
Configuration
| Property | Type | Default | Description |
|---|---|---|---|
columns | {key, label, width?}[] | Auto-detected | Column definitions |
maxRows | number | 100 | Max rows displayed (newest first) |
showTimestamp | boolean | true | Prepend received-at column |
| Device | device | — | The device to read from |
| Pin | V0–V255 | — | The virtual pin to read rows from |
| Label | string | — | Widget label |
Row format
The device sends a JSON object (one row per push):
{ "temp": 23.5, "hum": 61, "pressure": 1013, "status": "OK" }
The widget displays these as columns. Column order follows the columns config; keys not in columns are hidden.
Firmware example
void loop() {
Vwire.run();
float t = dht.readTemperature();
float h = dht.readHumidity();
int p = bmp.readPressure() / 100; // Pa → hPa
char buf[128];
snprintf(buf, sizeof(buf),
"{\"temp\":%.1f,\"hum\":%.0f,\"pressure\":%d,\"rssi\":%d}",
t, h, p, WiFi.RSSI());
Vwire.virtualSend(V0, buf);
delay(60000); // one row per minute
}
Column config (in widget settings)
[
{ "key": "temp", "label": "Temp (°C)", "width": 100 },
{ "key": "hum", "label": "Hum (%)", "width": 80 },
{ "key": "pressure", "label": "hPa", "width": 80 },
{ "key": "rssi", "label": "RSSI", "width": 70 }
]
Exporting data
All rows are stored in the VWire time-series DB. You can export via:
- Dashboard: download CSV from the widget's "⋮" menu → Export
- API:
GET /api/v1/data/:deviceId/:pin?format=csv
Tips
Logging every 1 minute → 60 rows/hour → 43,800 rows/month per device. This is well within platform performance limits.
Keep each JSON row under 1 KB for best performance. Split very wide datasets across multiple pins/tables.