Rotate 8x8 Dot Matrix

Hello professionals :blush:
I would like to build my own dot matrix display.
I got the idea from Adafruit. It is a 16 x 24 LED dot matrix display with a Holtec HT1632 controller and an ESP32 to drive it.
When building the board, I had to rotate each of the 6 8x8 Dot Matrix modules 90 degrees anti-clockwise to make it easier to route through the legs.
I was aware that I would have to rotate the displays 90 degrees anti-clockwise again later via software.
I use the Adafruit HT1632 library because it is obvious.

The library assumes that column 0 and row 0 (top left) control the first LED. The last LED of the first row is then at 0;23 (top right).
The first LED of the last row is at 15;0 (bottom left) and the last at 15;23 (bottom right). So there are exactly 384 LEDs that can be controlled.
The board is now assembled and works perfectly from a technical point of view.
However, because each of the 6 x 8x8 LED matrix is mechanically rotated 90 degrees anti-clockwise, I now have to correct this via software.
I have now given up trying to solve the problem with simple For next loops because I am a beginner. After eight hours I was completely exhausted.
To make progress, I have built two arrays where I store the corrected coordinates. However, this costs me 768 bytes of ram! Not a good solution.
Now I can set every single LED in Adafruit style via Set Pixel.
But only from my sketch.
But if I now want to use the Adafruit GFX Library library referenced from the Adafruit_HT1632 library, this is not possible because they do everything internally.
So I have no way of transferring my corrected coordinates to the Adafruit GFX Library library.

I now have two questions:
Is it possible to do it smarter with rotating the 8x8 LED dot matrix displays without using 768 bytes?

Does anyone see a way to pass my corrected coordinates to the Adafruit_HT1632 library without changing the library?
If I had to change the library, I would be lost because I've never done anything like this before.

Thanks for trying to help me.
Greetings Bienchen

#include "Adafruit_HT1632.h"

#define HT_DATA 14
#define HT_WR   0
#define HT_CS   4
//#define HT_CS2  5

// use this line for single matrix
Adafruit_HT1632LEDMatrix matrix = Adafruit_HT1632LEDMatrix(HT_DATA, HT_WR, HT_CS);
// use this line for two matrices!
//Adafruit_HT1632LEDMatrix matrix = Adafruit_HT1632LEDMatrix(HT_DATA, HT_WR, HT_CS, HT_CS2);

// Y = Row and X = Columm
uint8_t X_ARRAY[384];
uint8_t Y_ARRAY[384];





void setup() {
  Serial.begin(9600);
  pinMode(27, OUTPUT);    
  digitalWrite(27, LOW); // sets OE to disabled
  delay(1000);
  digitalWrite(27, HIGH); // sets OE to enabled
  delay(1000);
  
  
  
  matrix.begin(ADA_HT1632_COMMON_16NMOS);
  matrix.fillScreen();
  delay(500);
  matrix.clearScreen();
  matrix.setTextWrap(false);
  matrix.setRotation(0);
  //matrix.clearScreen();
  matrix.setBrightness(1);
  matrix.setCursor(0, 0);
  Fill_Array();
}




void loop() {


    uint8_t X_Work =0;
    uint8_t Y_Work =0;

    for (uint ADA_I=0;ADA_I < 384;ADA_I++){
    X_Work = X_ARRAY[ADA_I];
    Y_Work = Y_ARRAY[ADA_I];

        //Serial.print(" ADA Count = "); Serial.print(ADA_I);Serial.print(": Y Work = "); Serial.print(Y_Work);Serial.print(" X Work = "); Serial.print(X_Work);Serial.println();
        //matrix.setPixel(X_Work, Y_Work);
        //matrix.writeScreen();
        //delay (1000);
            // if (ADA_I == 383) {
            //   matrix.clearScreen();
            // }
        }

}




void Fill_Array() {

uint Counter = 0;
uint8_t x=7;
uint8_t X_modulo=0;
uint8_t y_modulo=0;

    for (int8_t l=0; l<16; l++) {

        for (uint8_t i=1; i<4; i++) {
          switch (i){
              case 1:
              x=7;
              break;
              case 2:
              x=15;
              break;
              case 3:
              x=23;
              break;         
              }
          
          if (l < 8 ) {
            x=x-l ;
          } else if (l > 8 ) {
            x=x-(l-8 );
          }

            for (uint8_t y=0; y<8; y++) {     

              X_modulo= Counter % 24;
              y_modulo= Counter / 24; 
                            
              if (l > 7){
              X_ARRAY[Counter] = x;
              Y_ARRAY[Counter] = y + 8;
              matrix.setPixel(x, y + 8);
              Serial.print(" LED Position = "); Serial.print(Counter);Serial.print(" ADAKORDS : X = ");Serial.print(X_modulo); Serial.print(" Y = ");Serial.print(y_modulo);Serial.print(" / MY = ");Serial.print(" X = "); Serial.print(x); Serial.print(" Y = ");
              Serial.print(y + 8);
              Serial.println();

            } else{
              X_ARRAY[Counter] = x;
              Y_ARRAY[Counter] = y;
              matrix.setPixel(x, y);
              Serial.print(" LED Position = "); Serial.print(Counter);Serial.print(" ADAKORDS : X = ");Serial.print(X_modulo); Serial.print(" Y = ");Serial.print(y_modulo);Serial.print(" / MY = ");Serial.print(" X = "); Serial.print(x); Serial.print(" Y = ");
              Serial.print(y);
              Serial.println();

            }
              Counter++;
              matrix.writeScreen();

              delay (500);



            }
        }
    }
matrix.clearScreen();
Serial.print("ARRAY written");Serial.println();
}

Rotate your monitor.

JK.

I would use an address translation algorithm. Make a function that takes your intended address and returns your rotated coordinates. Then slip it right into your write parameters.

You describe it like this a flat matrix with (0..23) columns and (0..15) rows. If they are, what is the problem with using a flat x, y? If they are not flat, how are they arranged?

Possibly useful - rotate a matrix.

There are two types of raster for a dot matrix a linear raster and a zig jag raster known as a serpentine raster. Then for each raster type there are two types of configuration, row based and column based.

So this gives you four different possible types of raster as illustrated by this diagram:-

To address any individual dot in a raster you need to know what sort you have. The simplest to address is the linear which is simply
led number = Y value + Xvalue * Yvalue
for a column raster or for a row matrix is
led number = X value + Xvalue * Yvalue

For a serpentine raster it is a bit more complex, but not very much so. The formula you use depends on if you are on an odd or even column or row.

int getPixPos(int x, int y){ // for a serpentine raster
   int pos;
   if(x &0x1) { // is it an odd or even
      pos = x * yMax + (yMax -1 - y) ;
   } else {
   pos = x * yMax + y;
   } 
   return pos;
}

Hope that clarifies what you have here. You can expand this to any size of raster you want.

Hello
Thank you for showing me the possibilities.
@xfpd
Yes, it is a flat. How the pixels are arranged?
I'll try to attach pictures that might explain.
@dougp
That could indeed be a solution. However, it is written in C++.
I've never worked in C++ and I'm a beginner in C. But I think I could make it work.
@Grumpy_Mike
I think my version is the second row on the left. However, the zero point is at the top.
I'll try to attach pictures.
I'll also attach a text file that gives you the coordinates.

At this point, thanks to all of you for helping me!
Greetings Bienchen
Coordinates.txt (24,5 KB)


I could not understand which picture is your configuration. I'm guessing the second (please, label your configuration). If so, address the LEDs in each character:

row = 7 - row; // to read rows top to bottom
col = 7 - col; // to read columns left to right

To address next character row...

row = (charRow * 8) + (7 - row);

To address the next character col...

col = (charCol * 8) + (7 - col);