DCS-Skunkworks / dcs-bios

Data export tool for DCS.
https://dcsbios.com/
GNU General Public License v3.0
290 stars 65 forks source link

Request for events in the M2000C module with strings providing Left, Right, Prep & Dest PCN Display strings #1002

Open escaner opened 3 months ago

escaner commented 3 months ago

Version

Aircraft

M2000C

Control

PCN Display for Left, Right, Prep & Dest

Description

Since the modification of the M2000C module PCN display to show malfunctions in the individual segments of the digits, we have lost the events that returned the full processed string of digits for PREP, DEST, LEFT & RIGHT displays in the PCN (INS). This request is for those events to be implemented again, as the code to do this in the Arduino requires over 100 callbacks and uses lots of precious flash code memory (almost 25% in an Arduino Pro Micro).

PS: The previously mentioned malfunctions can be disabled in DCS in: Options -> Special -> M-2000C -> Minor display wear malfunctions -> set to zero (0)

Screenshots

No response

Additional context

As a reference, I am providing my implementation in C++ for Arduino, it can be found here: https://github.com/escaner/ufc/blob/flightpanels/src/displpnl.cpp

I am also copying here the code for the PCN Prep display. Note that this code does not process the dots in the display, only the digits.

class DisplPnl
{

[...]

protected:

  struct Segments2Char_t
  {
    uint8_t Segments;  // 7 segment character representation
    char Char;         // Represented character
  };

  static const char _UNKNOWN_CHAR = '*';

};

// Given a 7 segment LCD configuration, which character represents
const DisplPnl::Segments2Char_t DisplPnl::_SEGMENTS2CHAR[] PROGMEM =
{
  { 0b00000000, ' ' },
  { 0b00111111, '0' },
  { 0b00011000, '1' },
  { 0b01101101, '2' },
  { 0b01111100, '3' },
  { 0b01011010, '4' },
  { 0b01110110, '5' },
  { 0b01110111, '6' },
  { 0b00011100, '7' },
  { 0b01111111, '8' },
  { 0b01111110, '9' },
};

/*
 *   Updates M2000C PCN Prep.
 *  Parameters:
 *  * Digit: in which digit happened the change.
 *  * Segment: in which segment of the digit happened the change.
 *  * Value: intensity of the segment (0-3; 0 is off).
 */
void DisplPnl::m2000cPcnPrep(DigitId_t Digit, SegmentId_t Segment,
  uint8_t Value)
{
  uint8_t SegmentPtrn;
  char Char;

  // Update the segment pattern for Digit
  SegmentPtrn = _Status.M2000c.DispPrep[Digit];
  bitWrite(SegmentPtrn, Segment, Value);
  _Status.M2000c.DispPrep[Digit] = SegmentPtrn;

  // Translate 7-segment pattern to actual character and write it in the LCD
  Char = _segments2Char(SegmentPtrn);
  if (Char != _UNKNOWN_CHAR)
  {
    _Lcd.setCursor(M2000C_PCNPREP_COL + Digit, M2000C_PREPDEST_ROW);
    _Lcd.write(Char);
  }
}

/*
 *   Given a 7 segment character configuration, translates it to the represented
 *  character.
 *  Parameters:
 *  * Segments: 7 segment representation in the lowest 7 bits
 *  Returns: the character represented by Segments or _UNKNOWN_CHAR
 *  when none is.
 */
char DisplPnl::_segments2Char(uint8_t Segments)
{
  const Segments2Char_t *pEntry;
  const uint8_t NumEntries = sizeof _SEGMENTS2CHAR / sizeof (Segments2Char_t);

  // Traverse all entries in the array looking for the matching configuration
  for (pEntry = _SEGMENTS2CHAR; pEntry != _SEGMENTS2CHAR + NumEntries; pEntry++)
  {
    // Is this the segment pattern we are looking for?
    if (Segments == pgm_read_byte(&pEntry->Segments))
      // Fount it!
      return pgm_read_byte(&pEntry->Char);
  }

  // We did not find a matching pattern
  return _UNKNOWN_CHAR;
}