Open halecivo opened 1 year ago
How is this info available in Home Assistant?
The data itself comes from REST api sensor, for Prague integrated transportation, I use golemio. Currently, I just combine the data into a string state for template sensor. The problem is that displayed state of the sensor is limited to only a few characters. In order to have "proper" timetable - data could be combined to provide destination, departure, line and possibly also last known position or delay.
rest:
- resource: https://api.golemio.cz/v2/pid/departureboards?ids=U2142Z301&minutesBefore=-7
scan_interval: 60
headers:
X-Access-Token: >
<token>
sensor:
name: departures
value_template: "{{ now() }}"
json_attributes:
- "departures"
sensor:
- platform: template
sensors:
ricany_departure_1:
value_template: "{{ state_attr('sensor.departures', 'departures')[0].departure_timestamp.minutes }} m - {{ state_attr('sensor.departures', 'departures')[0].trip.headsign }}: {{ state_attr('sensor.departures', 'departures')[0].route.short_name }}"
I was thinking on how I could use this for my own thing, which is almost the same, but not exactly. We have 2 nearby stops but we use one a lot more than the other.
What if we could allow a button to support text entities, and if you select it (short/long, or one of the 3 shortcut buttons on the home page) it would open a detailed screen which would just render the text.
Could just use monospaced font and fit, e.g. 8 rows of 24 characters each and mock it like so: (with newlines to indicate next row)
PATCHAM
5 Pavillion 6 min
5a Hollingbury 10 min
52 Town Square 10 min
17 Lancing 14 min
ELDRED
27 Saltdean 3 min
27a Saltdean 23 min
I'm thinking a single multiline text entry would work. That has a max length of 255 which should be enough for that kind of table. (8 × (24+1) = 200) You could extend it with some lightweight markup (like underline or bold/colour) and it would still fit. (not important)
Should be possible to implement, I think?
@halecivo Would that work for you?
Was thinking that a button that triggers an automation that then fetches the data from the API and then calls a service on the panel e.g. send_command_table
.
This would also only check the bus api when you want to see it, and you could also send metadata for e.g. font colour or icons to show as the data is now structured.
That would only require a new service and screen for custom presentation.
If you do this, to hide latency it would be useful to send 2 service calls, one to render a screen with no info, then fetch data from API, then send call again updated with the content. And any action on it would cancel it.
The challenge is on Nextion side. There are important limitation to change the screen dynamically. The screen is made of pre-define components with some hard coded attributes not available to be changed programmatically... Like font size, position, etc. I could have multiple pages, for 3 columns, 4 columns, etc., but then it will probably get to another Nextion limitation... memory. :(
Hence my initial suggestion of monospaced text. You can simulate columns by whitespace alignment. So there's not really any concept of "columns" needed for that.
I think that would be quite easy.
Any progress on this issue?
I would like to add also Helsinki Public Transportation data.
Do I understand it right that it's impossible to display HTML in the nspanel?
This is how I show data in my home assistant currently:
<!DOCTYPE html>
<html>
<head>
<title>HRT</title>
<style>
iframe {
pointer-events: none;
}
</style>
</head>
<body>
<iframe src="https://omatnaytot.hsl.fi/static/?url=033dc8fe-0220-5553-9976-43d14ab0717e" style="height:600px; width:100%;" allow="geolocation *; microphone *; camera *">
</iframe>
</body>
</html>
But there is a way to obtain the data via REST API as well.
Do I understand it right that it's impossible to display HTML in the nspanel?
"Impossible" is a hard word, but in fact, the Nextion display used by Sonoff on those panels is limited to plain text in fix coordinates. We can play with fonts, alignment, etc. and in the end we can draw tables, etc., like the one used on the entities pages... but it's quite rigid. One option would be a plain text with fix font space plotting a table like the one proposed here: https://github.com/Blackymas/NSPanel_HA_Blueprint/issues/811#issuecomment-1737237940
Another big challenge for this timetable is a lack of standardization between the multiple transport agencies around the world. 😞
PATCHAM 5 Pavillion 6 min 5a Hollingbury 10 min 52 Town Square 10 min 17 Lancing 14 min ELDRED 27 Saltdean 3 min 27a Saltdean 23 min
@halecivo Would that work for you?
sorry for late reply, this seems quite useful. Do you have some example on how to achieve it?
This is not implemented yet. :(
"Impossible" is a hard word, but in fact, the Nextion display used by Sonoff on those panels is limited to plain text in fix coordinates. We can play with fonts, alignment, etc. and in the end we can draw tables, etc., like the one used on the entities pages... but it's quite rigid. One option would be a plain text with fix font space plotting a table like the one proposed here: #811 (comment)
Text table sounds good. Nextion editor reference states those two components which can be up to the task:
The SLText component is used to present a scrollable textbox with .txt holding multiline data. The position of the list in pixels can be set through the .val_y attribute.
The DataRecord component is used to present a dataset in a scrollable table. DataRecord supports up to 12 fields per record. DataRecord incorporates 4 methods .insert(), .delete(), .up() and .clear(). Configuring DataRecord attributes for your application requirements will need be thoughtful at your HMI design time.
Are these elements supported by nspanel / esphome ?
(I have not tried the editor myself yet, fighting with PlayOnLinux to be able to run it).
Another big challenge for this timetable is a lack of standardization between the multiple transport agencies around the world. 😞
And then my second question comes - how to connect nspanel running esphome with table data source using blueprint? Are there any table data sources supported in the same way as entities with only one value (which you currently support in blueprint - the user just needs to select the entity, blueprint automation extracts the value from that entity and asks nspanel to display it. Is it possible to have the same thing with the table? Are there entity which can provide two-dimensional arrays (tables) ? (may be lists of lists etc)
I did manage to do something with the existing blueprint that is already pretty good. I utilize two lines for every tram and show the next 4 trams on one entity screen. You can see, it is not ideal to have less space on the right for the actual values, but it is still decent. Blue arrow points to the stop (title of the screen), Green says next tram (sorry for German) on the left side and displays the line number and the first 10 characters of the direction on the right side. The red arrows says departure (in German) on the left and shows the departure time. Minutes could be calculated as well.
Please note that there will always be the requirement to have the information in HA first. Then, it can be reformatted to fit a screen in the panel. If there is a dedicated screen with the table, I would be happy to come up with an intermediate layer in HA that does the reformatting in addition to the Blueprint that does the reformatting.
edit: clarified the meaning.
Looks good. But which nspanel's page did you display this ?
I used 'entities page 02'.
This looks great! Can you share your sensor's attributes from where you get this info? I wanna take a look to compare to my time table sensor and think in a solution that fits all.
For Prague (and surroundings), output from Golemio for a single stop can look like this:
departures:
- arrival_timestamp:
predicted: "2024-10-10T09:38:26+02:00"
scheduled: "2024-10-10T09:38:00+02:00"
delay:
is_available: true
minutes: 0
seconds: 26
departure_timestamp:
predicted: "2024-10-10T09:38:30+02:00"
scheduled: "2024-10-10T09:38:30+02:00"
minutes: "11"
last_stop:
id: U2277Z301
name: Mnichovice
route:
short_name: S9
type: 2
is_night: false
is_regional: true
is_substitute_transport: false
stop:
id: U2142Z301
platform_code: null
trip:
direction: null
headsign: Praha hl.n.
id: "1309_2522_231210"
is_at_stop: false
is_canceled: false
is_wheelchair_accessible: true
is_air_conditioned: null
short_name: Os 2522
- arrival_timestamp:
predicted: "2024-10-10T09:54:03+02:00"
scheduled: "2024-10-10T09:48:00+02:00"
delay:
is_available: true
minutes: 6
seconds: 363
departure_timestamp:
predicted: "2024-10-10T09:54:03+02:00"
scheduled: "2024-10-10T09:48:30+02:00"
minutes: "26"
last_stop:
id: U142Z301
name: Praha hl.n.
route:
short_name: S9
type: 2
is_night: false
is_regional: true
is_substitute_transport: false
stop:
id: U2142Z301
platform_code: null
trip:
direction: null
headsign: Benešov u Prahy
id: "1309_2525_231211"
is_at_stop: false
is_canceled: false
is_wheelchair_accessible: true
is_air_conditioned: null
short_name: Os 2525
- arrival_timestamp:
predicted: null
scheduled: null
delay:
is_available: false
minutes: null
seconds: null
departure_timestamp:
predicted: "2024-10-10T09:58:00+02:00"
scheduled: "2024-10-10T09:58:00+02:00"
minutes: "30"
last_stop:
id: null
name: null
route:
short_name: S9
type: 2
is_night: false
is_regional: true
is_substitute_transport: false
stop:
id: U2142Z301
platform_code: null
trip:
direction: null
headsign: Praha hl.n.
id: "1309_9118_231211"
is_at_stop: false
is_canceled: false
is_wheelchair_accessible: true
is_air_conditioned: null
short_name: Os 9118
- arrival_timestamp:
predicted: "2024-10-10T10:08:00+02:00"
scheduled: "2024-10-10T10:08:00+02:00"
delay:
is_available: false
minutes: null
seconds: null
departure_timestamp:
predicted: "2024-10-10T10:08:30+02:00"
scheduled: "2024-10-10T10:08:30+02:00"
minutes: "41"
last_stop:
id: null
name: null
route:
short_name: S9
type: 2
is_night: false
is_regional: true
is_substitute_transport: false
stop:
id: U2142Z301
platform_code: null
trip:
direction: null
headsign: Praha hl.n.
id: "1309_2524_231211"
is_at_stop: false
is_canceled: false
is_wheelchair_accessible: true
is_air_conditioned: null
short_name: Os 2524
- arrival_timestamp:
predicted: "2024-10-10T10:18:00+02:00"
scheduled: "2024-10-10T10:18:00+02:00"
delay:
is_available: false
minutes: null
seconds: null
departure_timestamp:
predicted: "2024-10-10T10:18:30+02:00"
scheduled: "2024-10-10T10:18:30+02:00"
minutes: "51"
last_stop:
id: null
name: null
route:
short_name: S9
type: 2
is_night: false
is_regional: true
is_substitute_transport: false
stop:
id: U2142Z301
platform_code: null
trip:
direction: null
headsign: Strančice
id: "1309_2527_231211"
is_at_stop: false
is_canceled: false
is_wheelchair_accessible: true
is_air_conditioned: null
short_name: Os 2527
- arrival_timestamp:
predicted: null
scheduled: null
delay:
is_available: false
minutes: null
seconds: null
departure_timestamp:
predicted: "2024-10-10T10:28:00+02:00"
scheduled: "2024-10-10T10:28:00+02:00"
minutes: "60"
last_stop:
id: null
name: null
route:
short_name: S9
type: 2
is_night: false
is_regional: true
is_substitute_transport: false
stop:
id: U2142Z301
platform_code: null
trip:
direction: null
headsign: Praha hl.n.
id: "1309_9120_231211"
is_at_stop: false
is_canceled: false
is_wheelchair_accessible: true
is_air_conditioned: null
short_name: Os 9120
- arrival_timestamp:
predicted: "2024-10-10T10:38:00+02:00"
scheduled: "2024-10-10T10:38:00+02:00"
delay:
is_available: false
minutes: null
seconds: null
departure_timestamp:
predicted: "2024-10-10T10:38:30+02:00"
scheduled: "2024-10-10T10:38:30+02:00"
minutes: "71"
last_stop:
id: null
name: null
route:
short_name: S9
type: 2
is_night: false
is_regional: true
is_substitute_transport: false
stop:
id: U2142Z301
platform_code: null
trip:
direction: null
headsign: Praha hl.n.
id: "1309_2526_231210"
is_at_stop: false
is_canceled: false
is_wheelchair_accessible: true
is_air_conditioned: null
short_name: Os 2526
- arrival_timestamp:
predicted: "2024-10-10T10:48:00+02:00"
scheduled: "2024-10-10T10:48:00+02:00"
delay:
is_available: false
minutes: null
seconds: null
departure_timestamp:
predicted: "2024-10-10T10:48:30+02:00"
scheduled: "2024-10-10T10:48:30+02:00"
minutes: "81"
last_stop:
id: null
name: null
route:
short_name: S9
type: 2
is_night: false
is_regional: true
is_substitute_transport: false
stop:
id: U2142Z301
platform_code: null
trip:
direction: null
headsign: Benešov u Prahy
id: "1309_2529_231210"
is_at_stop: false
is_canceled: false
is_wheelchair_accessible: true
is_air_conditioned: null
short_name: Os 2529
- arrival_timestamp:
predicted: null
scheduled: null
delay:
is_available: false
minutes: null
seconds: null
departure_timestamp:
predicted: "2024-10-10T10:58:00+02:00"
scheduled: "2024-10-10T10:58:00+02:00"
minutes: "90"
last_stop:
id: null
name: null
route:
short_name: S9
type: 2
is_night: false
is_regional: true
is_substitute_transport: false
stop:
id: U2142Z301
platform_code: null
trip:
direction: null
headsign: Praha hl.n.
id: "1309_9122_231211"
is_at_stop: false
is_canceled: false
is_wheelchair_accessible: true
is_air_conditioned: null
short_name: Os 9122
- arrival_timestamp:
predicted: "2024-10-10T11:08:00+02:00"
scheduled: "2024-10-10T11:08:00+02:00"
delay:
is_available: false
minutes: null
seconds: null
departure_timestamp:
predicted: "2024-10-10T11:08:30+02:00"
scheduled: "2024-10-10T11:08:30+02:00"
minutes: "101"
last_stop:
id: null
name: null
route:
short_name: S9
type: 2
is_night: false
is_regional: true
is_substitute_transport: false
stop:
id: U2142Z301
platform_code: null
trip:
direction: null
headsign: Praha hl.n.
id: "1309_2528_231211"
is_at_stop: false
is_canceled: false
is_wheelchair_accessible: true
is_air_conditioned: null
short_name: Os 2528
- arrival_timestamp:
predicted: "2024-10-10T11:18:00+02:00"
scheduled: "2024-10-10T11:18:00+02:00"
delay:
is_available: false
minutes: null
seconds: null
departure_timestamp:
predicted: "2024-10-10T11:18:30+02:00"
scheduled: "2024-10-10T11:18:30+02:00"
minutes: "111"
last_stop:
id: null
name: null
route:
short_name: S9
type: 2
is_night: false
is_regional: true
is_substitute_transport: false
stop:
id: U2142Z301
platform_code: null
trip:
direction: null
headsign: Strančice
id: "1309_2531_231211"
is_at_stop: false
is_canceled: false
is_wheelchair_accessible: true
is_air_conditioned: null
short_name: Os 2531
- arrival_timestamp:
predicted: null
scheduled: null
delay:
is_available: false
minutes: null
seconds: null
departure_timestamp:
predicted: "2024-10-10T11:28:00+02:00"
scheduled: "2024-10-10T11:28:00+02:00"
minutes: "120"
last_stop:
id: null
name: null
route:
short_name: S9
type: 2
is_night: false
is_regional: true
is_substitute_transport: false
stop:
id: U2142Z301
platform_code: null
trip:
direction: null
headsign: Praha hl.n.
id: "1309_9124_231211"
is_at_stop: false
is_canceled: false
is_wheelchair_accessible: true
is_air_conditioned: null
short_name: Os 9124
- arrival_timestamp:
predicted: "2024-10-10T11:38:00+02:00"
scheduled: "2024-10-10T11:38:00+02:00"
delay:
is_available: false
minutes: null
seconds: null
departure_timestamp:
predicted: "2024-10-10T11:38:30+02:00"
scheduled: "2024-10-10T11:38:30+02:00"
minutes: "131"
last_stop:
id: null
name: null
route:
short_name: S9
type: 2
is_night: false
is_regional: true
is_substitute_transport: false
stop:
id: U2142Z301
platform_code: null
trip:
direction: null
headsign: Praha hl.n.
id: "1309_2530_231210"
is_at_stop: false
is_canceled: false
is_wheelchair_accessible: true
is_air_conditioned: null
short_name: Os 2530
- arrival_timestamp:
predicted: "2024-10-10T11:48:00+02:00"
scheduled: "2024-10-10T11:48:00+02:00"
delay:
is_available: false
minutes: null
seconds: null
departure_timestamp:
predicted: "2024-10-10T11:48:30+02:00"
scheduled: "2024-10-10T11:48:30+02:00"
minutes: "141"
last_stop:
id: null
name: null
route:
short_name: S9
type: 2
is_night: false
is_regional: true
is_substitute_transport: false
stop:
id: U2142Z301
platform_code: null
trip:
direction: null
headsign: Benešov u Prahy
id: "1309_2533_231210"
is_at_stop: false
is_canceled: false
is_wheelchair_accessible: true
is_air_conditioned: null
short_name: Os 2533
- arrival_timestamp:
predicted: null
scheduled: null
delay:
is_available: false
minutes: null
seconds: null
departure_timestamp:
predicted: "2024-10-10T11:58:00+02:00"
scheduled: "2024-10-10T11:58:00+02:00"
minutes: "150"
last_stop:
id: null
name: null
route:
short_name: S9
type: 2
is_night: false
is_regional: true
is_substitute_transport: false
stop:
id: U2142Z301
platform_code: null
trip:
direction: null
headsign: Praha hl.n.
id: "1309_9126_231211"
is_at_stop: false
is_canceled: false
is_wheelchair_accessible: true
is_air_conditioned: null
short_name: Os 9126
- arrival_timestamp:
predicted: "2024-10-10T12:08:00+02:00"
scheduled: "2024-10-10T12:08:00+02:00"
delay:
is_available: false
minutes: null
seconds: null
departure_timestamp:
predicted: "2024-10-10T12:08:30+02:00"
scheduled: "2024-10-10T12:08:30+02:00"
minutes: "161"
last_stop:
id: null
name: null
route:
short_name: S9
type: 2
is_night: false
is_regional: true
is_substitute_transport: false
stop:
id: U2142Z301
platform_code: null
trip:
direction: null
headsign: Praha hl.n.
id: "1309_2532_231211"
is_at_stop: false
is_canceled: false
is_wheelchair_accessible: true
is_air_conditioned: null
short_name: Os 2532
- arrival_timestamp:
predicted: "2024-10-10T12:18:00+02:00"
scheduled: "2024-10-10T12:18:00+02:00"
delay:
is_available: false
minutes: null
seconds: null
departure_timestamp:
predicted: "2024-10-10T12:18:30+02:00"
scheduled: "2024-10-10T12:18:30+02:00"
minutes: "171"
last_stop:
id: null
name: null
route:
short_name: S9
type: 2
is_night: false
is_regional: true
is_substitute_transport: false
stop:
id: U2142Z301
platform_code: null
trip:
direction: null
headsign: Strančice
id: "1309_2535_231211"
is_at_stop: false
is_canceled: false
is_wheelchair_accessible: true
is_air_conditioned: null
short_name: Os 2535
friendly_name: departures
I then use template sensor to combine relevant properties into useful string.
I am using Home Assistant Transport, which is, unfortunately, not updated any more. However, the sensor part works fine, just the lovelace card is not, which is irrelevant for this use case. The sensor, e.g. from right now, has the following content:
departures:
- line_name: "2"
line_type: Tram
time: "21:48"
gap: 2
platform: "2"
direction: Gorbitz
color: "#D82020"
- line_name: "1"
line_type: Tram
time: "21:53"
gap: 7
platform: "2"
direction: Gorbitz
color: "#D82020"
- line_name: "2"
line_type: Tram
time: "21:56"
gap: 10
platform: "1"
direction: Kleinzschachwitz
color: "#D82020"
- line_name: "2"
line_type: Tram
time: "22:02"
gap: 16
platform: "2"
direction: Gorbitz
color: "#D82020"
- line_name: "2"
line_type: Tram
time: "22:11"
gap: 25
platform: "1"
direction: Kleinzschachwitz
color: "#D82020"
- line_name: "2"
line_type: Tram
time: "22:16"
gap: 30
platform: "2"
direction: Gorbitz
color: "#D82020"
- line_name: "2"
line_type: Tram
time: "22:30"
gap: 44
platform: "1"
direction: Kleinzschachwitz
color: "#D82020"
- line_name: "2"
line_type: Tram
time: "22:31"
gap: 45
platform: "2"
direction: Gorbitz
color: "#D82020"
- line_name: "11"
line_type: Tram
time: "22:48"
gap: 62
platform: "2"
direction: Gorbitz
color: "#D82020"
- line_name: "2"
line_type: Tram
time: "22:57"
gap: 71
platform: "2"
direction: Gorbitz
color: "#D82020"
icon: mdi:tram
friendly_name: Chamissostraße
Then, I was playing with helpers and how to get them in the panel in an appropriate way. I settled with the mentioned two lines of text per tram and the according helper for the first entry (helper, template, green arrow in my picture) looks like this:
{{state_attr('sensor.chamissostrasse', 'departures')[0]['line_name']}}
{{state_attr('sensor.chamissostrasse', 'departures')[0]['direction'][0:9]}}
and I used the friendly name 'Next tram.' Now, the time is missing, but all does not fit in one line of the panel, so the second helper (also template, red arrow in my picture) looks like this:
{{state_attr('sensor.chamissostrasse', 'departures')[0]['time']}}
with the friendly name 'departure.' I repeated this 3 more times and increased the list element counter accordingly. Then, I had 4 helpers for the line and direction and 4 more for the respective time. I added those 8 helpers to rows 1-8 of an entity page and gave it the title of the station (blue arrow in my picture).
Text table sounds good. Nextion editor reference states those two components which can be up to the task:
The SLText component is used to present a scrollable textbox with .txt holding multiline data. The position of the list in pixels can be set through the .val_y attribute. The DataRecord component is used to present a dataset in a scrollable table. DataRecord supports up to 12 fields per record. DataRecord incorporates 4 methods .insert(), .delete(), .up() and .clear(). Configuring DataRecord attributes for your application requirements will need be thoughtful at your HMI design time.
Are these elements supported by nspanel / esphome ?
Answering myself - no, these components are not supported by the nextion display used in the nspanel.
The only component which can be used to output tables seems to be Text.
I managed to create a separate page in the
HMI with a text field. But then I realized that the entitys page can be used for outputting the timetable. WIths ome hacks but still it is much simpler than to change HMI and support new page in blueprint etc.
I'll share my results soon.
I documented my results here: https://community.home-assistant.io/t/how-to-display-public-transport-timetable-in-your-nspanel/781855
Hello,
it would be awesome to see when next train departures in my hall. Line - Destination - time +delay (delay is just nice to have, I could already include it in the time).
For timetable page it would be cool to see something like this:
But in order to not need to touch the display while putting my shoes on and wondering whether I'm on time, something smaller would be great to have also on the home page.
It seems that most problematic is limit to few characters for a entity state, I am able to print something like "15m - Pra", which tells me that train to Prague leaves in 15 minutes, but it is not very nice. Being able to use template as a label for entity on entity page could help me to at least display "Praha hl. n." "15 m" on a single line.