Uso de GPIO en entradas binarias

Se pueden configurar pines de E/S de uso general (GPIO) para recibir señales eléctricas como entrada. En su nivel más básico, esto es útil en escenarios donde se detecta la apertura y el cierre de un circuito. Estos circuitos pueden incluir botones pulsadores, conmutadores de alternancia, interruptores de láminas, conmutadores de presión y otros mecanismos que representan valores binarios (es decir, activado/desactivado) y que completan un circuito.

En este tutorial, usará .NET y los pines de GPIO de su Raspberry Pi para detectar la apertura y el cierre de un circuito.

Requisitos previos

  • Equipo de placa única (SBC) basado en ARM (ARMv7 o superior)
  • Cables de puente
  • Placa de pruebas (opcional)
  • Placa adaptadora GPIO de Raspberry Pi (opcional)
  • SDK de .NET 7 o versiones posteriores.

Nota

En este tutorial, se presupone que el dispositivo de destino es Raspberry Pi. Sin embargo, se puede usar con cualquier equipo SBC basado en Linux que admita .NET, como Orange Pi, ODROID, etc.

Asegúrese de que SSH está habilitado en el dispositivo. Para Raspberry Pi, consulte Configuración de un servidor SSH en la documentación de Raspberry Pi.

Preparación del hardware

Use los componentes de hardware para crear el circuito como se muestra en el diagrama siguiente:

Diagrama donde se muestra un circuito que conecta un pin de tierra al pin 21

En la imagen anterior se muestra una conexión directa entre un pin de tierra y el pin 21.

Sugerencia

El diagrama muestra una placa de pruebas y una placa adaptadora GPIO a modo ilustrativo, pero no dude en conectar un pin de tierra y el pin 21 con un cable de puente en la Raspberry Pi si así lo desea.

Consulte el siguiente diagrama de pines según sea necesario:

Diagrama en el que se muestran los pines del encabezado GPIO de Raspberry Pi. Imagen de Raspberry Pi Foundation.
Imagen de Raspberry Pi Foundation.

Creación de la aplicación

Complete los pasos siguientes en el entorno de desarrollo que prefiera:

  1. Cree una aplicación de consola de .NET mediante la CLI de .NET o Visual Studio. Llámela InputTutorial.

    dotnet new console -o InputTutorial
    cd InputTutorial
    
  2. Agregue el paquete System.Device.Gpio al proyecto. Use la CLI de .NET desde el directorio del proyecto o Visual Studio.

    dotnet add package System.Device.Gpio --version 2.2.0-*
    
  3. Reemplace el contenido de Program.cs por el código siguiente:

    using System.Device.Gpio;
    using System.Threading.Tasks;
    
    const int Pin = 21;
    const string Alert = "ALERT 🚨";
    const string Ready = "READY ✅";
    
    using var controller = new GpioController();
    controller.OpenPin(Pin, PinMode.InputPullUp);
    
    Console.WriteLine(
        $"Initial status ({DateTime.Now}): {(controller.Read(Pin) == PinValue.High ? Alert : Ready)}");
    
    controller.RegisterCallbackForPinValueChangedEvent(
        Pin,
        PinEventTypes.Falling | PinEventTypes.Rising,
        OnPinEvent);
    
    await Task.Delay(Timeout.Infinite);
    
    static void OnPinEvent(object sender, PinValueChangedEventArgs args)
    {     
        Console.WriteLine(
            $"({DateTime.Now}) {(args.ChangeType is PinEventTypes.Rising ? Alert : Ready)}");
    }
    

    En el código anterior:

    • Una declaración using crea una instancia de GpioController. La declaración using garantiza que el objeto se deseche y que los recursos de hardware se liberen correctamente.
    • El pin 21 se abre con PinMode.InputPullUp.
      • Esto abre el pin con una resistencia PullUp acoplada. En este modo, cuando el pin está conectado a tierra, devolverá PinValue.Low. Cuando el pin no está conectado a tierra y el circuito está abierto, el pin devuelve PinValue.High.
    • El estado inicial se escribe en una consola mediante una expresión ternaria. El estado actual del pin se lee con Read(). Si es PinValue.High, escribe la cadena Alert en la consola. De lo contrario, escribe la cadena Ready.
    • RegisterCallbackForPinValueChangedEvent() registra una función de devolución de llamada para los eventos PinEventTypes.Rising y PinEventTypes.Falling en el pin. Estos eventos equivalen a los estados de pin PinValue.High y PinValue.Low respectivamente.
    • La función de devolución de llamada apunta a un método denominado OnPinEvent(). OnPinEvent() usa otra expresión ternaria que también escribe las cadenas Alert o Ready correspondientes.
    • El subproceso principal se suspende indefinidamente mientras se esperan eventos de pin.
  4. Compile la aplicación. Si usa la CLI de .NET, ejecute dotnet build. Para realizar la compilación en Visual Studio, presione Ctrl+Mayús+B.

  5. Implemente la aplicación en el equipo SBC como una aplicación independiente. Para obtener instrucciones, vea Implementación de aplicaciones .NET en Raspberry Pi. Asegúrese de conceder el permiso execute ejecutable mediante chmod +x.

  6. Para ejecutar la aplicación en Raspberry Pi, cambie al directorio de implementación y ejecute el archivo ejecutable.

    ./InputTutorial
    

    La consola muestra un texto parecido al siguiente:

    Initial status (05/10/2022 15:59:25): READY ✅
    
  7. Desconecte el pin 21 de tierra. La consola muestra un texto parecido al siguiente:

    (05/10/2022 15:59:59) ALERT 🚨
    
  8. Vuelva a conectar el pin 21 a tierra. La consola muestra un texto parecido al siguiente:

    (05/10/2022 16:00:25) READY ✅
    
  9. Presione Ctrl+C para finalizar el programa.

¡Enhorabuena! Ha usado GPIO para detectar entradas mediante el paquete NuGet System.Device.Gpio. Este tipo de entrada se puede usar de muchas formas. Este ejemplo se puede usar en cualquier escenario en el que un conmutador conecte o interrumpa un circuito. En este ejemplo de aquí se usa con un conmutador de láminas magnético, que suele emplearse para detectar puertas o ventanas abiertas.

GIF animado de un conmutador de láminas magnético abriéndose y cerrándose. Cuando el conmutador se expone a un imán, la aplicación muestra READY. Si el imán se quita, la aplicación muestra ALERT. La acción se repite.

Cable detonador láser

Por ampliar un poco más el concepto del ejemplo anterior, veamos cómo se podría aplicar esto para crear un cable detonador láser. Para crear un cable detonador láser, se necesitan los siguientes componentes adicionales:

  • Un módulo transmisor de láser KY-008
  • Un módulo sensor receptor de láser (ver la nota de abajo)
  • Dos resistencias de 10 000 Ω

Nota

Módulo sensor receptor de láser es el nombre genérico con el que hacemos referencia a un módulo común que se encuentra fácilmente en Internet. El nombre o el fabricante del dispositivo puede variar, pero debe parecerse al de esta imagen.

Imagen de un módulo sensor receptor de láser

Conexión de los componentes del cable detonador láser

Conecte los componentes como se detalla en el siguiente diagrama.

Diagrama que muestra un circuito que obtiene entradas de un módulo sensor receptor de láser

Preste mucha atención a las resistencias de 10 000 Ω. Implementan un divisor de voltaje. Esto se debe a que el módulo receptor de láser genera una salida de 5 V para indicar que el haz se ha interrumpido. Raspberry Pi solo admite entradas de GPIO de 3,3 V como máximo. Enviar la salida de 5 V completa al pin podría dañar la Raspberry Pi, de ahí que la corriente del módulo receptor pase por un divisor de voltaje, para reducir el voltaje a 2,5 V.

Aplicación de actualizaciones de código fuente

Casi podemos usar el mismo código de antes, con una excepción. En los otros ejemplos, usamos PinMode.InputPullUp para que cuando el pin no esté conectado a tierra y el circuito esté abierto, el pin devuelva PinValue.High.

Sin embargo, en el caso del módulo receptor de láser, no estamos detectando un circuito abierto, sino que queremos que el pin actúe como receptor de la corriente procedente del módulo receptor de láser. En este caso, abriremos el pin con PinMode.InputPullDown. De este modo, el pin devuelve PinValue.Low cuando no está recibiendo corriente y PinValue.High cuando reciba corriente del módulo receptor de láser.

controller.OpenPin(pin, PinMode.InputPullDown);

Importante

Asegúrese de que el código implementado en la Raspberry Pi incluye este cambio antes de probar un cable detonador láser. El programa funciona sin él, pero usar modo de entrada incorrecto podría dañar la Raspberry Pi.

GIF animado de un cable detonador láser. Cuando el emisor láser ilumina el módulo sensor láser, la aplicación muestra READY. Si el haz láser se interrumpe, la aplicación muestra ALERT. La acción se repite.

Obtención del código fuente

El código fuente de este tutorial está disponible en GitHub.

Pasos siguientes