Skip to content

2.3 Level III : Loading Images and Using Switches

Udo edited this page Nov 21, 2024 · 5 revisions

.. to be continued

just a test




Level 3: Loading Images and Using Switches (min/max vals)

****1. The Task:

Now it gets more challenging:

We are working on the truly usable version of our script, with the following enhancements over the "Level 2" version:

  • To make it look nicer, we want to display an icon before each of the two telemetry sensors.
  • Additionally, we will use a 3-position switch to retrieve either the current value (middle position) or the max/min value.
  • The color representation should also change accordingly (max values in red, min values in blue).

Example: Red = "Max Value"

The completed widget can already be found in the "tut 2.3" folder.

****2. Displaying Graphics

To display graphics or images under Ethos, they must first be "loaded" into the code. This effectively assigns a variable to the graphic.

In this example, this is done in the header section, i.e., at the "beginning" of the script.

This way, the variable is available to all handlers.

Since two sensor values will be displayed, I load two suitable images; the variables are named bmp1 and bmp2.

Often, images associated with the widget are stored in the corresponding widget directory, with the path specified accordingly.

What is the command for loading? Since we want to display an image on the screen, the method is logically located in the lcd class.

The code is as follows:

The display is achieved using the drawBitmap method, which can be referenced in more detail in the Reference Guide.

In general, the command is:

The graphic from the bmp variable is displayed at the coordinates x,y** **with the specified **width **and height.

3. Using Switches as a Source

The title says it all.

Whether it’s a telemetry sensor, logical switch, analog input, or physical switch, Ethos simply considers these objects as sources of some kind that return values.

Therefore, sources are defined as variables in the code.

As with telemetry sensors, the value() method reads a value from the source and assigns it to another variable.

Defining Switches as a Source

Remember, a source is defined as a variable only ONCE.

Once defined, it can be read as often as needed with value().

In 5.1, it was already mentioned that the header is executed once when the transmitter starts, along with the registration. Therefore, a variable for the switch sources (srcSwitch) is defined in the header and is available to this script environment.

As you can see, the syntax is the same as for the telemetry sensor; only a different category is used.

Using a Variable as Switch State (Handler)

Great, now we have a source, but how do I apply it?

First, I read the state of the switch in the wakeup handler:

Depending on the value, I then assign a "self-explanatory constant" to another variable.

This "other variable" can take on three states, just like the switch, and now represents the states "show minimum values," "show maximum values," and "show real-time values."

The names of the three corresponding constants were chosen as follows:

  • VALUE_LIVE
  • VALUE_MIN
  • VALUE_MAX

The variable that takes on one of these values "handles" the switch state and can therefore be referred to as a handler:

Assignment of the "switch handler" named swHandler:

Here you can see two things:

a)

Depending on the switch state (x < 0, x = 0 [middle position], or x > 0), the "switch handler" is assigned a value previously defined as a "self-explanatory constant" in the header.

The advantage is that later, you only need to check if the handler (representing the switch state) has the status for:

  • "Real-time" display, i.e., VALUE_LIVE
  • or "Minimum value display," i.e., VALUE_MIN, etc.

This makes the code much easier to read later, rather than repeatedly checking the actual switch value

for =0, <0, etc.

b)

Depending on the Max/Min state, a color value (tmpColor) is also set directly; only during the real-time display are the colors specifically chosen in the paint handler.

The necessary constants for the switch handler and colors were, of course, also added in the header beforehand.

For completeness:

Applying the Switch State

Now that swHandler has been set in the wakeup routine and represents the switch state, we can build a logic that reads the current, maximum, or minimum value from the telemetry sensors accordingly.

In the paint handler, you’ll find the following code block before displaying the values:

Depending on the switch state, the desired sensor values are provided.

It’s nice to see how the value method can specify parameters to achieve this.

  • OPTION_SENSOR_MIN
  • OPTION_SENSOR_MAX

The respective values are selected.

Such options are always listed under the 'base' section in the Lua reference guide.

... just take a look there to see what exists.

4. Displaying Min, Max, and Real-Time Data

As the title suggests ("display"), we are still in the paint handler.

Here is the essential excerpt for the actual display.

For Understanding: Before the actual data, the corresponding icon is placed first.

The Size of the Icon

Starting from the last widget, we add the necessary "sizing" for the bitmap, i.e., the size of the icon (local bmpSize). We set the icon size to 90% of the line height.

Positioning

We also define the variable bmpY for independent placement along the Y-axis, separate from the text. This adds a bit more code but looks nicer afterward (-;

Drawing

Finally, we can use lcd.drawBitmap(...) to draw the previously loaded bitmap.

Now, as in Level 2, the respective value is displayed!

5. A Preliminary Conclusion to This Exercise

With this, our original goal is achieved.

We display two telemetry values and can retrieve Max/Min values with a switch.

In addition to the three progressively developed widgets just described, a template is also included.

This allows the entire exercise to be easily followed in the simulator.

The template displays all three widgets simultaneously.

Feel free to experiment with the coding and make your own adjustments.

However (cliffhanger)!

I’m not a fan of conspiracy theories, but as is often the case in programming:

"Nothing is as it seems."

Our widgets seem to meet our goals and expectations in the simulator.

This is often the case. You’re pleased with the result, everything works as it should at first, but sooner or later, small issues arise because minor changes in the environment cause problems. The cause is not really the changed environment but that "not everything was done quite right."

I’ve intentionally placed a few small "Easter eggs" here; maybe you’ll spot them. Have fun searching! Only when these "Easter eggs" are found and fixed will this chapter truly be complete.

Otherwise, the solution will be revealed soon (-;

Further Information Sources

Ethos Lua Reference Guide

https://www.frsky-rc.com/wp-content/uploads/Downloads/EthosSuite/LuaDoc/index.html

The Ethos Lua Reference Guide represents the official documentation from FrSky.

It is a kind of reference book or overview of all currently available classes and methods under Ethos Lua. Additionally, the system constants are listed (category "base").

Usually, you start via the class overview and look at the available methods within a class to find out what functionalities can be implemented within a class.

Often, an example is provided for a method.

Github – Ethos community

https://github.com/FrSkyRC/ETHOS-Feedback-Community

As is well known, FrSky provides the latest software versions on GitHub, and using issue management, extensions can be requested or bugs can be reported.

On the entry page of the so-called repo, there is a typical git navigation structure with files and folders.

Among them is the folder "lua."

Here, several complete example Lua scripts on various topics such as forms ("tool-form"), graphical control ("widget-lcddemo"), and much more are available as examples.

Lua Basic Tutorial

https://www.tutorialspoint.com/lua/index.htm

Anyone who does not have any Lua/programming knowledge can find an online tutorial here for general programming knowledge.

The tutorial is, of course, general and does not address the specific requirements of Ethos Lua.

Fundamentals on topics such as variables, data types, operators, general syntax, etc., are clearly presented.

Official Lua Site

https://www.lua.org/

https://www.lua.org/manual/5.4/

https://www.lua.org/pil/contents.html#P3

The official Lua site.

A well-structured information source about Lua with a listing of all basic functions.

Especially noteworthy is the overview of the libraries with their (partially version-dependent) implemented methods.

These are, for example, important in handling strings ("string"), mathematical functions ("math"), IO operations (io), etc.

Engel Forum: -Lua Scripts

https://www.frsky-forum.de/forum/index.php?board/208-lua-scripte-f%C3%BCr-ethos/

https://www.frsky-forum.de/forum/index.php?board/241-download-bereich-f%C3%BCr-fertige-scripte/

The very active German forum also has sections for discussing Lua topics,

as well as an area where finished Lua scripts can be posted by authors.

RCG Lua thread

https://www.rcgroups.com/forums/showthread.php?4018791-FrSky-ETHOS-Lua-Script-Programming

The international "counterpart" to the Engel forum.

Here, too, there are regular discussions about the topic of Ethos Lua.

On the entry page, some scripts have been linked by Mike.

Lua Perfomance Tips

A very good document about optimizing lua performance can be found here:

https://www.lua.org/gems/sample.pdf

Glossary

Array

An ordered collection of elements addressed by indices.

In Lua, arrays are implemented as tables, with indices typically starting at 1.

Arrays can be multidimensional.

Compiler

A program that converts source code into an executable file.

However, Lua primarily uses an interpreter, but there are compilers like LuaJIT that can compile Lua code.

Class

A construct in object-oriented programming that defines a blueprint for objects, including their properties and methods.

Lua supports object-oriented programming through tables and metatables.

Debug

Generally, the process of removing errors from the code.

Under Ethos, the necessary information (values, process info, etc.) is largely provided via the print command in the simulator's shell window or via serial output.

****

Float

A data type for numbers with decimal places.

In Lua, all numbers are floats by default

Frame

Ethos-Lua: the area/frame in which a script runs on the home screen.

For the script, it is the "workspace" and "event horizon."

The script does not know "the world" outside the frame.



****Github

GitHub (https://github.com/) is a web-based platform for version control and collaborative development of software projects.

It uses Git, a distributed version control system, to track changes in the code.

Developers can create repositories, share code, report bugs, and collaborate on projects.

Users can also report bugs or request enhancements. Wikis are available.

GitHub also offers features such as project management tools, wikis, and Continuous Integration/Continuous Deployment (CI/CD).

Handler

****General: ****

A function or method that is called to process a specific event or condition.

Handlers are triggered by an event, such as:

  • Touch input or operation of a control button (event)
  • Calling the configuration menu (configure)
  • Changing a widget configuration (read/write)
  • Or when the system loops (e.g., mixer processing, LSW's, SF's, etc.) are completed in the internal process (wakeup)

Which handlers exist in the script is defined as an argument during registration.

Integer

A data type for whole numbers without decimal places.

In Lua, integers can also be represented as floating-point numbers, but there are libraries that support explicit integer operations.

Interpreter

A program that executes source code directly instead of compiling it. Lua is interpreted by default.

Key

A unique identifier in a table used to store and retrieve values. In Lua, keys can be any values except nil, but they are often strings or numbers.

Method

A function defined within a class or object that accesses or manipulates the object's data.

MPU

Abbreviation for Microprocessor or Microcontroller Processing Unit.

In embedded programming, this refers to the central processor of an "embedded application."

Objectorientated Programming** (OOP)**

A programming paradigm based on objects that encapsulate data (attributes) and functions (methods).

Lua supports OOP through the use of tables and metatables.

https://en.wikipedia.org/wiki/Object-oriented_programming

Pointer

A pointer is a variable that stores the address of another value.

Lua does not have explicit pointers like C/C++, but table references can be used similarly to pointers !

**Registration **

By registration, the script is made known to the Ethos system.

During the boot process, the transmitter searches the /scripts directory for all executable scripts, checks the syntax for major errors, and registers them if the check is plausible.

For this, the initialization handler is executed. This specifies the UID/Key, name, and type of the script (widget, source, task, etc.) and defines the list of used handlers.

For example, a widget named "Vartst" with various handlers is registered here, and the optional title display is generally turned off (title=false).

  • Code

    ** local function init()

    ** system.registerWidget({key="test10", name="VARtst", create=create, paint=paint, wakeup=wakeup, configure=configure, read = read, write = write, title=false} )

    ** end

UID

The "UID" (unique identifier) or "key" is a so-called unique key.

It identifies the script to the Ethos operating system. Even if the script's name is changed, Ethos can still "find" the script.

Therefore, the UID must not be used in another script.

It is used in the init handler during registration.

Widget

Often a graphical control element in a user interface, such as a button, textbox, or menu.

In Lua, widgets are little Apps running in a frame, organized by GUI framework.


Clone this wiki locally