Jump to content

Code sketchbook repository /Arduino uno/mega boards DCS BIOS and programming help/Please post your working sketches here!


protea1

Recommended Posts

this is what i use with arduino leonardo

#include <Joystick.h>

void setup() {
  // Initialize Button Pins
  pinMode(0, INPUT_PULLUP);
  pinMode(1, INPUT_PULLUP);
  pinMode(2, INPUT_PULLUP);
  pinMode(3, INPUT_PULLUP);
  pinMode(4, INPUT_PULLUP);
  pinMode(5, INPUT_PULLUP);
  pinMode(6, INPUT_PULLUP);
  pinMode(7, INPUT_PULLUP);
  pinMode(8, INPUT_PULLUP);
  pinMode(9, INPUT_PULLUP);
  pinMode(10, INPUT_PULLUP);
  
  // Initialize Joystick Library
  Joystick.begin();
}

// Costante che mappa il pin fisico sul pulsante del joystick.
const int pinToButtonMap = 0;

// Ultimo stato del pulsante
int lastButtonState[10] = {0,0,0,0};

void loop() {

  // Read pin values
  for (int index = 0; index < 6; index++)
  {
    int currentButtonState = !digitalRead(index + pinToButtonMap);
    if (currentButtonState != lastButtonState[index])
    {
      Joystick.setButton(index, currentButtonState);
      lastButtonState[index] = currentButtonState;
    }
  }

  delay(50);
}

  • Like 1
Link to comment
Share on other sites

  • 2 weeks later...

Some of the more esoteric OLED display boards can require particular coding to work that is similar to but not quite the same as the standard SSD1306 versions

This is for a 1.3 inch SH1106 128 x 64 I2C OLED (in this case for the TACAN), please note that the input pin order is different to the usual in that the VCC and GND pins are transposed

#define DCSBIOS_DEFAULT_SERIAL
//#define DCSBIOS_IRQ_SERIAL

//#define DCSBIOS_RS485_SLAVE 51
//#define TXENABLE_PIN 2

#include <SPI.h>
#include <Wire.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SH1106.h>
#include "Fonts/FreeSans24pt7b.h"

#define OLED_RESET 4
Adafruit_SH1106 display(OLED_RESET);


#include <DcsBios.h>

DcsBios::LED tacanTest(0x10da, 0x0400, 11);
DcsBios::ActionButton tacanTestBtnToggle("TACAN_TEST_BTN", "TOGGLE", 12);

DcsBios::RotaryEncoder tacan1("TACAN_1", "DEC", "INC", 3, 4);
DcsBios::RotaryEncoder tacan10("TACAN_10", "DEC", "INC", 5, 6); 
DcsBios::RotaryEncoder tacanXy("TACAN_XY", "DEC", "INC", 7, 8);
DcsBios::RotaryEncoder tacanVol("TACAN_VOL", "-3200", "+3200", 9, 10);

void setup()

{
display.begin(SH1106_SWITCHCAPVCC, 0x3C);  // initialize with the I2C addr 0x3D (for the 128x64)
delay(1000);
  display.clearDisplay();   // clears the screen and buffer
  display.setFont(&FreeSans24pt7b);
  
 DcsBios::setup();
}

void loop()
{
  DcsBios::loop();
  
}

  void onTacanChannelChange(char* newValue) {
  display.setRotation(2);   // Sets the rotation of the screen, set to 0 for normal
  display.fillRect(0, 0, 100, 50, BLACK);  // Draws a blank rectangle to clear the previous text
  display.setTextColor(WHITE, BLACK);
  display.setCursor(8, 40);
  display.print(newValue);
  display.display();
}
DcsBios::StringBuffer<4> tacanChannelBuffer(0x1162, onTacanChannelChange);

 

This one is for an SSD1305 128 x 32 OLED (in this case used for the ILS display) note that it is a seven pin connection type and you will have to make sure you adjust the CLK, MOSI, CS, DS and RESET pins accordingly, and also unlike some OLED displays I found that the RESET pin does have to be connected

 


#define DCSBIOS_IRQ_SERIAL

//#define DCSBIOS_RS485_SLAVE 75
//#define TXENABLE_PIN 2


#include <DcsBios.h>
#include <Wire.h>
#include <SPI.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SSD1305.h>
#include "Fonts/FreeSans18pt7b.h"

// Used for software SPI
#define OLED_CLK 13
#define OLED_MOSI 11

// Used for software or hardware SPI
#define OLED_CS 8
#define OLED_DC 9

// Used for I2C or SPI
#define OLED_RESET 10


Adafruit_SSD1305 display(128, 32, &SPI, OLED_DC, OLED_RESET, OLED_CS, 6000000UL);




void setup()   {                
   {

  display.begin(0x3C); 

  delay(1000);
  display.clearDisplay();   // clears the screen and buffer
  display.setFont(&FreeSans18pt7b);
  
}
DcsBios::setup();
}


DcsBios::RotaryEncoder ilsVol("ILS_VOL", "-3200", "+3200", 16, 17);

DcsBios::RotaryEncoder ilsKhz("ILS_KHZ", "DEC", "INC", 18, 19);

DcsBios::RotaryEncoder ilsMhz("ILS_MHZ", "DEC", "INC", 15, 14);

void loop() {
  DcsBios::loop();

  display.display();
  display.setTextColor(WHITE, BLACK);  // Draws a blank rectangle to clear the previous text
  display.setCursor(66, 27);
  display.print(".");
  display.display();
}

 void onIlsMhzChange(char* newValue) {
  display.fillRect(0, 0, 65, 32, BLACK);  // Draws a blank rectangle to clear the previous text
  display.setTextColor(WHITE, BLACK);
  display.setCursor(8, 27);
  display.print(newValue);
  display.display();
 
}
DcsBios::StringBuffer<3> ilsMhzStrBuffer(0x116e, onIlsMhzChange);

void onIlsKhzChange(char* newValue) {
  display.fillRect(75, 0, 50, 32, BLACK);
  display.setTextColor(WHITE, BLACK);
  display.setCursor(75, 27);
  display.print(newValue);
  display.display();
  
}

DcsBios::StringBuffer<2> ilsKhzStrBuffer(0x1172, onIlsKhzChange);

Hope this helps

Les


Edited by lesthegrngo
extra comments
  • Thanks 1
Link to comment
Share on other sites

  • 2 months later...

Let's carry on with the 16 bit port expansion to an Arduino Nano example.

To keep it simple we just use waveshare's MCP23017 ->board<- and ->library<- to extend the pins of a Nano to match the physical switches (not rotaries) requirements of the A-10 VHF FM radio.

I used the waveshare library because it is fast reacting and smaller than the Adafuit MCP23x17 library.

Here the Frequency Selection Dial (4 pins), Mode switch (3 pins), Squelch switch (2 pins), Load button (1 pin) and a simple rocker switch for the Preset Channel Selector (2 pins) are connected to 12 of the 16 expander inputs. The MCP23017 is connected via A4 and A5 to the I2C bus (just two Nano pins plus electrical power), that means you still have plenty pins left to connect the remaining rotaries and potentiometer as well as displays for the frequency output and other devices.

I wired all switches the typically DcsBios style active low, so a single switch also may be used directly connected for test purposes.

 

First the declaration of DcsBios, I2C-bus ("wire") and the MCP23017 object has to be done within the code.

#define DCSBIOS_IRQ_SERIAL
// #define DCSBIOS_DEFAULT_SERIAL  // for use with no Arduino Chips
#include "DcsBios.h"
#include <Wire.h>

// ----- 16 bit port expander connected @ IC2 address 0x27
#include "MCP23017.h"
MCP23017 mcp;
// Connect pin SCL of the expander to NANO/UNO pin A5
// Connect pin SDA of the expander to NANO/UNO pin A4
// MCP23017 connections
// Physial Pin# PinName PinID
//    21   GPA0    0
//    22   GPA1    1
//    23   GPA2    2
//    24   GPA3    3
//    25   GPA4    4
//    26   GPA5    5
//    27   GPA6    6
//    28   GPA7    7
//    1    GPB0    8
//    2    GPB1    9
//    3    GPB2    10
//    4    GPB3    11
//    5    GPB4    12
//    6    GPB5    13
//    7    GPB6    14
//    8    GPB7    15

 

Than a few variables may be declared, like debouncing time and the actual and previous switch status for further use.

// ----- declaration of variables
const byte debounce = 35; // debounce time (value to be multiplied by 10 to make an integer)
byte VHFFM_FREQEMER = 0;
byte prev_VHFFM_FREQEMER = 0;
byte VHFFM_MODE = 0;
byte prev_VHFFM_MODE = 0;
byte VHFFM_PRESET = 0;
byte prev_VHFFM_PRESET = 0;
byte VHFFM_SQUELCH = 1;
byte prev_VHFFM_SQUELCH = 1;
byte VHFFM_LOAD = 0;
byte prev_VHFFM_LOAD = 0;

 

Within the SETUP section the modes and pullups for each input have to be identified. We don't need all of the 16 expansions in this case.

// ---------- SETUP Loop ----------
void setup() {
    DcsBios::setup();
	
  // ----- initialize the 16 bit port expander
    mcp.begin(0x27);
    
    mcp.pinMode(0, INPUT);
    mcp.pullUp(0, HIGH);  
    mcp.pinMode(1, INPUT);
    mcp.pullUp(1, HIGH);  
    mcp.pinMode(2, INPUT);
    mcp.pullUp(2, HIGH);  
    mcp.pinMode(3, INPUT);
    mcp.pullUp(3, HIGH);
    mcp.pinMode(4, INPUT);
    mcp.pullUp(4, HIGH);  
    mcp.pinMode(5, INPUT);
    mcp.pullUp(5, HIGH);  
    mcp.pinMode(6, INPUT);
    mcp.pullUp(6, HIGH);  
    mcp.pinMode(7, INPUT);
    mcp.pullUp(7, HIGH);
    mcp.pinMode(8, INPUT);
    mcp.pullUp(8, HIGH);  
    mcp.pinMode(9, INPUT);
    mcp.pullUp(9, HIGH);  
    mcp.pinMode(10, INPUT);
    mcp.pullUp(10, HIGH);  
    mcp.pinMode(11, INPUT);
    mcp.pullUp(11, HIGH);     
// ... continue to pin 15 if necessary

}
// ---------- End of SETUP Loop ----------

 

Now we need to read the expander inputs and send the corresponding switch status to DcsBios.

Expander ports are read the typically Arduino code style: [mcp.digitalRead(expander port) == 0] if a switch is activated.

Btw. each status information may be placed into a variable related to the input device (switch).

I have grouped that into a compact function -> void send_mcpReadings()

// ----- read the physical VHF FM radio switch positions from cockpit, save status into variables and send to DcsBios
void send_mcpReadings()  {
  //  Frequency Selection Dial FM/AM/MAN/PRE
  if (mcp.digitalRead(0) == 0) {VHFFM_FREQEMER = 0; DcsBios::tryToSendDcsBiosMessage("VHFFM_FREQEMER", "0");}  // Emergency FM
  if (mcp.digitalRead(1) == 0) {VHFFM_FREQEMER = 1; DcsBios::tryToSendDcsBiosMessage("VHFFM_FREQEMER", "1");}  // Emergency AM
  if (mcp.digitalRead(2) == 0) {VHFFM_FREQEMER = 2; DcsBios::tryToSendDcsBiosMessage("VHFFM_FREQEMER", "2");}  // Manual mode
  if (mcp.digitalRead(3) == 0) {VHFFM_FREQEMER = 3; DcsBios::tryToSendDcsBiosMessage("VHFFM_FREQEMER", "3");}  // preselected channel mode
  //  Mode OFF/TR/DF
  if (mcp.digitalRead(4) == 0) {VHFFM_MODE = 0; DcsBios::tryToSendDcsBiosMessage("VHFFM_MODE", "0");}  // OFF - disables the radio
  if (mcp.digitalRead(5) == 0) {VHFFM_MODE = 1; DcsBios::tryToSendDcsBiosMessage("VHFFM_MODE", "1");}  // TR - Transmit and Recieve mode
  if (mcp.digitalRead(6) == 0) {VHFFM_MODE = 2; DcsBios::tryToSendDcsBiosMessage("VHFFM_MODE", "2");}  // DF - Direction finding mode for the ADI and HSI
  //  Preset Channel Selector
  if (mcp.digitalRead(7) == 0) {VHFFM_PRESET = 0; DcsBios::tryToSendDcsBiosMessage("VHFFM_PRESET", "DEC");}  // decrease channel selection
  if (mcp.digitalRead(8) == 0) {VHFFM_PRESET = 1; DcsBios::tryToSendDcsBiosMessage("VHFFM_PRESET", "INC");}  // increase channel selection
  //  Squelch
  if (mcp.digitalRead(9) == 0) {VHFFM_SQUELCH = 0; DcsBios::tryToSendDcsBiosMessage("VHFFM_SQUELCH", "0");} // Squelch disabled
  if ((mcp.digitalRead(9) == 1) && (mcp.digitalRead(10) == 1)) {VHFFM_SQUELCH = 1; DcsBios::tryToSendDcsBiosMessage("VHFFM_SQUELCH", "1");} // if no push botton is pressed
  // momentary and therefore, may be commented out for regularily sending
  if (mcp.digitalRead(10) == 0) {VHFFM_SQUELCH = 2; DcsBios::tryToSendDcsBiosMessage("VHFFM_SQUELCH", "2");}  // Squelch tone mode
  if (mcp.digitalRead(11) == 0) {VHFFM_LOAD = 1; DcsBios::tryToSendDcsBiosMessage("VHFFM_LOAD", "1");}  // Load Button pressed  
  if ((mcp.digitalRead(11) == 1) && (VHFFM_LOAD == 1)) {VHFFM_LOAD = 0; DcsBios::tryToSendDcsBiosMessage("VHFFM_LOAD", "0");}  // reset Load Button 
}

 

You also may skip to set status variables and send data directly to DcsBios by using code like below

  //  Frequency Selection Dial FM/AM/MAN/PRE
  if (mcp.digitalRead(0) == 0) DcsBios::tryToSendDcsBiosMessage("VHFFM_FREQEMER", "0");  // Emergency FM
  if (mcp.digitalRead(1) == 0) DcsBios::tryToSendDcsBiosMessage("VHFFM_FREQEMER", "1");  // Emergency AM
  if (mcp.digitalRead(2) == 0) DcsBios::tryToSendDcsBiosMessage("VHFFM_FREQEMER", "2");  // Manual mode
  if (mcp.digitalRead(3) == 0) DcsBios::tryToSendDcsBiosMessage("VHFFM_FREQEMER", "3");  // preselected channel mode

 

At last the readings continuously can be pulled and than send to DcsBios within the execution loop.

// ---------- EXECUTION loop ----------
void loop() { 
 DcsBios::loop();
 send_mcpReadings();
}

 

To do it more elegant, the information may be send non blocking and periodically to DcsBios. That way the traffic on the connected bus may be decreased.

We first have to declare two more variables within the code:

// ----- declaration of variables
...
  const byte period = 10;  // refresh and send switch positions regularily in seconds (value to be multiplied by 1000 to make an integer)
  long lastChangeTime = 0;

 

and than enhance the loop section so, that the information is send only e.g. every 10 seconds (to be changed with the variable "period").

// ---------- EXECUTION loop ----------
void loop() { 
 DcsBios::loop();
 
 // send switch positions regularily (non blocking)
 long now = millis();
 if (now > lastChangeTime + (period*1000))
  {
   send_mcpReadings();
   lastChangeTime = now;
  }
}

 

A further way is to read the expander inputs and send the corresponding switch status to the simulator only if a switch position has changed.

To keep the overview, again functional grouping is used -> void send_onChange()

// ----- read Inputs from MCP23017 and send switch positions only on change
void send_onChange()
{
//  Frequency Selection Dial FM/AM/MAN/PRE -> SwitchMultiPos at expander pins GPA0 (0) to GPA3 (3)
  if (mcp.digitalRead(0) == 0)
    {
    VHFFM_FREQEMER = 0;
      if (prev_VHFFM_FREQEMER != 0)
        {
            DcsBios::tryToSendDcsBiosMessage("VHFFM_FREQEMER", "0");		// "tryToSendDcsBiosMessage" or "sendDcsBiosMessage"
            prev_VHFFM_FREQEMER = VHFFM_FREQEMER;
        }
    }
  
  if (mcp.digitalRead(1) == 0)
    {
    VHFFM_FREQEMER = 1;
      if (prev_VHFFM_FREQEMER != 1)
        {
            DcsBios::tryToSendDcsBiosMessage("VHFFM_FREQEMER", "1");
            prev_VHFFM_FREQEMER = VHFFM_FREQEMER;
        }
    }
  
  if (mcp.digitalRead(2) == 0)
    {
    VHFFM_FREQEMER = 2;
      if (prev_VHFFM_FREQEMER != 2)
        {
            DcsBios::tryToSendDcsBiosMessage("VHFFM_FREQEMER", "2");
            prev_VHFFM_FREQEMER = VHFFM_FREQEMER;
        }
    }

  if (mcp.digitalRead(3) == 0)
    {
    VHFFM_FREQEMER = 3;
      if (prev_VHFFM_FREQEMER != 3)
        {
            DcsBios::tryToSendDcsBiosMessage("VHFFM_FREQEMER", "3");
            prev_VHFFM_FREQEMER = VHFFM_FREQEMER;
        }
    }

//  Mode OFF/TR/DF -> SwitchMultiPos at expander pins GPA4 (4) to GPA6 (6)
  if (mcp.digitalRead(4) == 0)
    {
    VHFFM_MODE = 0;
      if (prev_VHFFM_MODE != 0)
        {
            DcsBios::tryToSendDcsBiosMessage("VHFFM_MODE", "0");
            prev_VHFFM_MODE = VHFFM_MODE;
        }
    }
  if (mcp.digitalRead(5) == 0)
    {
    VHFFM_MODE = 1;
      if (prev_VHFFM_MODE != 1)
        {
            DcsBios::tryToSendDcsBiosMessage("VHFFM_MODE", "1");
            prev_VHFFM_MODE = VHFFM_MODE;
        }
    }
  if (mcp.digitalRead(6) == 0)
    {
    VHFFM_MODE = 2;
      if (prev_VHFFM_MODE != 2)
        {
            DcsBios::tryToSendDcsBiosMessage("VHFFM_MODE", "2");
            prev_VHFFM_MODE = VHFFM_MODE;
        }
    }
//  Preset Channel Selector -> two push buttons workaround for a rocker switch at expander pins GPA7 (7) and GPB0 (8)
  if (mcp.digitalRead(7) == 0)
    {
    VHFFM_PRESET = 1;
      if (prev_VHFFM_PRESET != 1)
        {
          DcsBios::tryToSendDcsBiosMessage("VHFFM_PRESET", "DEC");
          delay(debounce*10);
          prev_VHFFM_PRESET = 0;  // reset to accept next button signal
        }
    }
  if (mcp.digitalRead(8) == 0)
    {
    VHFFM_PRESET = 2;
      if (prev_VHFFM_PRESET != 2)
        {
            DcsBios::tryToSendDcsBiosMessage("VHFFM_PRESET", "INC");
            delay(debounce*10);
            prev_VHFFM_PRESET = 0;  // reset to accept next button signal
        }
    }
//  Squelch -> Switch3Pos at expander pins GPB1 (9) and GPB2 (10)
  if ((mcp.digitalRead(9) == 1) && (mcp.digitalRead(10) == 1))  // workaround to active send from the middle position of a 3 pos toggle switch
    {
    VHFFM_SQUELCH = 1;
      if (prev_VHFFM_SQUELCH != 1)
        {
            DcsBios::tryToSendDcsBiosMessage("VHFFM_SQUELCH", "1");
            prev_VHFFM_SQUELCH = VHFFM_SQUELCH;
        }
    }
       
  if (mcp.digitalRead(9) == 0)
    {
    VHFFM_SQUELCH = 0;
      if (prev_VHFFM_SQUELCH != 0)
        {
            DcsBios::tryToSendDcsBiosMessage("VHFFM_SQUELCH", "0");
            prev_VHFFM_SQUELCH = VHFFM_SQUELCH;
        }
    }
    
  if (mcp.digitalRead(10) == 0)
    {
    VHFFM_SQUELCH = 2;
      if (prev_VHFFM_SQUELCH != 2)
        {
            DcsBios::tryToSendDcsBiosMessage("VHFFM_SQUELCH", "2");
            prev_VHFFM_SQUELCH = VHFFM_SQUELCH;
        }
    }  

//  Load Button -> simple push button at expander pin GPB3 (11)
  if (mcp.digitalRead(11) == 0)
    {
    VHFFM_LOAD = 1;
      if (prev_VHFFM_LOAD != 1)
        {
          DcsBios::tryToSendDcsBiosMessage("VHFFM_LOAD", "1");
          delay(debounce*10);
          prev_VHFFM_LOAD = 0;  // push Load Button
        }
    }

  if ((mcp.digitalRead(11) == 1) && (VHFFM_LOAD == 1))  // release button and reset the variable
    {
      delay(debounce*10);
      DcsBios::tryToSendDcsBiosMessage("VHFFM_LOAD", "0");
      VHFFM_LOAD = 0;
      prev_VHFFM_LOAD = 0;
    }
}

 

In the end both functions may be used within the same loop to send the readings periodically and on switch input changes.

// ---------- EXECUTION loop ----------
void loop() { 
 DcsBios::loop();
 
 // possibility 1: send switch positions regularily (non blocking)
 long now = millis();
 if (now > lastChangeTime + (period*1000))
  {
   send_mcpReadings();
   lastChangeTime = now;
 }
 
 // possibility 2: continously read the port expander and send switch positions only on change
 send_onChange();
}
// ---------- End of EXECUTION loop ----------

 

Btw. the switch positions still may be read out from the simulator, for example that of the Mode switch.

// ---------- DCS content here below ----------

// example to read the switch feedback from DcsBios, here: status change of the Mode OFF/TR/DF switch (OFF = 0/TR = 1/DF =2)
void onVhffmModeChange(unsigned int newValue) {
    // your code here
}
DcsBios::IntegerBuffer vhffmModeBuffer(0x1194, 0x0060, 5, onVhffmModeChange);

 

Below is the final sketch to read all switches from the VHF FM radio panel and send their status information regularly and on change to DcsBios.

Spoiler
// ---------- Chip declaration here ----------  
#define DCSBIOS_IRQ_SERIAL
// #define DCSBIOS_DEFAULT_SERIAL  // for use with no Arduino Chips
#include "DcsBios.h"
#include <Wire.h>

// ----- 16 bit port expander connected @ IC2 address 0x27
#include "MCP23017.h"
MCP23017 mcp;
// Connect pin SCL of the expander to NANO/UNO pin A5
// Connect pin SDA of the expander to NANO/UNO pin A4
// MCP23017 connections
// Physial Pin# PinName PinID
//    21   GPA0    0
//    22   GPA1    1
//    23   GPA2    2
//    24   GPA3    3
//    25   GPA4    4
//    26   GPA5    5
//    27   GPA6    6
//    28   GPA7    7
//    1    GPB0    8
//    2    GPB1    9
//    3    GPB2    10
//    4    GPB3    11
//    5    GPB4    12
//    6    GPB5    13
//    7    GPB6    14
//    8    GPB7    15

// ----- declaration of variables
const byte debounce = 35; // debounce time (value to be multiplied by 10 to make an integer)
byte VHFFM_FREQEMER = 0;
byte prev_VHFFM_FREQEMER = 0;
byte VHFFM_MODE = 0;
byte prev_VHFFM_MODE = 0;
byte VHFFM_PRESET = 0;
byte prev_VHFFM_PRESET = 0;
byte VHFFM_SQUELCH = 1;
byte prev_VHFFM_SQUELCH = 1;
byte VHFFM_LOAD = 0;
byte prev_VHFFM_LOAD = 0;
long lastChangeTime = 0;
const byte period = 10;  // refresh and send switch positions regularily in seconds (value to be multiplied by 1000 to make an integer)
byte VhffmMode = 1;


// ---------- DCS content here below ----------

// example to read the switch feedback from DcsBios
// here: status change of the Mode OFF/TR/DF switch (OFF = 0/TR = 1/DF =2)
void onVhffmModeChange(unsigned int newValue) {
    VhffmMode = newValue;
}
DcsBios::IntegerBuffer vhffmModeBuffer(0x1194, 0x0060, 5, onVhffmModeChange);

// ---------- SETUP Loop ----------
void setup() {
    DcsBios::setup();
	
  // ----- initialize the 16 bit port expander
    mcp.begin(0x27);
    
    mcp.pinMode(0, INPUT);
    mcp.pullUp(0, HIGH);  
    mcp.pinMode(1, INPUT);
    mcp.pullUp(1, HIGH);  
    mcp.pinMode(2, INPUT);
    mcp.pullUp(2, HIGH);  
    mcp.pinMode(3, INPUT);
    mcp.pullUp(3, HIGH);
    mcp.pinMode(4, INPUT);
    mcp.pullUp(4, HIGH);  
    mcp.pinMode(5, INPUT);
    mcp.pullUp(5, HIGH);  
    mcp.pinMode(6, INPUT);
    mcp.pullUp(6, HIGH);  
    mcp.pinMode(7, INPUT);
    mcp.pullUp(7, HIGH);
    mcp.pinMode(8, INPUT);
    mcp.pullUp(8, HIGH);  
    mcp.pinMode(9, INPUT);
    mcp.pullUp(9, HIGH);  
    mcp.pinMode(10, INPUT);
    mcp.pullUp(10, HIGH);  
    mcp.pinMode(11, INPUT);
    mcp.pullUp(11, HIGH);     
// ... continue to pin 15 if necessary

}
// ---------- End of SETUP Loop ----------

// ---------- EXECUTION loop ----------
void loop() { 
 DcsBios::loop();
 
 // possibility 1: send switch positions regularily (non blocking)
 long now = millis();
 if (now > lastChangeTime + (period*1000))
  {
   send_mcpReadings();
   lastChangeTime = now;
 }
 
 // possibility 2: continously read the port expander and send switch positions only on change
 send_onChange();
}
// ---------- End of EXECUTION loop ----------

// ---------- Declaration of Functions ----------


// ----- read the physical VHF FM radio switch positions from cockpit, save status into variables and send to DcsBios
void send_mcpReadings()  {
  //  Frequency Selection Dial FM/AM/MAN/PRE
  if (mcp.digitalRead(0) == 0) {VHFFM_FREQEMER = 0; DcsBios::tryToSendDcsBiosMessage("VHFFM_FREQEMER", "0");}  // Emergency FM
  if (mcp.digitalRead(1) == 0) {VHFFM_FREQEMER = 1; DcsBios::tryToSendDcsBiosMessage("VHFFM_FREQEMER", "1");}  // Emergency AM
  if (mcp.digitalRead(2) == 0) {VHFFM_FREQEMER = 2; DcsBios::tryToSendDcsBiosMessage("VHFFM_FREQEMER", "2");}  // Manual mode
  if (mcp.digitalRead(3) == 0) {VHFFM_FREQEMER = 3; DcsBios::tryToSendDcsBiosMessage("VHFFM_FREQEMER", "3");}  // preselected channel mode
  //  Mode OFF/TR/DF
  if (mcp.digitalRead(4) == 0) {VHFFM_MODE = 0; DcsBios::tryToSendDcsBiosMessage("VHFFM_MODE", "0");}  // OFF - disables the radio
  if (mcp.digitalRead(5) == 0) {VHFFM_MODE = 1; DcsBios::tryToSendDcsBiosMessage("VHFFM_MODE", "1");}  // TR - Transmit and Recieve mode
  if (mcp.digitalRead(6) == 0) {VHFFM_MODE = 2; DcsBios::tryToSendDcsBiosMessage("VHFFM_MODE", "2");}  // DF - Direction finding mode for the ADI and HSI
  //  Preset Channel Selector
  if (mcp.digitalRead(7) == 0) {VHFFM_PRESET = 0; DcsBios::tryToSendDcsBiosMessage("VHFFM_PRESET", "DEC");}  // decrease channel selection
  if (mcp.digitalRead(8) == 0) {VHFFM_PRESET = 1; DcsBios::tryToSendDcsBiosMessage("VHFFM_PRESET", "INC");}  // increase channel selection
  //  Squelch
  if (mcp.digitalRead(9) == 0) {VHFFM_SQUELCH = 0; DcsBios::tryToSendDcsBiosMessage("VHFFM_SQUELCH", "0");} // Squelch disabled
  if ((mcp.digitalRead(9) == 1) && (mcp.digitalRead(10) == 1)) {VHFFM_SQUELCH = 1; DcsBios::tryToSendDcsBiosMessage("VHFFM_SQUELCH", "1");} // if no push botton is pressed
  // momentary and therefore, may be commented out for regularily sending
  /*
  if (mcp.digitalRead(10) == 0) {VHFFM_SQUELCH = 2; DcsBios::tryToSendDcsBiosMessage("VHFFM_SQUELCH", "2");}  // Squelch tone mode
  if (mcp.digitalRead(11) == 0) {VHFFM_LOAD = 1; DcsBios::tryToSendDcsBiosMessage("VHFFM_LOAD", "1");}  // Load Button pressed  
  if ((mcp.digitalRead(11) == 1) && (VHFFM_LOAD == 1)) {VHFFM_LOAD = 0; DcsBios::tryToSendDcsBiosMessage("VHFFM_LOAD", "0");}  // reset Load Button 
  */
}

// ----- read Inputs from MCP23017 and send switch positions only on change
void send_onChange()
{
//  Frequency Selection Dial FM/AM/MAN/PRE -> SwitchMultiPos at expander pins GPA0 (0) to GPA3 (3)
  if (mcp.digitalRead(0) == 0)
    {
    VHFFM_FREQEMER = 0;
      if (prev_VHFFM_FREQEMER != 0)
        {
            DcsBios::tryToSendDcsBiosMessage("VHFFM_FREQEMER", "0");		// "tryToSendDcsBiosMessage" or "sendDcsBiosMessage"
            prev_VHFFM_FREQEMER = VHFFM_FREQEMER;
        }
    }
  
  if (mcp.digitalRead(1) == 0)
    {
    VHFFM_FREQEMER = 1;
      if (prev_VHFFM_FREQEMER != 1)
        {
            DcsBios::tryToSendDcsBiosMessage("VHFFM_FREQEMER", "1");
            prev_VHFFM_FREQEMER = VHFFM_FREQEMER;
        }
    }
  
  if (mcp.digitalRead(2) == 0)
    {
    VHFFM_FREQEMER = 2;
      if (prev_VHFFM_FREQEMER != 2)
        {
            DcsBios::tryToSendDcsBiosMessage("VHFFM_FREQEMER", "2");
            prev_VHFFM_FREQEMER = VHFFM_FREQEMER;
        }
    }

  if (mcp.digitalRead(3) == 0)
    {
    VHFFM_FREQEMER = 3;
      if (prev_VHFFM_FREQEMER != 3)
        {
            DcsBios::tryToSendDcsBiosMessage("VHFFM_FREQEMER", "3");
            prev_VHFFM_FREQEMER = VHFFM_FREQEMER;
        }
    }

//  Mode OFF/TR/DF -> SwitchMultiPos at expander pins GPA4 (4) to GPA6 (6)
  if (mcp.digitalRead(4) == 0)
    {
    VHFFM_MODE = 0;
      if (prev_VHFFM_MODE != 0)
        {
            DcsBios::tryToSendDcsBiosMessage("VHFFM_MODE", "0");
            prev_VHFFM_MODE = VHFFM_MODE;
        }
    }
  if (mcp.digitalRead(5) == 0)
    {
    VHFFM_MODE = 1;
      if (prev_VHFFM_MODE != 1)
        {
            DcsBios::tryToSendDcsBiosMessage("VHFFM_MODE", "1");
            prev_VHFFM_MODE = VHFFM_MODE;
        }
    }
  if (mcp.digitalRead(6) == 0)
    {
    VHFFM_MODE = 2;
      if (prev_VHFFM_MODE != 2)
        {
            DcsBios::tryToSendDcsBiosMessage("VHFFM_MODE", "2");
            prev_VHFFM_MODE = VHFFM_MODE;
        }
    }
//  Preset Channel Selector -> two push buttons workaround for a rocker switch at expander pins GPA7 (7) and GPB0 (8)
  if (mcp.digitalRead(7) == 0)
    {
    VHFFM_PRESET = 1;
      if (prev_VHFFM_PRESET != 1)
        {
          DcsBios::tryToSendDcsBiosMessage("VHFFM_PRESET", "DEC");
          delay(debounce*10);
          prev_VHFFM_PRESET = 0;  // reset to accept next button signal
        }
    }
  if (mcp.digitalRead(8) == 0)
    {
    VHFFM_PRESET = 2;
      if (prev_VHFFM_PRESET != 2)
        {
            DcsBios::tryToSendDcsBiosMessage("VHFFM_PRESET", "INC");
            delay(debounce*10);
            prev_VHFFM_PRESET = 0;  // reset to accept next button signal
        }
    }
//  Squelch -> Switch3Pos at expander pins GPB1 (9) and GPB2 (10)
  if ((mcp.digitalRead(9) == 1) && (mcp.digitalRead(10) == 1))  // workaround to active send from the middle position of a 3 pos toggle switch
    {
    VHFFM_SQUELCH = 1;
      if (prev_VHFFM_SQUELCH != 1)
        {
            DcsBios::tryToSendDcsBiosMessage("VHFFM_SQUELCH", "1");
            prev_VHFFM_SQUELCH = VHFFM_SQUELCH;
        }
    }
       
  if (mcp.digitalRead(9) == 0)
    {
    VHFFM_SQUELCH = 0;
      if (prev_VHFFM_SQUELCH != 0)
        {
            DcsBios::tryToSendDcsBiosMessage("VHFFM_SQUELCH", "0");
            prev_VHFFM_SQUELCH = VHFFM_SQUELCH;
        }
    }
    
  if (mcp.digitalRead(10) == 0)
    {
    VHFFM_SQUELCH = 2;
      if (prev_VHFFM_SQUELCH != 2)
        {
            DcsBios::tryToSendDcsBiosMessage("VHFFM_SQUELCH", "2");
            prev_VHFFM_SQUELCH = VHFFM_SQUELCH;
        }
    }  

//  Load Button -> simple push button at expander pin GPB3 (11)
  if (mcp.digitalRead(11) == 0)
    {
    VHFFM_LOAD = 1;
      if (prev_VHFFM_LOAD != 1)
        {
          DcsBios::tryToSendDcsBiosMessage("VHFFM_LOAD", "1");
          delay(debounce*10);
          prev_VHFFM_LOAD = 0;  // push Load Button
        }
    }

  if ((mcp.digitalRead(11) == 1) && (VHFFM_LOAD == 1))  // release button and reset the variable
    {
      delay(debounce*10);
      DcsBios::tryToSendDcsBiosMessage("VHFFM_LOAD", "0");
      VHFFM_LOAD = 0;
      prev_VHFFM_LOAD = 0;
    }
}

// ---------- End of Declaration of Functions ----------

 

Regards, Vinc


Edited by Vinc_Vega
  • Like 1
  • Thanks 1

Regards, Vinc

real life: Royal Bavarian Airforce

online: VJS-GermanKnights.de

[sIGPIC][/sIGPIC]

Link to comment
Share on other sites

  • 2 weeks later...

For the sake of completeness:

Functioning sketch for the F-16 Fuel Flow Counter, adapted to a SH1106 I2C OLED 128 x 64 pixel.

https://forum.dcs.world/topic/329533-code-needed-for-viper-ffi-using-sh1106-13-128x64-iic/#comment-5296189

 

Regards, Vinc


Edited by Vinc_Vega
  • Like 1

Regards, Vinc

real life: Royal Bavarian Airforce

online: VJS-GermanKnights.de

[sIGPIC][/sIGPIC]

Link to comment
Share on other sites

  • 3 months later...

Producing DCS-BIOS Gauges – Example coding and lessons learned

Thought that I would share my work to-date on DCS-BIOS controlled gauges.  First with three example individual gauges for the F-18, then a more complex example (first example below and attached), building on these gauges, to have them all controlled from a single ESP32, hence saving on COM ports. 

I will explain the structure of each bit of code and how it all fits together. Happy to take comments or suggestions for improvements. I have kept the code down to the minimum needed.

I am using the GC9A01 1.28 inch 3.3v TFT round displays, but I will try to explain where you will have to amend the code if you are using something else. The code should work with any ESP32 that you can program via the Arduino IDE.

Hardware

First task is to ensure that your hardware is configured correctly. We will be using the TFT_eSPI library, so this needs to be loaded and configured correctly. In particular you need to ensure that the correct driver is loaded (GC9A01 in this case) and that the pin outs are correct. This can be done in the User_Setup.h file within the TFT_eSPI folder. I suggest running the Color Test from the TFT_eSPI examples to check everything is working correctly.  It you are using a different display you will have to select an alternative driver etc.

Examples

The three gauges that I am going to cover are:

  • Battery Gauge 
  • Hydraulic Pressure
  • Brake Pressure

All three sketches share a common format, with the main differences around the number, position and rotation of the needles.  When we get to the three gauge sketch you will notice that, in addition to adding the code to get the displays to work together, I had to change a few of the names to avoid any conflict or just make things more consistent.  Lesson 1 – If you are going to make multiple gauges that you might want to later combine into a single sketch, develop a format for all your function and variable names.

Producing Graphics

The method of producing the graphics is common to all the gauges, so I will start with that. All the gauges consist of a background image and one or more needles. These are converted into ‘Sprites’ in the code which is the most efficient means of using them.

I used the following tools for producing the graphics, but alternatives are fine:

  • Paint.net – Used to produce and manipulate .png images. I found that a tool that supported layers was very useful in developing the images, allowed trial and error.  I also found myself using Microsoft Paint on occasion when I needed a very basic capability.
  • Icd-image-converter – This was used to convert the .png files into code that the Arduino IDE can use.

Background Image – This needs to be produced at 240x240 pixels (for the GC9A01), I kept with 8-bit colors. My experience is to keep the background of the background image black (and I mean black, not dark grey).  Lesson 2 – Not doing this proved troublesome later when the needles passed over the not quite black areas and left a trace behind. The final image needs to be converted, in Icd-image-converter, to R5G6B5 format with a block size of 16 bit and Little-Endian Byte order.  Once configured in the tool you can use the ‘Show Preview’ option to display the resultant code and cut and paste it into your sketch.

Needle Image - This follows the same process as the background. The size of the needle will be driven by your particular gauge, but will be about 80-120 pixels tall and 15 -25 pixels wide.  Try to keep the needle symmetrical and an odd number of pixels wide (see pivot later).  Keep your needle background color something you are not using elsewhere on the image as once you have imported it into the IDE you will want to use the Find drop down to replace this color code with the one for TRANSPARENT (0x0120).

Pivots – You will need to identify pivot points for your background image and needles. The pivot for the background (GC9A01) will be 120x120. The needle(s) pivot will depend on the needle(s), this is where the odd number of pixels for the needle width comes in handy.  Lesson 3 - The needle overall size and pivot point must be accurate in the code otherwise you will get all sorts of strange behaviour.

Example 1 - Battery Gauge (F-18_Battery_Gauge.ino)

Having produced the graphics for your Battery gauge, we can start on the coding. We will need the ‘colorDepth’ regularly, so set a constant for this (7).

‘include’ the two image files, CDS-BIOS and the TFT_eSPI library (9, 10, 14, 16)

‘define’ DCSBIOS_DEFAULT_SERIAL (12)

Set up the Sprites, there will be three in this case, the background and two needles (both the same image) (18 – 20)

Declare initial values for the needle angles (22, 23)

Call the two sections of DCS-BIOS code, one for each needle (U and E) (25 – 37). There are two common lines of code within this that I will explain. The first ‘angleMapU or E’ uses the Map command with the input ‘newValue’ from the DCS-BIOS function, along with the range of possible outputs from DCS-BIOS (0-65535), together with the range of desired values of the needle to produce a needle angle. In the first case the desired needle value we want is on the left of the gauge between -150 to -30, the needle degrees are measured from 0 (12 O’clock position). In the second case the needle is on the right of the gauge and hence 150 to 30 e.g.  both needles will start at the bottom and climb upwards. ‘plotGauge’ is then used to plot both needle positions, even if only one has actually changed.

Within the setup function (41 – 47) we include the necessary DCS-BIOS call, initialize TFT and fill the screen with BLACK color. There are then three lines of code that impact the Byte order of the graphics. These interact with the Big and Little-Endian settings.  You might need to change these in your own projects, but they work in the example here.  There is then a call to a Bit_test that will run on power up and cycle the needles through there min – max movement.  You can leave as is, or comment this line out as required.

The loop function (52) only needs the DCS-BIOS reference.

Lines 55 – 69 are the Bit_test.

Lines 71 – 82 are the ‘plotGauge’ function. It starts of creating the three Sprites and pushing the needles, as the desired angles, onto the background. The TFT_TRANSPARENT tell the code to not display anything in this color. Once complete we delete the ‘Sprites’ to free up memory.

Lines 84-91 create the background, setting the colorDepth, size and pivot point, and pushing the ‘Battery’ image onto the screen.

Lines 93 – 99 and 101 – 107 create the two needles, note the difference between the total size of the needle and its pivot point.

If you have done everything correctly you should be good to go….

F-18_Battery_Gauge.ino BatteryBackground.h Needle.h

F-18 Gauges.jpg


Edited by Tanarg
Added picture
  • Like 1
  • Thanks 2
Link to comment
Share on other sites

Example 2 - Hydraulic Pressure (F-18_HydraulicPressure_Gauge.ino)

The second example is for the F-18 Hydraulic Pressure Gauge. It follows basically the same format as the first example, except that there are two different needles (because they are numbered as 1 and 2) that run over one another around the same scale. I will only explain the differences which are really confined to the Bit_test.  Lesson 4: The thing that confused me to start with was that to get the needles to behave correctly I needed to start counting at -280 e.g. anticlockwise 280 rather than 80 degrees clockwise, whilst I needed to end at +40. At face value the needles start at +80 and go clockwise to end at +40.

F-18_HydralicPressure_Gauge.ino hydPressBackground.h hydPressNeedle1.h hydPressNeedle2.h

  • Like 2
  • Thanks 1
Link to comment
Share on other sites

12 hours ago, Tanarg said:

Example 3 – Brake Pressure Gauge (F-18_BrakePressure_Gauge.ino)

Nothing in this one that we have not already covered

(Three gauge example to be posted tomorrow)

 

Thanks, But I should note the addresses you have in these sketches don't work in my up-to-date Open Beta / Flightpanels DCS-BIOS install.
They all need 0x0010 to be added to them.  A named address file was added to DCS-BIOS a several months ago to make updates easier.

Link to comment
Share on other sites

Example 4 – Three Gauges driven from single ESP32 (F-18_ThreeGauge.ino)

The individual gauge mechanics and coding of this example haven’t changed from the previous examples, except in same cases to avoid name conflicts or have more consistent naming.  I will concentrate on the additional coding required to get all three displays working on the single ESP32. 

Hardware

This is the first fundamental area of change. Normally you would have TFT_eSPI control the pin outs in User_Setup.h. This would include which pin you had been using for Chip Select (CS).  This pin is used to identify the display the program is going use – normally this is a single display and does not change. In this case, we want to comment out the ‘CS’ line in User_Setup.h. In its place we are going to control the pins used at any given time via the sketch.

We want to end up with each display connecting to the same pins except for the CS pin, where they will each connect to a different pin. See drawing1 attached.

Multi Display Code

As DCS-BIOS is interrupt driven, we can use the outputs from it to know when we need to write something to a particular screen.  To write something to a display we need to set the relevant CS pin to low (0) and set it back to high (1) when we have finished.  Where appropriate we can write to multiple displays simultaneously.   In the first addition we are going to define three displays associating a pin with each, 4, 16 & 17 in my case (lines 20 – 22). To make things more readable we have created four functions (289-311) that can be used to turn on or off one display (Screen) or all displays (Screens).

The next change is setting ‘pinMode’ for each display to OUTPUT (89 – 91)

As part of setup, we initialise and fillScreen all displays to TFT_BLACK (93 – 96) – ScreensOn & ScreensOff

In lines (98 – 113) we set the setSwapBytes status for the Sprites for each display – ScreenOn x & ScreenOff x

We then drop down to the plotGauge sections that drive the display for each gauge:

  • plotBatGauge (180 – 193)
  • plotHydPressGauge (220 – 233)
  • plotBrakePressGauge (260 – 270)

Each starts with a ScreenOn and finishes with a ScreenOff for a particular Display

So, the logic is that something changes in DCS and is picked up by the relevant DCS-BIOS function that we are monitoring. It works out the new needle position for the relevant needle and gauge and calls the associated plotGauge function. At this point we select the relevant display (screen) and turn it on so that we can write to it. We create the appropriate Sprites etc and push them to the display. We then turn the screen off (for writing) and await the next event from DCS-BIOS.

Compared to a game like Ping running on all three displays simultaneously, the number of updates from DCS is comparatively small and therefore this interrupt mode of screen handling seems to work fine in testing. The alternative would be creating a separate display handler and some form of time-based display multiplexing. I think this is overkill for what we need.

brakePressNeedle.h F-18_ThreeGauge.ino hydPressBackground.h hydPressNeedle1.h hydPressNeedle2.h batBackground.h batNeedle.h brakePressBackground.h

Drawing1.jpg


Edited by Tanarg
Add pin connection diagram
  • Like 2
  • Thanks 1
Link to comment
Share on other sites

12 hours ago, Maxglider said:

I am messing up with my sketch for F/A18 Hornet Altimeter setting.

I can not solve how to display the first two digit correctly. (ex, 28 29 30 31)

Could any one help with me?

Mod_FA18_BARO_and_Knob_copy_20240120170254.ino 8.98 kB · 4 downloads

You should start a fresh post in the forum rather than post for help in a "Working code" thread...

Link to comment
Share on other sites

  • 1 month later...

F-18C Cabin Pressure Gauge

Something a bit different this time. I have been looking for a bigger round display to cope with some of the larger cockpit gauges. The next size I have been looking for was 2-2.5 inch and I found the best fit was a 2.1 inch round ST7701S display I found on AliExpress. The display at this size uses 480x480 pixels, so this presents some challenges in terms of driving it. At this resolution you can't really use a SPI (serial) connection, it's just not fast enough.  The ST7701S uses a mixture of SPI for config and parallel to move the data. The second point is that the bitmaps at this scale are four times the size of those on the smaller displays I have been using. A third point is that the ST7701S interface is not widely supported. As an example it is not supported by TFT_eSPI, which you will note from above I widely use.

To get around these issues I found the Adafruit Qualia ESP32S3 board. It provides a parallel link to the ST7001S display and the on-board ESP32S3 has enough memory (for this sketch I used 41% of it's available memory). It used the GFX library for communications and graphics handling. As far as I can see the GFX library does not provide all the functionality that I wanted particularly in respect of sprite handling. Fortunately, we can use both TFT_eSPI and GFX libraries at the same time. TFT_eSPI to do the graphics manipulation and GFX to push the resultant image to the display.  This seems to work well, and performance seems good. Be careful though if you want to add additional code. For example, you will note that I do not initialise TFT, it doesn't appear to be needed in this situation and it you try will likely find the sketch will compile, but not work (at all).

You will find that the sketch follows my normal format, but with a larger configuration section at the top. Note that you do not need to configure TFT UserSetup.h as this part of the config is done by GFX in the sketch. As usual, I have added a BIT test, which I find useful for testing, you can comment out if not required, otherwise it will run once on start-up. The sketch is written for DCS-BIOS FP, if you are using the original version, you will need to change 0x7514 to 0x7504 in the DCS-BIOS section of the code.

FYI, the Qualia board does support other ST7701 display sizes if required.

Now that I have this size of display working, I am thinking that the F-18 RAD ALT should be my next project.

Comments/Questions welcome.

CabinPressure.jpg

cabinPressBackground.h cabinPressNeedle.h F_18_Cabin_Pressure_Gauge_Qualia_FP.ino

  • Like 3
Link to comment
Share on other sites

This should be a code and sketches repository post to help cockpit builders, but nevertheless you may try the above Search function and filters and get something like this:

Than open the hidden content for a DED sketch.

 

Regards, Vinc

Regards, Vinc

real life: Royal Bavarian Airforce

online: VJS-GermanKnights.de

[sIGPIC][/sIGPIC]

Link to comment
Share on other sites

F-18C RALT

Building on the previous Qualia based display. This one is the Radar Alt for the F-18C. Somewhat more complex in terms of the number of parts and that they are layered. Effectively the display is broken into two parts, the needles and the lamps.  The needle handling is very similar to the previous example, using push.Rotated to push the needle position onto the background at the appropriate angle. The minimum height pointer graphic is the reverse of what we have used before. The graphic is mainly transparent with only the reverse triangle at the top in white and the pivot point in the transparent area at the bottom.

The lamps don't need to be rotated, so we use pushToSprite instead. Remember we can't use pushImage as drawing to the screen is taken care of by GFX. The red and green lamp functions are almost the same with 0 for off and 1 for on, so if the value returned by DCS-BIOS is 1 we create the associated sprite and push it to the background sprite, overwise we don't and skip over the code. The OFF flag is the same except it's two values are 0 and 65535, nothing in-between. The 65535 value corresponds to 5,000ft over which height the RADALT is not accurate, and hence turned off.

As usual there is a BIT test to use if required. Written for FP (Skunkworks)

I have not provided the code to replicate the push to test and altitude set function (simple to add) as this requires additional hardware and needs some further work on the integration to the Qualia ESP32S3 board. I will update once this work is done.

As usual any comments/questions welcome.

gauge.jpg

F_18_RALT_Gauge_Qualia_FP.ino radarAltNeedle.h radarAltOffFlag.h radarAltBackground.h radarAltGreenLamp.h radarAltLowAltWarning.h radarAltMinHeightPointer.h

  • Like 4
Link to comment
Share on other sites

  • 2 weeks later...

please help:

F-18C Cabin Pressure Gauge

C:\Users\scorp\OneDrive\Počítač\Arduino F18c_HORNET\__01_FINAL\BUDIKY Final\07_CABIN-ovy_tlakomer\07_CABIN\Adafruit Qualia ESP32S3\F_18_Cabin_Pressure_Gauge_Qualia_FP\F_18_Cabin_Pressure_Gauge_Qualia_FP.ino:24:3: error: 'PCA_TFT_RESET' was not declared in this scope
C:\Users\scorp\OneDrive\Počítač\Arduino F18c_HORNET\__01_FINAL\BUDIKY Final\07_CABIN-ovy_tlakomer\07_CABIN\Adafruit Qualia ESP32S3\F_18_Cabin_Pressure_Gauge_Qualia_FP\F_18_Cabin_Pressure_Gauge_Qualia_FP.ino:24:18: error: 'PCA_TFT_CS' was not declared in this scope
C:\Users\scorp\OneDrive\Počítač\Arduino F18c_HORNET\__01_FINAL\BUDIKY Final\07_CABIN-ovy_tlakomer\07_CABIN\Adafruit Qualia ESP32S3\F_18_Cabin_Pressure_Gauge_Qualia_FP\F_18_Cabin_Pressure_Gauge_Qualia_FP.ino:24:30: error: 'PCA_TFT_SCK' was not declared in this scope
C:\Users\scorp\OneDrive\Počítač\Arduino F18c_HORNET\__01_FINAL\BUDIKY Final\07_CABIN-ovy_tlakomer\07_CABIN\Adafruit Qualia ESP32S3\F_18_Cabin_Pressure_Gauge_Qualia_FP\F_18_Cabin_Pressure_Gauge_Qualia_FP.ino:24:43: error: 'PCA_TFT_MOSI' was not declared in this scope
C:\Users\scorp\OneDrive\Počítač\Arduino F18c_HORNET\__01_FINAL\BUDIKY Final\07_CABIN-ovy_tlakomer\07_CABIN\Adafruit Qualia ESP32S3\F_18_Cabin_Pressure_Gauge_Qualia_FP\F_18_Cabin_Pressure_Gauge_Qualia_FP.ino:27:1: error: 'Arduino_ESP32RGBPanel' does not name a type
C:\Users\scorp\OneDrive\Počítač\Arduino F18c_HORNET\__01_FINAL\BUDIKY Final\07_CABIN-ovy_tlakomer\07_CABIN\Adafruit Qualia ESP32S3\F_18_Cabin_Pressure_Gauge_Qualia_FP\F_18_Cabin_Pressure_Gauge_Qualia_FP.ino:35:1: error: 'Arduino_RGB_Display' does not name a type
C:\Users\scorp\OneDrive\Počítač\Arduino F18c_HORNET\__01_FINAL\BUDIKY Final\07_CABIN-ovy_tlakomer\07_CABIN\Adafruit Qualia ESP32S3\F_18_Cabin_Pressure_Gauge_Qualia_FP\F_18_Cabin_Pressure_Gauge_Qualia_FP.ino: In function 'void setup()':
C:\Users\scorp\OneDrive\Počítač\Arduino F18c_HORNET\__01_FINAL\BUDIKY Final\07_CABIN-ovy_tlakomer\07_CABIN\Adafruit Qualia ESP32S3\F_18_Cabin_Pressure_Gauge_Qualia_FP\F_18_Cabin_Pressure_Gauge_Qualia_FP.ino:58:8: error: 'gfx' was not declared in this scope
C:\Users\scorp\OneDrive\Počítač\Arduino F18c_HORNET\__01_FINAL\BUDIKY Final\07_CABIN-ovy_tlakomer\07_CABIN\Adafruit Qualia ESP32S3\F_18_Cabin_Pressure_Gauge_Qualia_FP\F_18_Cabin_Pressure_Gauge_Qualia_FP.ino: In function 'void plotCabinPressGauge(int16_t)':
C:\Users\scorp\OneDrive\Počítač\Arduino F18c_HORNET\__01_FINAL\BUDIKY Final\07_CABIN-ovy_tlakomer\07_CABIN\Adafruit Qualia ESP32S3\F_18_Cabin_Pressure_Gauge_Qualia_FP\F_18_Cabin_Pressure_Gauge_Qualia_FP.ino:95:3: error: 'gfx' was not declared in this scope

exit status 1

Compilation error: 'PCA_TFT_RESET' was not declared in this scope


Edited by scorpyq
Link to comment
Share on other sites

2 hours ago, scorpyq said:

please help:

F-18C Cabin Pressure Gauge

C:\Users\scorp\OneDrive\Počítač\Arduino F18c_HORNET\__01_FINAL\BUDIKY Final\07_CABIN-ovy_tlakomer\07_CABIN\Adafruit Qualia ESP32S3\F_18_Cabin_Pressure_Gauge_Qualia_FP\F_18_Cabin_Pressure_Gauge_Qualia_FP.ino:24:3: error: 'PCA_TFT_RESET' was not declared in this scope
C:\Users\scorp\OneDrive\Počítač\Arduino F18c_HORNET\__01_FINAL\BUDIKY Final\07_CABIN-ovy_tlakomer\07_CABIN\Adafruit Qualia ESP32S3\F_18_Cabin_Pressure_Gauge_Qualia_FP\F_18_Cabin_Pressure_Gauge_Qualia_FP.ino:24:18: error: 'PCA_TFT_CS' was not declared in this scope
C:\Users\scorp\OneDrive\Počítač\Arduino F18c_HORNET\__01_FINAL\BUDIKY Final\07_CABIN-ovy_tlakomer\07_CABIN\Adafruit Qualia ESP32S3\F_18_Cabin_Pressure_Gauge_Qualia_FP\F_18_Cabin_Pressure_Gauge_Qualia_FP.ino:24:30: error: 'PCA_TFT_SCK' was not declared in this scope
C:\Users\scorp\OneDrive\Počítač\Arduino F18c_HORNET\__01_FINAL\BUDIKY Final\07_CABIN-ovy_tlakomer\07_CABIN\Adafruit Qualia ESP32S3\F_18_Cabin_Pressure_Gauge_Qualia_FP\F_18_Cabin_Pressure_Gauge_Qualia_FP.ino:24:43: error: 'PCA_TFT_MOSI' was not declared in this scope
C:\Users\scorp\OneDrive\Počítač\Arduino F18c_HORNET\__01_FINAL\BUDIKY Final\07_CABIN-ovy_tlakomer\07_CABIN\Adafruit Qualia ESP32S3\F_18_Cabin_Pressure_Gauge_Qualia_FP\F_18_Cabin_Pressure_Gauge_Qualia_FP.ino:27:1: error: 'Arduino_ESP32RGBPanel' does not name a type
C:\Users\scorp\OneDrive\Počítač\Arduino F18c_HORNET\__01_FINAL\BUDIKY Final\07_CABIN-ovy_tlakomer\07_CABIN\Adafruit Qualia ESP32S3\F_18_Cabin_Pressure_Gauge_Qualia_FP\F_18_Cabin_Pressure_Gauge_Qualia_FP.ino:35:1: error: 'Arduino_RGB_Display' does not name a type
C:\Users\scorp\OneDrive\Počítač\Arduino F18c_HORNET\__01_FINAL\BUDIKY Final\07_CABIN-ovy_tlakomer\07_CABIN\Adafruit Qualia ESP32S3\F_18_Cabin_Pressure_Gauge_Qualia_FP\F_18_Cabin_Pressure_Gauge_Qualia_FP.ino: In function 'void setup()':
C:\Users\scorp\OneDrive\Počítač\Arduino F18c_HORNET\__01_FINAL\BUDIKY Final\07_CABIN-ovy_tlakomer\07_CABIN\Adafruit Qualia ESP32S3\F_18_Cabin_Pressure_Gauge_Qualia_FP\F_18_Cabin_Pressure_Gauge_Qualia_FP.ino:58:8: error: 'gfx' was not declared in this scope
C:\Users\scorp\OneDrive\Počítač\Arduino F18c_HORNET\__01_FINAL\BUDIKY Final\07_CABIN-ovy_tlakomer\07_CABIN\Adafruit Qualia ESP32S3\F_18_Cabin_Pressure_Gauge_Qualia_FP\F_18_Cabin_Pressure_Gauge_Qualia_FP.ino: In function 'void plotCabinPressGauge(int16_t)':
C:\Users\scorp\OneDrive\Počítač\Arduino F18c_HORNET\__01_FINAL\BUDIKY Final\07_CABIN-ovy_tlakomer\07_CABIN\Adafruit Qualia ESP32S3\F_18_Cabin_Pressure_Gauge_Qualia_FP\F_18_Cabin_Pressure_Gauge_Qualia_FP.ino:95:3: error: 'gfx' was not declared in this scope

exit status 1

Compilation error: 'PCA_TFT_RESET' was not declared in this scope

 

Do you have the Adafruit GFX library installed in your Arduino IDE?  If not, try installing that.

Link to comment
Share on other sites

  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...