Arduino + Java: Fácil y Rápido

66
67124

Recientemente hemos lanzado una nueva y mejorada versión de la librería PanamaHitek_Arduino. Con el lanzamiento de la versión 2.8.2, considero que es hora postear algo sobre la utilización de esta herramienta. Esta librería consiste en un a herramienta que hemos desarrollado para facilitar la integración de proyectos de Arduino + Java.

Este código ha evolucionado a través del tiempo hasta convertirse en lo que es hoy, uno de los recursos más utilizados para comunicar Arduino y Java. Se trata de una colección de métodos que facilitan tareas a los usuarios. Con solo ver los ejemplos de uso nos damos cuenta que no se requiere muchos conocimientos de programación para implementar este código y lograr resultados interesantes.

Antes de proceder con los ejemplos de uso, es importante que el usuario tenga claro algunos conceptos. Para ello recomiendo algunos de los posts que ya hemos publicado sobre este tema:

Ahora vamos a proceder con algunos ejemplos sobre instalación e implementación de la librería.

Instalación de la librería

Para instalar la librería podemos utilizar dos métodos: descargar el JAR o usar maven. El archivo JAR lo podemos encontrar en los repositorios de Panama Hitek en Github o en Sourceforge.

Cuando se haya descargado el fichero JAR podemos agregarlo a un proyecto y empezar a programar. Suponiendo que estamos Netbeans como IDE de Java, el agregar un JAR resulta muy fácil.

java_add_jar

java_added_jar

Este es el método tradicional, aunque debo decir que ya está obsoleto. La tendencia es utilizar gestores de repositorios, como Maven.

¿Qué es Maven y para qué se utiliza?

Hace un tiempo escribí un post sobre cómo agregar la librería PanamaHitek_Arduino a un proyecto utilizando Maven. He aquí el enlace:

Utilizar Github como repositorio de Maven

Con la ayuda de este tipo de herramientas se nos hace muy fácil importar cualquier tipo de librería a nuestro proyecto.

Las clases de la librería

Nuestra librería cuenta con 4 clases:

  • PanamaHitek_Arduino: esta clase permite manejar todo lo relacionado a la conexión con el Arduino a través del puerto serie. Contiene los métodos para iniciar y detener la conexión, los parámetros de comunicación serie y las funciones para envío y recepción de datos.
  • PanamaHitek_Multimessage: clase que permite recibir múltiples datos en el Arduino de forma simultánea. Es muy útil a la hora de trabajar con varios sensores a la vez y cuando queremos que el Arduino nos entregue los valores de diferentes al mismo tiempo.
  • PanamaHitek_SpreadSheetHandler: una clase que estamos desarrollando para almacenamiento de datos y su posterior exportación a ficheros de MS Excel (formato .xls). Estaremos publicando más sobre esto en los próximos días.
  • ArduinoException: gestor de excepciones de la librería.

La clase ArduinoException es una herramienta auxiliar de las primeras tres clases nombradas. En el futuro esperamos agregar nuevas clases con funcionalidades tales como gráficas en tiempo real, manejo de bases de datos y comunicación a través de Internet. En un futuro esperamos que esta librería sea la herramienta más completa para el desarrollo de proyectos Arduino + Java.

Ejemplos de Arduino + Java

Transmisión en Java – Recepción en Arduino

Este es el ejemplo más sencillo de todos. Me gusta ilustrarlo a través del encendido de un LED en Arduino desde un programa en Java. Lo que hacemos es programar un código en el Arduino en el cual al enviar un «1» desde el Monitor Serie encendemos un LED. Cuando se envía un «0», se apaga el LED.

Los códigos, tanto el de Arduino como el de Java los pueden encontrar en nuestro repositorio de Github. El código de Arduino luce así:

arduino-y-java

Si lo subimos al Arduino, nos damos cuenta que enviando el 1 y el 0 desde el Monitor Serie provoca un cambio de estado en el LED que tengamos conectado al Pin 13.

Ahora, en vez de enviar el 1 y el 0 desde el Monitor Serie, lo haremos con un programa en Java. El código, disponible en Github, luce así:

arduino-y-java

Se trata de un código sencillo. En la línea 17 creamos una instancia de la librería. En la línea 22 iniciamos la conexión con Arduino (puerto COM4). Esta conexión debe ser iniciada como ArduinoTX debido a que vamos a transmitir información.

Luego las líneas 81 y 91 representan los métodos que se ejecutan al presionar dos botones, los cuales envían «1» y «0» para encender y apagar el LED.

Cuando se ejecuta el código debe aparecer una ventana similar a la de la siguiente imagen.

arduino-y-java

Este mismo código, así como está, puede ser utilizado para lograr cosas interesantes como la que se muestra en el siguiente video.

Es el mismo código, solo que con un circuito de potencia (optoacoplados + TRIAC). En el caso del programa en Java, le hemos dado un estilo gráfico un poco más llamativo. Pero la programación de las acciones de los botones permanece igual.

Transmisión en Arduino- Recepción en Java

Una vez más contamos con dos códigos, uno para Arduino y uno para Java. Ambos se encuentran disponibles en nuestro repositorio de Github. El código de Arduino es el siguiente:

arduino-y-java

Lo que hacemos aquí es enviar un mensaje al Puerto Serie. El mensaje está compuesto por la palabra «Mensaje » seguido de un número que aumenta una unidad por cada segundo.

Ahora en Java vamos a recibir esta información y a imprimirla en la consola. El código en Java es el siguiente:

Arduino + Java

Otro código sencillo. En la línea 19 creamos la instancia de la librería. La línea 20 crea una variable listener que escuchará el Puerto Serie para determinar cuando se ha recibido un Byte. En la línea 24 se discrimina cuando ha finalizado la recepción de un mensaje desde Arduino.

La línea 26 es la encargada de imprimir el mensaje recibido en la consola (ino.printMessage() devuelve un String con el mensaje recibido). En la línea 37 iniciamos la conexión con el Arduino (puerto COM4), esta vez utilizando el método ArduinoRX que es especial para recepción de datos.

 

Transmisión y Recepción entre Arduino y Java

Esta vez haremos una comunicación de dos vías. Vamos a encender y apagar un LED desde Java, pero Arduino nos enviará un mensaje cada vez que lo hagamos. El código de Arduino es el siguiente:

arduino-y-java

Si lo probamos en el Monitor Serie nos daremos cuenta que podemos encender o apagar el LED con «1» y «0». Cuando lo hagamos, recibiremos un mensaje con el estado lógico del LED, seguido de un tiempo en milisegundos. Este tiempo corresponde a la cantidad de milisegundos que ha trascurrido desde el inicio del programa.

El código en Java incluye un botón de encendido y apagado, junto a un Label donde se mostrará el resultado recibido desde Arduino.

arduino-y-java

El código en Java es el siguiente:

Arduino + Java

Una programación sencilla, similar a las anteriores. La excepción en este código es la línea 28, con el método arduinoRXTX. También tenemos la línea 18, donde en vez de imprimir el mensaje en la consola, lo pasamos a el Label que colocamos en la interfaz.

Este ejemplo muestra las posibilidades que existen cuando integramos Arduino + Java. Interfaces gráficas acopladas a circuitos electrónicos es la base fundamental de proyectos avanzados con posibilidad de una amplia variedad de resultados.

Demostración en tiempo real

El siguiente video lo he preparado para demostrar el funcionamiento de cada uno de los códigos que hemos presentado en este post.

Debo recordarles que los códigos de todos estos ejemplos se encuentran disponibles en nuestro repositorio de Github. Es importante adquirir la buena costumbre de trabajar en base a repositorios y herramientas de programación para control de versiones como Git. Sobre estos temas ya hemos escrito antes en este blog:

Guía básica sobre el uso de Git y GitHub

Cómo contribuir en proyectos con Git y GitHub

Esperamos que la información mostrada sea de utilidad para ustedes. Cualquier duda, comentario, observación u opinión, no duden dejarla en la caja de comentarios.

 

 

 

66 Comentarios

  1. Muchas gracias, funcionan muy bien, a un inicio no me funciono con Java 14 y netbeans 11.3(porblemas con maven), luego intente con Java 8 y NetBeans 8.2 y todo va excelente

    • No he podido actualizar por encima de Java 8, principalmente porque la librería en la que me he basado, la JSSC, funciona hasta la versión 1.8. Hace falta investigar más para poder actualizar

  2. Buenas, me ha encantado el post pero como siempre, me dan fallo las cosas.
    El programa funciona bien sin enchufar arduino, me sale la ventana con los botones y todo eso pero cuando enchufo arduino al puerto USB y le doy run me sale el siguiente error:
    Command execution failed.
    org.apache.commons.exec.ExecuteException: Process exited with an error: 1 (Exit value: 1)
    at org.apache.commons.exec.DefaultExecutor.executeInternal(DefaultExecutor.java:404)
    at org.apache.commons.exec.DefaultExecutor.execute(DefaultExecutor.java:166)
    at org.codehaus.mojo.exec.ExecMojo.executeCommandLine(ExecMojo.java:764)
    at org.codehaus.mojo.exec.ExecMojo.executeCommandLine(ExecMojo.java:711)
    at org.codehaus.mojo.exec.ExecMojo.execute(ExecMojo.java:289)
    at org.apache.maven.plugin.DefaultBuildPluginManager.executeMojo(DefaultBuildPluginManager.java:134)
    at org.apache.maven.lifecycle.internal.MojoExecutor.execute(MojoExecutor.java:207)
    at org.apache.maven.lifecycle.internal.MojoExecutor.execute(MojoExecutor.java:153)
    at org.apache.maven.lifecycle.internal.MojoExecutor.execute(MojoExecutor.java:145)
    at org.apache.maven.lifecycle.internal.LifecycleModuleBuilder.buildProject(LifecycleModuleBuilder.java:116)
    at org.apache.maven.lifecycle.internal.LifecycleModuleBuilder.buildProject(LifecycleModuleBuilder.java:80)
    at org.apache.maven.lifecycle.internal.builder.singlethreaded.SingleThreadedBuilder.build(SingleThreadedBuilder.java:51)
    at org.apache.maven.lifecycle.internal.LifecycleStarter.execute(LifecycleStarter.java:128)
    at org.apache.maven.DefaultMaven.doExecute(DefaultMaven.java:307)
    at org.apache.maven.DefaultMaven.doExecute(DefaultMaven.java:193)
    at org.apache.maven.DefaultMaven.execute(DefaultMaven.java:106)
    at org.apache.maven.cli.MavenCli.execute(MavenCli.java:863)
    at org.apache.maven.cli.MavenCli.doMain(MavenCli.java:288)
    at org.apache.maven.cli.MavenCli.main(MavenCli.java:199)
    at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.base/java.lang.reflect.Method.invoke(Method.java:564)
    at org.codehaus.plexus.classworlds.launcher.Launcher.launchEnhanced(Launcher.java:289)
    at org.codehaus.plexus.classworlds.launcher.Launcher.launch(Launcher.java:229)
    at org.codehaus.plexus.classworlds.launcher.Launcher.mainWithExitCode(Launcher.java:415)
    at org.codehaus.plexus.classworlds.launcher.Launcher.main(Launcher.java:356)
    ————————————————————————
    BUILD FAILURE
    ————————————————————————
    Total time: 2.238 s
    Finished at: 2020-03-29T23:20:41+02:00
    Final Memory: 8M/37M
    ————————————————————————
    Failed to execute goal org.codehaus.mojo:exec-maven-plugin:1.5.0:exec (default-cli) on project mavenproject5: Command execution failed. Process exited with an error: 1 (Exit value: 1) -> [Help 1]

    To see the full stack trace of the errors, re-run Maven with the -e switch.
    Re-run Maven using the -X switch to enable full debug logging.

    For more information about the errors and possible solutions, please read the following articles:
    [Help 1] http://cwiki.apache.org/confluence/display/MAVEN/MojoExecutionException

    Y no se abre la ventena. Necesito ayuda!!
    Muchas gracias y un saludo!!!

    • Parece algo de Maven. Compila el proyecto antes de ejecutarlo a ver si hace falta que se descarguen algunas dependencias

      • Buenas, sigue saliendo el mismo error haga lo que haga (siempre que arduino esté conectado).
        Como puedo descargar las dependencias de maven?

        • hola Jose tengo el mismo problema .cuando no esta conectado el arduino abre el Frame con los botones y cuando lo conecto me sale :

          Comunicacion Serial Library, version 2.1
          ==============================================
          Esta Libreria ha sido creada desde Java Simple Serial Connector, por Alexey Sokolov
          Esta Libreria esta basada en La libreria PanamaHitek.
          Puede encontrar toda la información sobre esta biblioteca en http://panamahitek.com
          #
          # A fatal error has been detected by the Java Runtime Environment:
          #
          # EXCEPTION_ACCESS_VIOLATION (0xc0000005) at pc=0x000000006ec4b5bb, pid=1508, tid=4964
          #
          # JRE version: Java(TM) SE Runtime Environment (13.0.2+8) (build 13.0.2+8)
          # Java VM: Java HotSpot(TM) 64-Bit Server VM (13.0.2+8, mixed mode, sharing, tiered, compressed oops, g1 gc, windows-amd64)
          # Problematic frame:
          # C [jSSC-2.7_x86_64.dll+0xb5bb]
          #
          # No core dump will be written. Minidumps are not enabled by default on client versions of Windows
          #
          # An error report file with more information is saved as:
          # C:\Users\HP\Documents\NetBeansProjects\PruebaArduino\hs_err_pid1508.log
          #
          # If you would like to submit a bug report, please visit:
          # http://bugreport.java.com/bugreport/crash.jsp
          # The crash happened outside the Java Virtual Machine in native code.
          # See problematic frame for where to report the bug.
          #
          C:\Users\HP\AppData\Local\NetBeans\Cache\11.3\executor-snippets\run.xml:111: The following error occurred while executing this line:
          C:\Users\HP\AppData\Local\NetBeans\Cache\11.3\executor-snippets\run.xml:68: Java returned: 1
          BUILD FAILED (total time: 0 seconds)

          tengo instalado Netbeans 11.3 y JDK 13.
          gracias

        • hola Jose tengo el mismo problema .cuando no esta conectado el arduino abre el Frame con los botones y cuando lo conecto sale error

          tengo instalado Netbeans 11.3 y JDK 13.
          gracias

  3. buenas tardes amigo muchas gracias por tu colaboración
    logro enviar datos desde un jframe con un botón con la clase ino.sendData(¨3¨) el arduino lo recive perfectmente con u respectivo try catch pero quisiera enviar otro dato adicional con el mismo pulso o evento pero no se puede enviar dos datos o varios a la vez usted sabrá como se puede hacer ayuda por favor

  4. muchas gracias por el contenidole agradeceria si puede ayudarme a solucionar un problema como se puede abrir el puerto com en varios jframe osea en dos ventanas diferentes me refiero a este parametro qu inicializa el puerto com ino.RXTX(«COM5»,9600,listener);
    ya e logrado hacer transmicion de envios y recepcion de datos hacia el arduino y viceversa hacia java con su libreria de evento de multi.getMensaje
    estos datos se muestran en un text field en una ventana jframe de java para guardar las variables que maneja arduino hasta ahy too bien pero luego le agrege un boton para cambiar a otra ventana y cambia bien pero una vez dentro de la siguiente ventana el puerto serie no abre para iniciar otro proceso de transmicion y rcepcion el caso esta en que quiero hacer una ventana de configuracion donde los datos sean transmitidos a arduino ejemplo velcidad del motor 1 ,velocidad del motor 2 ,numero de vueltas etc.. y la otra ventan donde se pueda iniciar el ciclo de aranque de l motor y la visualicion del incremento de un sensor contador.. la unica manera que me fuciona es con una sola ventana borrando de una de las dos ventanas el codigo ino.RXTX(«COM5»,9600,listener); y quisiera que funcionaran en las dos ventanas o mas si se puede ante todo muchs gracias

  5. Tengo un problema a la hora de mandar datos a arduino solo me acepta números entre 0 y 9, mi programa es que en una arduino manda los grados que lee y en otra los recibe y tiene que encender un ventilador pero cuando pasa de 9 ya no enciende el ventilador

  6. Buenas ,
    Como podría enviar dos mensajes desde la misma función para responder a dos peticiones del serial diferentes.
    Como por ejemplo que primero el serial me pida la velocidad de un motor y después la dirección a la que tiene que ir y se la pase ambas desde la misma función. Solo que primero le paso la velocidad del motor y después la dirección.
    Un saludo y muchas gracias.

  7. Hola Antony, tengo un problema y no sé cuál puede ser el error, estoy implementando el proyecto de graficar los datos de un sensor con JFreeChart y lo implemente con la nueva librería de PanamaHitek_Arduino. Pero cuando ejecuto el programa me dice la excepción que el puerto COM3 que es el que utiliza mi Arduino está cerrado, ya comprobé y el puerto parece estar todo bien, ¿como puedo solucionar este error?

  8. Hola, excelentes aportes.
    Llevo aproximadamente un mes intentando que me ayuden en algo pero no encuentra una respuesta.
    Quizás no me he hecho entender:

    PROBLEMA!
    Quiero realizar un programa que toma información de un arduino el cual se encuentra separada por comes y este sea guardada la información en un Jpanel para posterior a ello ser Exportada a Excel.

    Pero no ha sido posible y deseo que usted con ese Don de compartir sus conocimientos me colabore, es mi trabajo final y me interesa enormemente poder terminarlo.

    Gracias por su colaboración.

  9. Buenas tardes. Si necesito realizar algo similar, sólo que con audio (receptor de audio), es posible elaborarlo con este ejemplo? Qué habría que modificar?

  10. Hola amigo. No he logrado hacer andar el ejemplo de encender un led y he visto varios videos.
    Tengo Mac y en el puerto no sé qué poner ya que no figuran como COM. Me podrás ayudar

  11. Hola Antony. Muchas gracias por tu aporte.
    Tengo una app hecha en Java que maneja algunos casilleros con la temperatura ambiente. Y tengo un sensor hecho en arduino que mide la temperatura. Es posible que al conectar el termometro por usb, en java se coloque el valor de temperatura que esta tomando el termometro en tiempo real?
    Saludos y muchas gracias!!

    • Si eltermómetro utiliza comunicación Serial/RS-232 sí es posible. Sino, es necesario un Arduino. Por la parte de Java, sí es posible

  12. Buenas, Estoy relizando un proyecto sobre una mano que emula movimientos humanos mediante sensores puestos en nuestras manos(especificamente nuestros dedos), he logrado mediante su ejemplo de grafico en tiempo real en java con jfreecharts. mostrar el resultado para un dedo mediante el puerto A0, pero me gustaria hacer un grafico diferente para cada dedo, es decir A0,A1,A2,A3,A4 hay alguna forma de hacer esto?…desde ya gracias por su informacion me ha ayudado bastante!.

  13. Hola buenas noches tengo una duda, estoy utilizando Arduino y NetBeans, tengo que hacer una practica que desde arduino por medio de un push Botton encender una Botton en NetBeans como tengo que hacer la comunicacion para mandarla desde mi push hacia el Botton de NetBeans. Espero me puedan ayudar.
    Saludos.

  14. Tengo una duda.. porque estoy haciendo un proyecto con Arduino y NetBeans pero nose cómo hacer para que el programa NetBeans me lea la programación de Arduino. Espero su respuesta 🙂

  15. Hola Antony García González, estoy probando la libreria (muy buena por cierto), pero tengo un problema a la hora de mostrar los datos en java. me muestra los datos de forma muy desordenada y no puedo capturar el caracter bandera cuando la informacion llega a java. probando en el serial monitor no hay problema, uso el println y me deja salto de linea, cosa que no ocurre en java…. la unica forma que he usado para que me muestre los datos ordenados es usando un delay(35) y aun asi llega un momento en que se daña la tranferencia, no respeta los saltos de linea y se estropea la aplicacion….

    img sin delay

    con delay(22), mejora la cosa

    delay 35, pero en algun momento falla

    muchas gracias

    • Amigo, te invito a que posteesesta duda en nuestro foro y nos compartas el código para decirte qué puede estar saliendo mal. Saludos.

    • Amigo, te invito a que postees esta duda en nuestro foro y nos compartas el código para decirte qué puede estar saliendo mal. Saludos.

  16. Hola!!
    Estoy he desarrollado una interfaz q muestra los piertos COM disponibles en el PC, permite seleccionar uno de ellos e iniciar la conexion con Arduino. Mi pregunta es ¿Como puedo chequear q en el COM seleccionado existe un Arduino conectado?

  17. hay que verificar el código en el lado del Arduino para ver si es que por alguna razón no se está recibiendo el segundo comando

  18. buenas, por favor me podrían ayudar con un problema, he montado el circuito, en un protoboard tal cual y funciona bien, pero al montarlo en una tabletica de circuito, no sirve, ya he probado muchas veces, y diferentes personas me han ayudado a montarlo, y no funciona, la soldadura esta bien, alguna recomendacion??,, por favor

  19. buenas noches amigo me podrian ayudar con que codigo desconecto el puerto serial un ejemplo tengo conectar (arduino) y quiero un desconectar. Me podrian ayudar gracias

  20. Excelentes aportaciones, me nace una duda se que me pueden ayudar, ¿Se puede controlar diferentes pines desde java? tengo un proyecto para controlar sensor de temperatura, sensor de humedad, relay´s, pero quiero que sea desde una plataforma hecha en netbeans. como se podría hacer esto.

    Saludos desde México.

    • Sí se puede. Sólo debes programar tu Arduino para que reaccione ante las diferentes señales que le lleguen desde Java a través del Serial

Dejar respuesta

Please enter your comment!
Please enter your name here