Home Soluciones Control de un Smart Display Custom CAN ID con Arduino y OLED Knob Display

Control de un Smart Display Custom CAN ID con Arduino y OLED Knob Display

Mar 01, 2024

Introducción

El protocolo Custom CAN ID se utiliza ampliamente en aplicaciones de automatización industrial para el control de dispositivos. En este contexto, una placa Arduino constituye una solución práctica para la integración de sistemas y puede utilizarse como controlador host de Smart Displays, especialmente en modelos sin función táctil. Mediante el protocolo Custom CAN ID, Arduino permite controlar eficazmente Smart Displays sin interfaz táctil.

En este artículo se presenta un programa de demostración que utiliza un Arduino UNO junto con un CAN bus shield para implementar la comunicación mediante el protocolo Custom CAN ID. El ejemplo muestra cómo controlar un Smart Display utilizando un OLED Knob Display como dispositivo de entrada. A través de este programa se pueden explorar distintas funciones y operaciones de un Smart Display sin función táctil. El ejemplo sirve como referencia para desarrolladores que deseen ampliar sus conocimientos sobre integración de sistemas y sobre el control de Smart Displays, tanto táctiles como no táctiles, mediante un OLED Knob Display. El desarrollo de la aplicación se muestra en el siguiente diagrama.

Para esta aplicación se requieren los siguientes componentes:

  1. Smart Display Custom CAN ID de 10,1”
  2. Arduino UNO
  3. CAN bus shield para Arduino UNO
  4. Módulo OLED Display Knob Rotator
  5. ST-Link CAN bus Dongle
  6. GUI Builder v0.4.2 o posterior
  7. Arduino IDE v2.0.4
 

La demostración se divide en tres partes:

  1. Diseño del proyecto de demostración en GUI Builder.
  2. Compilación y carga del proyecto.
  3. Programación del host Arduino.
 

Diseño del proyecto de demostración en GUI Builder

Para empezar, abra una versión actualizada de GUI Builder y cree un nuevo proyecto. Introduzca el nombre del proyecto y compruebe que la carpeta correspondiente se haya seleccionado automáticamente. A continuación, seleccione el tipo de dispositivo; en este ejemplo se utiliza un display de 10,1". Seleccione el protocolo correspondiente y mantenga la orientación predeterminada en modo horizontal. Elija una plantilla de interfaz en blanco y haga clic en el botón Create para crear el proyecto. La siguiente imagen muestra los pasos descritos.

Una vez creado el proyecto, se abrirá la siguiente pantalla.

Para implementar el escenario de demostración se necesitan un total de cuatro páginas, por lo que deben añadirse tres páginas adicionales. Para ello, localice el botón Page y haga clic en él. A continuación, pulse el botón Plus para añadir las tres páginas restantes.

El siguiente paso consiste en añadir un fondo personalizado. Vaya a la sección de recursos y localice la opción Background. En la opción 2 encontrará tres fondos predefinidos para las páginas Industry, Medical y Vehicle. Para añadir otro fondo, haga clic en Add Widget en la opción 3. A continuación, pulse el botón de tres puntos situado a la izquierda del botón Reset en la opción 4. Desde este botón (...) puede seleccionar un fondo personalizado para sustituir el fondo predeterminado que se utilizará en la primera página.

A continuación, puede seleccionar el estilo de fondo que desee entre las opciones disponibles en la sección Pages, tal como se muestra en la siguiente imagen.

Ahora se añadirá un widget personalizado. De acuerdo con el escenario de demostración, se utiliza un widget Multistate personalizado para seleccionar las páginas Industry, Medical y Vehicle. Vuelva a la sección Controls de la primera página y, dentro de la sección de recursos, localice la opción Multistate. Haga clic en Add Widget en la opción 2 y, a continuación, en Modify en la opción 3. En el paso 4, elimine todas las imágenes predeterminadas asociadas al widget. Después, haga clic en Add en la opción 5 y seleccione individualmente las imágenes personalizadas de los widgets desde la carpeta local del ordenador, tal como se indica en el paso 6. Por último, haga clic en OK en el paso 7 para añadir las imágenes personalizadas a la lista del widget Multistate, como se muestra a continuación.

Vuelva a la sección Controls de la primera página. Siguiendo el escenario de demostración, seleccione el widget Multistate personalizado que permitirá elegir entre las páginas Industry, Medical y Vehicle. Arrastre el widget hasta el área de diseño de la página y colóquelo en la posición correspondiente. Con este paso queda creada la primera página.

Aplique el mismo procedimiento a las otras tres páginas creadas. En la segunda página, seleccione un widget relacionado con aplicaciones industriales; en la tercera, uno relacionado con aplicaciones médicas; y en la cuarta, uno relacionado con vehículos. Arrastre y coloque cada widget en el área de diseño de la página correspondiente.

Compilación y carga del proyecto

Una vez creadas las cuatro páginas y añadidos los widgets correspondientes en cada una de ellas, asegúrese de incluir en la página inicial el widget Multistate personalizado que permite seleccionar las páginas Industry, Medical y Vehicle. A continuación, proceda a compilar el proyecto. Vaya a la sección Page Information, localice el botón Device y haga clic en él para seleccionar Device Properties. Compruebe que la configuración del protocolo sea correcta, seleccione el puerto COM correspondiente y establezca la velocidad en baudios deseada. Para establecer la conexión con el dispositivo, haga clic en el botón "Connect to Device". Por último, haga clic en Upload para iniciar la carga del proyecto, tal como se muestra en la siguiente imagen. Espere hasta que el proceso de carga haya finalizado.

Una vez finalizada la carga del proyecto, haga clic en OK, tal como se muestra en la siguiente imagen.

Una vez completada la carga, aparecerá la pantalla de inicio que se muestra a continuación.

Después de la pantalla de inicio, el sistema pasará a la primera página. Con ello finaliza el proceso de compilación y carga mediante GUI Builder, tal como se muestra en la siguiente imagen.

Programación del host Arduino

El fragmento de código que se muestra a continuación comienza con una sección de inclusiones ("includes"), en la que se importan las distintas bibliotecas y archivos de cabecera necesarios para el programa. Entre ellos se encuentran bibliotecas como Adafruit_SSD1327, Adafruit_FT6206, Adafruit_GFX y SPI, además de archivos de cabecera específicos como mcp2515_can.h, lcdgfx_gui.h y lcdgfx.h.

A continuación se encuentra la sección de definiciones ("defines"), en la que se establecen distintas constantes y configuraciones de pines. Esta sección incluye definiciones para el encoder rotativo, las dimensiones del display OLED, la configuración del bus CAN, los ajustes de los widgets y otros parámetros.

Por último, una instrucción condicional comprueba el tipo de microcontrolador utilizado y selecciona la interfaz serie correspondiente. Si el código se ejecuta en un microcontrolador SAMD, se define la interfaz SerialUSB. En caso contrario, se utiliza la interfaz Serial estándar.

En conjunto, este fragmento de código incorpora las bibliotecas y archivos necesarios, define las constantes y configuraciones de pines y selecciona la interfaz serie adecuada en función del tipo de microcontrolador utilizado.

A continuación, se declaran e inicializan distintas variables y pines necesarios para el funcionamiento del programa. Por ejemplo:

SPI_CS_PIN: Esta constante tiene el valor 9 y corresponde al pin Chip Select utilizado para la comunicación SPI.
CAN_INT_PIN: Esta constante tiene el valor 2 y corresponde al pin de interrupción del bus CAN.
CAN: Se crea una instancia de la clase mcp2515_can y se inicializa con el valor SPI_CS_PIN. Esta instancia se utiliza para la comunicación a través del bus CAN.
ts: Se crea una instancia de la clase Adafruit_FT6206, utilizada para gestionar la función táctil.
display: Se crea una instancia de la clase DisplaySSD1327_128x128_SPI y se inicializa con la configuración de pines utilizada para la comunicación SPI con el display SSD1327.

La siguiente sección del código declara e inicializa varios arrays formados por variables de tipo unsigned char. La función de cada array es la siguiente:

“configMsg”: Array de 8 elementos de tipo unsigned char que representa un mensaje de configuración.
`PageIndex_0` a `PageIndex_3`: Cada uno de estos arrays contiene 8 elementos de tipo unsigned char y representa los índices de las páginas 0 a 3.
“displayMode”: Array de 8 elementos de tipo unsigned char que representa el modo de visualización.

Además, se definen varios arrays denominados `stmp`, `stmp1`, `stmp2` y así sucesivamente hasta `stmp12`. Cada uno de ellos también contiene 8 elementos de tipo unsigned char y se utiliza para almacenar bytes de datos correspondientes a distintos widgets o componentes.

En conjunto, estos arrays almacenan los conjuntos de datos necesarios para el programa, incluidos los mensajes de configuración, los índices de página, los modos de visualización y los datos asociados a los distintos widgets.

A continuación se define una función denominada “bitmapDemo”, que recibe el parámetro entero “imageIndex”. Esta función se encarga de mostrar una imagen en el OLED Knob Display.
Las imágenes específicas, junto con sus correspondientes posiciones y dimensiones, se definen en el archivo de cabecera "Image.h".

La siguiente función espera una respuesta a través del bus CAN, introduciendo repetidamente un determinado retardo y comprobando el valor de la variable de indicador Recv. Una vez recibida la respuesta, el valor de Recv se restablece a 0.

Este código define una función denominada `changePageFunction`, encargada de cambiar el valor de página dentro del sistema de comunicación mediante bus CAN. La función envía mensajes a través del bus CAN para cambiar de página en función del parámetro `pageValue` recibido. Los mensajes enviados dependen del valor de `pageValue` y corresponden a los distintos arrays `PageIndex`.

La función "handleTouchEvents" gestiona los eventos táctiles del display. Detecta las entradas táctiles, convierte las coordenadas y ejecuta distintas acciones en función de la presión y la duración de la pulsación. También utiliza `changePageFunction` para actualizar la página actual según la entrada detectada. Por ejemplo, cuando se detecta una pulsación prolongada, se llama a "changePageFunction" con el valor de "nowPage" para volver a la página de inicio. Cuando se detecta una pulsación breve, se llama a "changePageFunction" con el valor de "nowPage" para cambiar a la página seleccionada.

El fragmento de código que se muestra a continuación corresponde a la función "setup" de Arduino, que se ejecuta una sola vez al iniciar el programa. Esta función se encarga de inicializar los pines, establecer la comunicación serie, configurar el display, configurar el bus CAN e inicializar el controlador de la pantalla táctil.

En primer lugar, la función configura el modo de varios pines (pinA, pinB, pinC y EN_Pin), ya sea como entradas con resistencias pull-up habilitadas o como salida. El pin de salida EN_Pin se establece en nivel lógico alto.

A continuación, se establece la comunicación serie a una velocidad de 115200 baudios y el código espera hasta que se haya establecido la conexión.

Después se inicializa el objeto display y se configuran distintos parámetros, como la fuente y el color. A continuación, se dibuja una imagen bitmap en una posición determinada del display y se aplica un retardo de 2 segundos.

Se configura una interrupción en el pin CAN_INT_PIN y se especifica la función MCP2515_ISR como rutina que debe ejecutarse cuando se produzca la interrupción. Esta interrupción se activa con el flanco descendente de la señal.

El bus CAN se inicializa a una velocidad de 250 kbit/s. Si la inicialización falla, el código vuelve a intentarlo después de un determinado retardo. Una vez completada correctamente, el bus CAN se establece en modo normal y se muestra un mensaje de confirmación a través de la salida serie.

A continuación, se configuran las máscaras y los filtros para aceptar todas las tramas, incluidas las tramas extendidas.

Después se inicializa el controlador de la pantalla táctil. Si la inicialización falla, se muestra un mensaje de error y el programa entra en un bucle infinito.

Por último, cuando el controlador táctil se ha iniciado correctamente, se muestra un mensaje de confirmación a través de la salida serie.

Esta función actúa como una rutina de servicio de interrupción (ISR) para el MCP2515, el controlador CAN. Cuando se activa una interrupción, la función establece un indicador y muestra un mensaje.

Estas funciones están relacionadas con la gestión del estado del mando giratorio. La función “setKnobState” actualiza el estado del mando y establece un temporizador para detectar el estado de inactividad, mientras que la función “isKnobIdle” comprueba, a partir del valor del temporizador, si el mando se encuentra inactivo.

La función “redrawScreen()” actualiza el contenido del display en función del estado actual del mando giratorio. Comprueba si se ha producido un cambio de estado, borra la pantalla y muestra la imagen bitmap correspondiente según el estado del mando.

La siguiente parte de la función “loop()” lee el estado de tres pines y determina un nuevo estado a partir de sus valores. Si el nuevo estado es diferente del anterior, se ejecutan distintas acciones, entre ellas la actualización del contador y de las variables “MultiStateValue”, “GaugeValue” y de otros widgets.

Después del bloque anterior de la función “loop()”, esta parte del código gestiona el caso en el que el mando gira en una dirección determinada. El programa actualiza las variables correspondientes y llama a las funciones necesarias. A continuación, actualiza la variable que almacena el estado anterior para la siguiente iteración de “loop()”.

La siguiente sección muestra otra parte de la función “loop()”. Después del bloque de código anterior, se realizan las siguientes operaciones.

La variable oldState se actualiza con el valor de newState.

Si nowPage es igual a 0, correspondiente a la página 1, el código comprueba si MultiStateValue es diferente de LastMultiStateValue. Si los valores son distintos, LastMultiStateValue se actualiza con el valor de MultiStateValue y dicho valor se almacena en el array stmp1. A continuación, se envía a través del bus CAN un mensaje que contiene el valor de MultiStateValue utilizando el ID Multi-State 0x716.

Si nowPage es igual a 1, correspondiente a la página 2, se realizan comprobaciones similares para las variables de los distintos widgets (CircleProgressValue, HorizontalSliderValue, VerticalSliderValue, TemperatureValue, GaugeValue, FixedWidgetValue e IndicatorValue). Si alguna de estas variables es diferente de su valor anterior correspondiente, se actualiza dicho valor y se envía a través del bus CAN un mensaje con el nuevo valor utilizando el ID correspondiente.

Si nowPage es igual a 2, correspondiente a la página 3, se realizan comprobaciones similares para los widgets disponibles en dicha página, como CircleProgressValue, HorizontalSliderValue, GraphValue y AnimationValue. Si alguna de estas variables es diferente de su valor anterior correspondiente, se actualiza dicho valor y se envía a través del bus CAN un mensaje con el nuevo valor utilizando el ID correspondiente.

Si nowPage es igual a 3, correspondiente a la página 4, se realizan comprobaciones similares para los widgets disponibles en esta página, como HorizontalSliderValue, GaugeValue, FixedWidgetValue, AnimationValue, IndicatorValue y ToggleButtonValue. Si alguna de estas variables es diferente de su valor anterior correspondiente, se actualiza dicho valor y se envía a través del bus CAN un mensaje con el nuevo valor utilizando el ID correspondiente.

Después del bloque de código anterior dentro de la función “loop()”, se llama a la función handleTouchEvents() para gestionar los eventos táctiles.

Si el mando se encuentra inactivo (isKnobIdle() devuelve 1), su estado se establece en KNOB_IDLE mediante la función setKnobState(). A continuación, se llama a redrawScreen() para actualizar la pantalla. Con ello finaliza el código del proyecto de demostración.

Una vez verificado y cargado correctamente el programa mediante Arduino IDE, el contenido mostrado en el OLED Knob Display cambiará. La imagen de Smart Display será sustituida por una indicación de Touch o Rotate. En este momento, tanto el Smart Display como el OLED Knob Display mostrarán la página de inicio predeterminada.

A partir de este momento puede ejecutar los distintos escenarios de la demostración. Desde la página de inicio, gire el mando para seleccionar una de las tres páginas disponibles: Industry, Medical o Vehicle, tal como se muestra en la siguiente imagen.

Una vez seleccionada la página, una pulsación breve sobre el OLED Knob Display permite cambiar inmediatamente el Smart Display a la página seleccionada.

Veamos otro ejemplo del funcionamiento de la demostración. Desde la página de inicio, gire el mando para seleccionar una de las otras tres páginas. En este ejemplo se selecciona la página Medical.

Después de seleccionar la página Medical, pulse brevemente el OLED Knob Display para acceder a la página seleccionada en el Smart Display.

Al girar el mando del OLED Knob Display hacia la izquierda o hacia la derecha, es posible controlar los distintos widgets disponibles en la página, tal como se muestra en la siguiente imagen.

Una pulsación prolongada sobre el OLED Knob Display permite volver automáticamente a la página de inicio, es decir, la página 1. Además, si el mando no se gira ni se pulsa durante 10 segundos, el display se restablece y vuelve automáticamente a la página de inicio.

Con esto finaliza la demostración desarrollada para el Smart Display de 10,1" y el OLED Knob Rotator Display. La demostración permite controlar distintas páginas y cambiar entre ellas mediante pulsaciones breves o prolongadas en el OLED Knob Rotator Display. Asimismo, permite interactuar con los distintos widgets disponibles en cada página.

El programa utilizado en esta demostración está disponible en GitHub: https://bit.ly/3oT0o5M. Desde este enlace puede descargar el programa y consultar más información sobre el proyecto de demostración.

La configuración física del hardware utilizada en la demostración se muestra en la siguiente imagen.

Este programa ofrece una demostración práctica de cómo utilizar una placa Arduino junto con un OLED Knob Rotator Display y el protocolo Custom CAN ID para gestionar distintas páginas y navegar entre ellas mediante pulsaciones breves o prolongadas. También permite interactuar con los distintos widgets disponibles en cada página y controlar sus funciones. El programa constituye una referencia práctica tanto para desarrolladores principiantes como experimentados que deseen conocer mejor la programación del host y su aplicación al control de Smart Displays, especialmente aquellos que no incorporan funcionalidad táctil.

¿Tiene preguntas sobre soluciones de pantallas para su negocio? Contacte con nosotros!

Subscribirse

Reciba correos electrónicos sobre nuevas actualizaciones de Winstar

Contacte con nosotros

Precio/Ficha técnica/Consulta general

Soporte técnico

Contacte con nosotros para cualquier información técnica

go top
Contacto
close

Valoramos tu privacidad

Al hacer clic en "Permitir todas las cookies", aceptas el almacenamiento de cookies en tu dispositivo para mejorar la navegación en el sitio, analizar el uso del sitio y ayudar en nuestros esfuerzos de marketing y rendimiento. Puedes encontrar más información sobre este tema en nuestra política. Política de privacidad

Valoramos tu privacidad

Winstar y ciertos terceros utilizan cookies en www.winstar.com.tw. Los detalles sobre los tipos de cookies, su propósito y las partes involucradas se describen a continuación y en nuestra Política de Cookies. Haga clic en “Permitir todos” para dar su consentimiento para el uso de cookies y tener la mejor experiencia posible en nuestros sitios web. También puede establecer sus preferencias o rechazar cookies (excepto las cookies estrictamente necesarias).

Gestionar preferencias de consentimiento

Siempre activo
Cookies esenciales

Estas cookies son esenciales para permitirte navegar por el sitio web y utilizar sus funciones, como establecer tus preferencias de privacidad, iniciar sesión o completar formularios.

Cookies de análisis

También conocidos como "cookies estadísticas", estas cookies recogen información sobre cómo utilizas un sitio web, como qué páginas has visitado y qué enlaces has clicado. Ver detalles.