How to Design your WebSocket Front Panel Application
This document is aimed at embedded systems designers who would like a basic introduction to designing a human-machine interface (HMI) prior to working with Mosaic's WebSocket messaging library. Assuming you understand the issues involved in the embedded control side, this will provide a top-down summary of the process in designing a WebSocket Front Panel interface.
This guide is will walk you through the broad steps required to design a water boiler control interface. The guide is structured into these key stages:
- Hardware description and desired capabilities.
- Breakdown of specific data and control signals.
- Functional Design of HTML human-machine interface.
The purpose of this document is to give you an idea of how to design a WebSocket Front Panel application to solve a specific problem. When designing your application, it is very beneficial to break down your problem in the same way this document does. Developers often skip this process and end up doing unnecessary work later down the road. This is sometimes referred to as a software specification. If you would like to read more, this article describes the costs and benefits of a software specifications: Painless Functional Specifications.
The system we want to design consists of two boilers. The lists below simply enumerate all the data and control points that we have available. When looking at your own hardware, this stage should be the easiest. Collect all the datasheet for the devices you will be using and make a list of every input/output that is available.
Each boiler provides the following output:
- Temperature in Celsius, represented by a float
- Pressure in pounds per square inch, represented by a float
- Flow measured in gallons per minute, represented by a float
Each boiler also accepts the following inputs:
- On / Off, represented by a boolean
- Temperature set point in Celsius, represented by a long int
Software Specification / System Capabilities
The following is an example of a synopsis of a software specification, roughly comparable in detail to the simple system description presented above.
Having a comprehensive software spec will greatly improve communications with your developer. If you are doing the development yourself, the software spec will help you in two ways. First, it helps you see the project from the user's perspective, and focus on providing the best possible user experience. Second, it helps you stay on course and save time.
Data Flow Breakdown
In this section we will cover how to control all the data in the system based on the hardware description shown above.
Controlling the Boilers
In this example we have two boilers that need to be controlled. Each of these boilers has an on/off switch as well as a temperature set point. Both of these variables should be saved on the PDQ Board as a
long respectively. In general these two variables will be write only; that is if the user turns one boiler off, it will remain off and not be turned back on except through the same interface. The same goes for the temperature set point — once set by the user, the set point will not be changed by other factors. However, in critical control applications such as this one it is useful to receive application-level feedback that a change has been accepted. Thus, in a final version of the application you may wish to add a Value Message from the PDQ Board to the browser communicating the current setpoint, and change the user interface to provide confirmation to the user that a new value has been accepted. One way this is done in our provided demo application is to grey out the relevant input in the browser after a new value has been entered, and re-enable the input when the updated value is received from the PDQ Board for confirmation.
You should use the following macros in your C application code for receiving values from the browser:
If you implement feedback to confirm updated values as described above, these macros are the simplest method for sending values from the PDQ Board to the browser:
Monitoring the Boilers
In the previous section we discussed how to control the boilers, now we will cover how to monitor them. The best way to approach monitoring the boilers is to constantly send the status from the PDQ Board to the browser. This can be accomplished by calling the appropriate functions inside a continuous loop. One thing to consider is the frequency of updates. If the boiler is very large with a slow rate of change, it may only be necessary to sample and update the temperature once per minute. If this is not true, once per second or more may be necessary. Sending messages more often than needed is a waste of resources, including processing time and bandwidth. You should be careful to design your system in the most efficient way possible to make further expansion easy.
Each boiler in this example has three
float type variables that can be sampled. They are temperature, pressure, and flow rate. To send these values to the browser, you should call the following function:
These three float values will need to be sent to the browser for each boiler that is connected.
Note about Control Logic
Designing the HTML Human-Machine Interface
The HTML human-machine interface (HMI) is the webpage that the operator views in a browser. The HTML HMI runs in the browser, and is the counterpart to the C application which runs on the PDQ Board. When designing your HTML HMI it's important to remember that this portion of your application is only for viewing and modifying data.
It's best to use unique variable names when designing your HTML HMI. Data can be generated by both the HMI in the browser and the application running on the PDQ Board. This data is represented by variables which have a fixed origin. If a variable is calculated, generated, or sampled by the PDQ Board, then it originates from the application. If a variable or control signal is entered or triggered by the user, then its origin is the HMI running in the browser.
Regardless of which side of the connection the data originates from, the name of the variable holding the data on the PDQ Board and the HTML element holding the data in the browser should be similar to avoid confusion.
Choosing Variable Names
In this example we have data coming from the boilers, and inputs going into the boilers. Here we will lay out a set of suggested names. In the next section we will talk about using these names in the HTML human-machine interface (HMI).
This list is based on the software specification section above. The following variable names originate in the application running on the PDQ Board and will be displayed in the HMI running in the browser.
The following variables originate in the HMI running in the browser and are sent to the application on the PDQ Board:
After laying out desired variable names, the first stage is to build your HTML HMI. Here is a screen shot and source code for a simple HTML HMI that is built with variable names set up correctly.
<!DOCTYPE html> <html lang="en"><head> <meta charset="utf-8" /> <link rel="icon" href="data:image/png;base64," /> <title>Mosaic EtherSmart WebSocket Boiler Control</title> </head><body> <div class="client_side_page" id="boiler"> <table> <tr><th colspan="2">Boiler 1</th></tr> <tr><td>Temperature:</td><td id="boiler1Temperature"></td></tr> <tr><td>Pressure:</td><td id="boiler1Pressure"></td></tr> <tr><td>Flow Rate:</td><td id="boiler1Flow"></td></tr> </table> <hr /><p> Set Temperature: <input type="text" id="boiler1Setpoint" onChange="MosaicPDQ.sendValue('boiler1Setpoint',this.value)" /> <br /> Boiler Switch: <input type="button" value="on" onClick="MosaicPDQ.sendValue('boiler1On',true)" /> <input type="button" value="off" onClick="MosaicPDQ.sendValue('boiler1On',false)" /> <br /><br /></p> <table> <tr><th colspan="2">Boiler 2</th></tr> <tr><td>Temperature:</td><td id="boiler2Temperature"></td></tr> <tr><td>Pressure:</td><td id="boiler2Pressure"></td></tr> <tr><td>Flow Rate:</td><td id="boiler2Flow"></td></tr> </table> <hr /><p> Set Temperature: <input type="text" id="boiler2Setpoint" onChange="MosaicPDQ.sendValue('boiler2Setpoint',this.value)" > <br /> Boiler Switch: <input type="button" value="on" onClick="MosaicPDQ.sendValue('boiler2On',true)" /> <input type="button" value="off" onClick="MosaicPDQ.sendValue('boiler2On',false)" /> </div> </body></html>
With the interface defined and WebSocket communication functioning, you can implement the necessary control signals for your application-specific equipment using the PDQ Board built-in inputs and outputs, or using Mosaic's range of Modular I/O Boards for expanded measurement and control options. See the collection of demo programs provided with Mosaic IDE Plus for ideas on implementing the embedded side of your application.