Skip to content

Joystick Wireling Tutorial

This Wireling features a 4 position digital joystick. This board is great for user input for games or RC (Radio Controller) projects.

To learn more about the TinyDuino Platform, click here


Technical Details

This Wireling lets you use a discrete joystick for inputs to your development system of choice! This Up, Down, Left, Right joystick outputs data to an SX1505 I2C I/O expander.

To see what other TinyShields are compatible with this TinyShield, see the TinyShield Compatibility Matrix

Technical Details

SX1505 Specs

  • 8 Channel GPIO with NINT and NRESET
  • Fully programmable logic functions (PLD)

SKRHABE010 Joystick Specs

  • 4 Directional Digital Joystick
  • Center Pushbutton Input
  • I2C Semtech SX1505 I/O Expander

    TinyDuino Power Requirements

    • Voltage: 3.0V - 5.5V 
    • Current: 1.0uA (Normal Mode).  Due to the low current, this board can be run using the TinyDuino coin cell option

    Pins Used 

    • A5/SCL - I²C Clock 
    • A4/SDA - I²C Data

    Dimensions

    • 17mm x 10mm (.670 inches x .394 inches)
    • Max Height (from the lower bottom of Wireling to upper top Wireling Connector): 16mm (0.63 inches)
    • Weight: 1 gram (.04 ounces)

    Notes

    • Please note that this is not a full range analog joystick. It is essentially 4 buttons mounted sideways at the base of the joystick knob.

    Materials

    Wireling Processor, Joystick Wireling, and 5-Pin Wireling Connector

    Hardware

    Software


    Hardware Assembly

    Plug the 5-Pin Wireling Connector into the desired Wireling Port and Joystick Wireling.

    Hardware Assembled


    Software Setup

    For this tutorial, you'll need the TinyJoystick Arduino Library to read joystick data from the Wireling. If you need a reminder for how to download a library, please refer to the Installing Libraries tutorial.


    Upload Program

    If you would like to use a different port on the Wireling Adapter board of your choice, simply change the value of JS_PORT in the code and plug the Wireling into the corresponding port (0-3).

    If using the Serial Monitor instead of a 0.42" OLED Wireling to view output, set USE_OLED to false. The code is currently setup to have the screen on Port 3.

    A Rotary Switch Wireling can also be tested with this code by plugging it into Port 0.

    Code
    /*
      TinyCircuits Rotary Switch/Joystick Wireling Example Sketch
    
      This sketch will output the integer value selected on the
      Rotary Switch Wireling along with the directional input
      from the Joystick Wireling.
    
      Written 15 July 2019
      By Hunter Hykes
      Modified 01/02/2020
      By Hunter Hykes
    
      https://TinyCircuits.com
    */
    
    #include <Wire.h>
    #include <Wireling.h>
    #include <TinierScreen.h>       // For interfacing with the 0.42" OLED
    #include <TinyBuffer.h>         // For building a screen buffer for the 0.42" OLED
    #include "font.h"
    #include "WirelingInputs.h"     // For interfacing with Joystick and Rotary Switch Wirelings
    
    // Universal Serial Monitor Config
    #if defined (ARDUINO_ARCH_AVR)
    #define SerialMonitorInterface Serial
    #elif defined(ARDUINO_ARCH_SAMD)
    #define SerialMonitorInterface SerialUSB
    #endif
    
    #define USE_OLED true // set true if using 0.42" OLED to echo input, false if using Serial Monitor
    
    /* * * * * * * * * * Rotary * * * * * * * * * */
    #define ROT_PORT 0 // port 0 on wireling board
    TinyRotary rotary = TinyRotary(); // create new TinyRotary object
    uint8_t rotaryValue;
    
    /* * * * * * * * * * Joystick * * * * * * * * * */
    #define JS_PORT 1 // port 1 on wireling board
    TinyJoystick joystick = TinyJoystick(); // create new TinyJoystick object
    
    /* * * * * * * * * * 0.42" OLED * * * * * * * * * */
    #define OLED_PORT 3 // use Port 0 for screen
    #define OLED_RST (uint8_t) A3 //OLED reset line
    TinierScreen display042 = TinierScreen(OLED042);
    TinyBuffer screenBuffer042 = TinyBuffer(72, 40, colorDepth1BPP);
    
    void setup() {
      Wire.begin();
      Wireling.begin();
    
      /* * * * * * Screen Stuff * * * * */
      pinMode(OLED_RST, OUTPUT);
      screenBuffer042.clear();
      digitalWrite(OLED_RST, LOW);
      delay(1);
      digitalWrite(OLED_RST, HIGH);
      Wireling.selectPort(OLED_PORT);
      display042.begin();
      Wire.setClock(1000000);
      screenBuffer042.setFont(thinPixel7_10ptFontInfo);
    
      /* * * * * * Rotary Stuff * * * * */
      Wireling.selectPort(ROT_PORT); // select the Rotary Switch Wireling port
      rotary.begin(); // begin communications with rotary switch I/O expander
      rotary.init(); // initialize I/O expander
    
      /* * * * * * Joystick Stuff * * * * */
      Wireling.selectPort(JS_PORT); // select the Rotary Switch Wireling port
      joystick.begin(); // begin communications with rotary switch I/O expander
      joystick.init(); // initialize I/O expander
    
      SerialMonitorInterface.begin(9600);
      delay(500);
    }
    
    void loop() {
      // get rotary switch data
      Wireling.selectPort(ROT_PORT);
      rotaryValue = rotary.getPosition();
    
      // get joystick data
      Wireling.selectPort(JS_PORT);
      joystick.getPosition();
    
      if(USE_OLED) {
        // write the screen buffer
        Wireling.selectPort(OLED_PORT); // select the Wireling screen port
        screenBuffer042.clear();        // clear old screen contents
        writeNum();                     // add rotary switch number to buffer
        writePos();                     // add joystick direction to buffer
        display042.writeBuffer(screenBuffer042.getBuffer(), screenBuffer042.getBufferSize()); // write buffer to the screen
      } else {
        writeToMonitor();
      }
    }
    
    int x, y;
    void writeNum() {
      screenBuffer042.setCursor(x = 10, y = 10);
      screenBuffer042.print(String(rotaryValue));
    }
    
    void writePos() {
      if(joystick.up) {
        screenBuffer042.setCursor(x = 10, y = 0);
        screenBuffer042.print("^");
      }
      if(joystick.down) {
        screenBuffer042.setCursor(x = 10, y = 20);
        screenBuffer042.print("v");
      }
      if(joystick.left) {
        screenBuffer042.setCursor(x = 0, y = 10);
        screenBuffer042.print("<");
      }
      if(joystick.right) {
        screenBuffer042.setCursor(x = 20, y = 10);
        screenBuffer042.print(">");
      }
    }
    
    void writeToMonitor() {
      SerialMonitorInterface.print("Rotary: " + String(rotaryValue) + "\t");
    
      if(joystick.up) {
        SerialMonitorInterface.print("UP\t");
      }
      if(joystick.down) {
        SerialMonitorInterface.print("DOWN\t");
      }
      if(joystick.left) {
        SerialMonitorInterface.print("LEFT\t");
      }
      if(joystick.right) {
        SerialMonitorInterface.print("RIGHT\t");
      }
      SerialMonitorInterface.println();
      delay(100);
    }
    
    

    After uploading, either look to the Serial Monitor or 0.42" OLED Screen Wireling for feedback as you move the joystick. The "up" direction is registered when the joystick is pushed towards the Wireling cable.


    Projects

    • It is possible to create multiplayer games with two Joystick Wireling boards! However, it is important to acquire timestamps via the appropriate interrupt pins from each Wireling to make sure inputs are interpreted in the order they are received.

    Contact Us

    If you have any questions or feedback, feel free to email us at info@tinycircuits.com or make a post on the forum.

    Show us what you make by tagging @TinyCircuits on Instagram, Twitter, or Facebook so we can feature it!

    Thanks for making with us!


    Downloads