425 Human Interface: Nextion Display - k3ng/k3ng_rotator_controller GitHub Wiki
Introduction
The K3NG Arduino Rotator Controller support Nextion displays. As of this writing the Nextion display functionality is in development on a Nextion NX4832TO35 3.5" display.
If you are unfamiliar with Nextion displays, this is an excellent tutorial on using them with Arduinos. Some of the steps below are covered in more detail in this tutorial.
Adam, VK4GHZ leads Nextion display development; Goody, K3NG, created and maintains the API described below.
https://vk4ghz.com/k3ng-rotator-controller-nextion-development/
Installation and Configuration
Please note that the Nextion Arduino library is not utilized by the Arduino Rotator Controller
-
Download and install the Nextion Editor. Unfortunately there is no Mac OSX or Linux version. I run it within Windows 10 on a VirtualBox virtual machine on a MacBook with no issues. You can skip installing Nextion Editor if you want to use a pre-compiled TFT file and aren't going to customize your display (see next step).
-
Select an HMI file, compile a TFT file, and install on your Nextion display. This is covered in detail in this tutorial. Various pre-built HMI files which define the Nextion screen are in the Nextion directory from the K3NG Arduino Rotator Controller GitHub download. The Nextion_HMI_Files directory also contains font .ZI files and pre-compiled TFT files.
-
Uncomment this line in your features file and save (default file: rotator_feature.h )
#define FEATURE_NEXTION_DISPLAY
-
In your settings file, update this line to reflect the Arduino serial port you are going to connect your Nextion to:
#define nexSerial Serial3
Note that this line should normally be set for 115200 baud:
#define NEXTION_SERIAL_BAUD 115200
- Physically connect your Nextion display to the Arduino. Using the wiring harness supplied with the Nextion display:
Red: +5V
Black: Ground
Yellow: Serial TX on the Arduino (Settings file defaults to Serial3, so pin TX3)
Blue: Serial TX on the Arduino (Settings file defaults to Serial3, so pin RX3)
- Compile and upload the code to the Arduino. Shortly after boot up the Nextion display should show a "K3NG Rotator Controller" splash screen and then go to the Main display page.
HMI Files
As of this writing, one HMI display definition file is being developed. This contains the foundational API variables for building customized displays.
Creating or Customizing A Display
Integration of the Nextion display is implemented via the use of several "API variables". The BASE HMI file in the Github repository provides API variable definitions and a sample Nextion user interface implementation. This HMI file can be used as is, or customized. If a user wants to create a new Nextion HMI file, the variable definitions that are in the BASE HMI file API page, along with the global variables in Program.s (prefixed with a 'g'), should be copied to the new HMI file. (If it is desired to create a new display definition, it's highly recommended and more convenient to use the BASE HMI file as a starting point and delete all the pages except for the API page.)
API Variables
vSS1 String[32] Status String 1 - Most important status messages relating to rotation and targets
vSS2 String[16] Status String 2 - Parking, Parked, Overlap messages
vSS3 String[16] Status String 3 - Deprecated as of version 2020.08.12.01
vAz String[6] The real azimuth heading in degrees (0.00 - 360.00)
gAz Integer The real azimuth heading in degrees, integer
(0 - 360, no decimal places)
gAzR Integer The raw azimuth heading in degrees, integer
(0 - 450, no decimal places)
vEl String[6] The elevation in degrees (0 - 180)
gEl Integer The elevation in degrees, integer
(0 - 180, no decimal places)
gX Integer Heading Cartesian coordinates - X (0,0 is upper left; 180,180 is lower right)
gY Integer Heading Cartesian coordinates - Y
gAOS Integer Azimuth overall status
NOT_DOING_ANYTHING 0
ROTATING_CW 1
ROTATING_CCW 2
gADS Integer Azimuth detailed status
IDLE 0
SLOW_START_CW 1
SLOW_START_CCW 2
NORMAL_CW 3
NORMAL_CCW 4
SLOW_DOWN_CW 5
SLOW_DOWN_CCW 6
INITIALIZE_SLOW_START_CW 7
INITIALIZE_SLOW_START_CCW 8
INITIALIZE_TIMED_SLOW_DOWN_CW 9
INITIALIZE_TIMED_SLOW_DOWN_CCW 10
TIMED_SLOW_DOWN_CW 11
TIMED_SLOW_DOWN_CCW 12
INITIALIZE_DIR_CHANGE_TO_CW 13
INITIALIZE_DIR_CHANGE_TO_CCW 14
INITIALIZE_NORMAL_CW 15
INITIALIZE_NORMAL_CCW 16
gEOS Integer Elevation overall status
NOT_DOING_ANYTHING 0
ROTATING_UP 3
ROTATING_DOWN 4
gEDS Integer Elevation detailed status
IDLE 0
SLOW_START_UP 1
SLOW_START_DOWN 2
NORMAL_UP 3
NORMAL_DOWN 4
SLOW_DOWN_DOWN 5
SLOW_DOWN_UP 6
INITIALIZE_SLOW_START_UP 7
INITIALIZE_SLOW_START_DOWN 8
INITIALIZE_TIMED_SLOW_DOWN_UP 9
INITIALIZE_TIMED_SLOW_DOWN_DOWN 10
TIMED_SLOW_DOWN_UP 11
TIMED_SLOW_DOWN_DOWN 12
INITIALIZE_DIR_CHANGE_TO_UP 13
INITIALIZE_DIR_CHANGE_TO_DOWN 14
INITIALIZE_NORMAL_UP 15
INITIALIZE_NORMAL_DOWN 16
vClk String[13] The clock time
gCS Integer Clock Status
FREE_RUNNING 0
GPS_SYNC 1
RTC_SYNC 2
SLAVE_SYNC 3
SLAVE_SYNC_GPS 4
NOT_PROVISIONED 255
vGPS String[16] GPS Status
vGrid String[6] Grid Locator
vCrd String[25] Coordinates
gGF Integer GPS fix age in mS
gVS Integer, Bit Mapped Various States
Bit Values
brake_az_engaged 1
brake_el_engaged 2
az_request_queue_state
IN_QUEUE 4
IN_PROGRESS_TIMED 8
IN_PROGRESS_TO_TARGET 16
el_request_queue_state
IN_QUEUE 32
IN_PROGRESS_TIMED 64
IN_PROGRESS_TO_TARGET 128
park_status
PARK_INITIATED 256
PARKED 512
autocorrect_state_az
AUTOCORRECT_WAITING_AZ 1024
AUTOCORRECT_WATCHING_AZ 2048
autocorrect_state_el
AUTOCORRECT_WAITING_AZ 4096
AUTOCORRECT_WATCHING_AZ 8192
overlap_indicator 16384
autopark_active 32768
configuration_dirty 65536
gV2 Integer, Bit Mapped Various States 2, The Sequel
Bit Values
audible_alert_enabled 1
gSC Integer, Bit Mapped System Capabilities (variable definition is in Nextion Program.s)
Bit Values
GS_232A 1
GS_232B 2
EASYCOM 4
DCU_1 8
ELEVATION 16
CLOCK 32
GPS 64
MOON 128
SUN 256
RTC 512
SATELLITE 1024
PARK 2048
AUTOPARK 4096
AUDIBLE_ALERT 8192
gL Integer, Bit Mapped Language
ENGLISH 1
SPANISH 2
CZECH 4
PORTUGUESE_BRASIL 8
GERMAN 16
FRENCH 32
vMAS String[6] Moon Azimuth String
vMES String[6] Moon Elevation String
vSAS String[6] Sun Azimuth String
vSES String[6] Sun Elevation String
vSAT String[16] Current Satellite Name
vTAS String[6] Satellite Azimuth String
vTES String[6] Satellite Elevation String
vTLA String[7] Satellite Latitude String
vTLO String[7] Satellite Longitude String
vADF String[11] Satellite Next AOS Full Date String (YYYY-MM-DD)
vADS String[5] Satellite Next AOS Short Date String (MM-DD)
vATS String[5] Satellite Next AOS Time String (HH:MM)
vLDF String[11] Satellite Next LOS Full Date String (YYYY-MM-DD)
vLDS String[5] Satellite Next LOS Short Date String (MM-DD)
vLTS String[5] Satellite Next LOS Time String (HH:MM)
vALI String[13] Satellite AOS/LOS In String (Examples: "AOS in 1d13h","LOS in 30m12s","LOS in 5s")
vS1-vS34 String[15] Satellite #x in Stored TLEs (x = 1 to 34, 34 variables total)
(Sample Data: "AO-07" Available for tracking with \$ command. Example Cmd: "\$AO-070x0D" )
vSatNx String List of satellites next AOS, Satellite Name; x = 1 to NEXTION_NUMBER_OF_NEXT_SATELLITES setting
Example: "AO-07"
vSatOx String List of satellites next AOS, AOS / LOS string; x = 1 to NEXTION_NUMBER_OF_NEXT_SATELLITES setting
Example: "AOS in 5m"
vSatAx Integer List of satellites next AOS; Satellite AOS status; x = 1 to NEXTION_NUMBER_OF_NEXT_SATELLITES setting
0 = Not in AOS, 1 = In AOS
gMSS Integer, Bit Mapped Moon, Sun, and Satellite Status
Bit Values
moon_tracking_active 1
moon_visible 2
sun_tracking_active 4
sun_visible 8
satellite_tracking_active 16
satellite_visible 32
gDP Integer Number of decimal places used in various heading variables (set by DISPLAY_DECIMAL_PLACES)
vPA Integer Park azimuth setting
vPE Integer Park elevation setting
vAT Integer AutoPark time setting, in minutes
gTS Integer Satellite tracking check interval (mS)
gTU Integer Sun tracking check interval (mS)
gTM Integer Moon tracking check interval (mS)
gTX Integer Satellite tracking rotation interval (mS)
gTY Integer Sun tracking rotation interval (mS)
gTZ Integer Moon tracking rotation interval (mS)
vTA String[5] Satellite tracking degrees difference threshold
vTB String[5] Sun tracking degrees difference threshold
vTC String[5] Moon tracking degrees difference threshold
vConResult String Result of backslash commands sent to the Arduino
vRCVersion String The Arduino Rotator Controller's code version
vRCAPIv Integer The Arduino Rotator Controller's API version (DEPRECATED IN VERSION 2020.09.01.03)
It is not necessary to copy all API variables to all display pages, however it's highly recommended. The reason for this is that the Arduino Rotator Controller attempts to periodically update all API variables, regardless of what display page is active or what API variables exist on that page. Attempts to update an API variable that doesn't existing on a page results in the Nextion display returning an error code back to the Arduino. This is not a fatal event but creates additional unnecessary serial port traffic.
Currently the Arduino Rotator Controller does not trap and/or recognize error codes coming from the Nextion display.
Commands from the Nextion display to the Arduino Rotator Controller are accomplish through backslash commands. Controls should use the Nextion prints and printh commands to send commands to the Arduino via the serial port. Commands must be terminated with a carriage return (decimal 13 / 0x0D). Here is sample Nextion code for implementing a CCW (rotate left) button:
prints "\\?RL",0
printh 0D
This code would be placed in the Touch Press or Touch Release event of the button to send the serial data when the user interacts with the Nextion display button.
Backslash commands are documented here.
The output from backslash commands is returned immediately via the vConResult string API variable.
Start Up
Upon startup the display can / should send the ?NG command. This will prompt the Arduino to immediately send the gSC variable, giving the Nextion display the necessary information to determine what features are activated in the Arduino, and adjust the user interface accordingly.
User Contributions
The provided HMI display definition files are examples, fully functional and usable in production. However, there is so much more than can be done using the Nextion displays, and it's difficult to satisfy everyone's needs. Creative radio artisans can undoubtedly more elaborate displays that other users may find useful. If you create a customized display, please consider contributing it so others may benefit from it. You will receive credit and kudos from your fellow radio artisans.
Debugging and Troubleshooting
Uncomment the following lines in rotator_debug_log_activation.h:
#define DEBUG_NEXTION_DISPLAY
#define DEBUG_NEXTION_DISPLAY_SERIAL_SEND
#define DEBUG_NEXTION_DISPLAY_SERIAL_RECV
Notes
Do not attempt to use this display with an Arduino Uno or Nano. Just. Don't. You need a serial port dedicated to the Nextion display serial port, so it would be difficult from a hardware perspective to do. (SoftwareSerial is buuuuuugy.) Also, the regular and extended backslash commands are required in the Rotator Controller. These eat up a lot of memory.
It is highly recommended to use an external 5 volt power supply to power your Nextion display. Avoid using the Arduino 5 volt power, unless perhaps you're powering the Arduino with an external power supply and not just USB power. (I haven't tried this, your mileage may vary, not responsible if you damage something.)
The Nextion display can be used in parallel with an LCD display. Not sure why anyone would want to do this for a production system, but it can be put in place during Nextion display development to provide additional user feedback and help troubleshoot Nextion GUI issues.
Design Choices
In case K3NG gets hit by a bus and someone wonders why certain design choices were made, here are some notes...
-
After three development iterations consuming a lot of time were done and lots of hair was pulled out, it was decided to forgo using the Nextion Arduino library. The need to define each Nextion object the Arduino touches was maddening. Having to link Nextion object IDs made creating an API so that users could easily create their own displays made things very klunky
-
I had problems with lost Nextion display events using the Nextion Arduino library. After diving in the Nextion Arduino library code, I found what I think was the culprit. When a command is sent from the Arduino to the Nextion unit using the library, the command send routine dumps any bytes sitting in the Arduino serial send buffer. So if a Nextion display event occurs while a command is being sent by the Arduino to the Nextion unit, the event is lost.
-
I could not get the Nextion 'get' command to work via the serial port and ended up using prints.
-
The API variable objects in the Nextion unit are defined as local variables and placed on all pages. I originally tried to implement these as global and kept them just in the API page, however I discovered that global variables cannot be written to by serial port commands unless the Nextion page containing them is currently displayed. WHY????? They're global variables, for f---- sake. Global variables defined in Program.s can be accessed via the serial port at any time, so some of the API variables are implemented there (these are prefixed with a 'g', rather than a 'v' like the local variable objects are). However, I was not able to read a global variable defined in Program.s via the serial port.
-
The Nextion IDE doesn't let you change object IDs and if you delete an object it renumbers all the object IDs of objects created after the deleted object. WHY????? This is another reason trying to create a stable API that was easy for users to use was nearly impossible with the Nextion Arduino library.
-
I had a few instances where the Nextion IDE Debug simulation didn't match what the hardware would do in real life. I didn't keep a list, but keep this in mind when you're developing a new display definition. You're not crazy. Some things that work as expected in the simulator won't work on your display.
-
Nextion documentation is hokey.