Help with 8x17 LED Neopixel Matrix

Hi, I have recently constructed my first matrix which is 17 neopixels long by 8 neopixels. 8 rows of 17 neopixels in a zigzag pattern.

I have a couple of questions. When i run the matrixtest code in arduino, the “Howdy” example is being displayed sideways. I have it set up in the example like this:

// Adafruit_NeoMatrix example for single NeoPixel Shield.
// Scrolls 'Howdy' across the matrix in a portrait (vertical) orientation.

#include <Adafruit_GFX.h>
#include <Adafruit_NeoMatrix.h>
#include <Adafruit_NeoPixel.h>
#ifndef PSTR
 #define PSTR // Make Arduino Due happy
#endif

#define PIN 6

// MATRIX DECLARATION:
// Parameter 1 = width of NeoPixel matrix
// Parameter 2 = height of matrix
// Parameter 3 = pin number (most are valid)
// Parameter 4 = matrix layout flags, add together as needed:
//   NEO_MATRIX_TOP, NEO_MATRIX_BOTTOM, NEO_MATRIX_LEFT, NEO_MATRIX_RIGHT:
//     Position of the FIRST LED in the matrix; pick two, e.g.
//     NEO_MATRIX_TOP + NEO_MATRIX_LEFT for the top-left corner.
//   NEO_MATRIX_ROWS, NEO_MATRIX_COLUMNS: LEDs are arranged in horizontal
//     rows or in vertical columns, respectively; pick one or the other.
//   NEO_MATRIX_PROGRESSIVE, NEO_MATRIX_ZIGZAG: all rows/columns proceed
//     in the same order, or alternate lines reverse direction; pick one.
//   See example below for these values in action.
// Parameter 5 = pixel type flags, add together as needed:
//   NEO_KHZ800  800 KHz bitstream (most NeoPixel products w/WS2812 LEDs)
//   NEO_KHZ400  400 KHz (classic 'v1' (not v2) FLORA pixels, WS2811 drivers)
//   NEO_GRB     Pixels are wired for GRB bitstream (most NeoPixel products)
//   NEO_RGB     Pixels are wired for RGB bitstream (v1 FLORA pixels, not v2)


// Example for NeoPixel Shield.  In this application we'd like to use it
// as a 5x8 tall matrix, with the USB port positioned at the top of the
// Arduino.  When held that way, the first pixel is at the top right, and
// lines are arranged in columns, progressive order.  The shield uses
// 800 KHz (v2) pixels that expect GRB color data.
Adafruit_NeoMatrix matrix = Adafruit_NeoMatrix(5, 8, PIN,
  NEO_MATRIX_TOP     + NEO_MATRIX_LEFT +
  NEO_MATRIX_COLUMNS + NEO_MATRIX_ZIGZAG,
  NEO_GRB            + NEO_KHZ800);

const uint16_t colors[] = {
  matrix.Color(255, 0, 0), matrix.Color(0, 255, 0), matrix.Color(0, 0, 255) };

void setup() {
  matrix.begin();
  matrix.setTextWrap(false);
  matrix.setBrightness(40);
  matrix.setTextColor(colors[0]);
}

int x    = matrix.width();
int pass = 0;

void loop() {
  matrix.fillScreen(0);
  matrix.setCursor(x, 0);
  matrix.print(F("Howdy"));
  if(--x < -36) {
    x = matrix.width();
    if(++pass >= 3) pass = 0;
    matrix.setTextColor(colors[pass]);
  }
  matrix.show();
  delay(100);
}

If i flip my matrix this way it makes it long really tall without the howdy being utilized. I’ve tried rearranging the columns and top/bottom right/left etc. and if I change these it won’t even display howdy correctly. Anyway I can get around this so it displays the way I want it instead of 90 degrees to the right?

Here is a schematic on how I have my setup arranged, with the 0 neopixel leading to the arduino uno, (so it starts in the top right)

  {16, 15, 14, 13, 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 1,0},
  {17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33},
  {50, 49, 48, 47, 46, 45, 44, 43, 42, 41, 40, 39, 38, 37, 36, 35, 34},
  {51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 66, 67},
  {84, 83, 82, 81, 80, 79, 78, 77, 76, 76, 74, 73, 72, 71, 70, 69, 68},
  {85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99, 100, 101},
  {118, 117, 116, 115, 114, 113, 112, 111, 110, 109, 108, 107, 106, 105, 104, 103, 102},
  {119, 120, 121, 122, 123, 124, 125, 126, 127, 128, 129, 130, 131, 132, 133, 134, 135}

Question #2, I have made the word “SAM” on my matrix using the simple set pixels, what would be a good approach for a noob coder to shift this to the right efficiently until its off the screen or in a loop? The only way I know now would be to create “SAM” in multiple versions on my matrix with each version shifted one pixel to the right and display each one after another with a delay in between. I don’t know how to correctly do this in an multidimensional array as I think this would be done in. Here is my source code I have for creating this “SAM” in my matrix.

#include <Adafruit_NeoPixel.h>
#define PIN 6
#define N_LEDS 135

Adafruit_NeoPixel strip = Adafruit_NeoPixel(N_LEDS, PIN, NEO_GRB + NEO_KHZ800);

void setup() {
  strip.begin();
  strip.show();
}
void loop() {
  strip.setPixelColor(16, 255, 0, 0);
  strip.setPixelColor(15, 255, 0, 0);
  strip.setPixelColor(14, 255, 0, 0);
  strip.setPixelColor(17, 255, 0, 0);
  strip.setPixelColor(50, 255, 0, 0);
  strip.setPixelColor(49, 255, 0, 0);
  strip.setPixelColor(48, 255, 0, 0);
  strip.setPixelColor(53, 255, 0, 0);
  strip.setPixelColor(84, 255, 0, 0);
  strip.setPixelColor(83, 255, 0, 0);
  strip.setPixelColor(82, 255, 0, 0);
  strip.setPixelColor(79, 255, 0, 255);
  strip.setPixelColor(56, 255, 0, 255);
  strip.setPixelColor(45, 255, 0, 255);
  strip.setPixelColor(44, 255, 0, 255);  
  strip.setPixelColor(43, 255, 0, 255);
  strip.setPixelColor(22, 255, 0, 255);
  strip.setPixelColor(11, 255, 0, 255);
  strip.setPixelColor(10, 255, 0, 255);
  strip.setPixelColor(9, 255, 0, 255);
  strip.setPixelColor(24, 255, 0, 255);
  strip.setPixelColor(58, 255, 0, 255);
  strip.setPixelColor(77, 255, 0, 255);
  strip.setPixelColor(74, 0, 255, 0);
  strip.setPixelColor(61, 0, 255, 0);
  strip.setPixelColor(40, 0, 255, 0);
  strip.setPixelColor(27, 0, 255, 0);
  strip.setPixelColor(6, 0, 255, 0);
  strip.setPixelColor(28, 0, 255, 0);
  strip.setPixelColor(38, 0, 255, 0);
  strip.setPixelColor(30, 0, 255, 0);
  strip.setPixelColor(2, 0, 255, 0);
  strip.setPixelColor(31, 0, 255, 0);
  strip.setPixelColor(36, 0, 255, 0);
  strip.setPixelColor(65, 0, 255, 0);
  strip.setPixelColor(70, 0, 255, 0);
  strip.show();
}

Question 3, I am trying to wrap my head around using a 2d array but I’m having some trouble and would like some help with clarification on what i’m really doing with this other sketch code I am trying to do since I know it doesn’t work. So I think I have initialized my matrix in a new sketch as an array then I created another array that is turning on the pixels I declared that should look like “SAM” again. I don’t know how to set all the colors in the array to a certain color and how to call the function correctly. I am just trying to be efficient and wanted to create a couple functions that have words this way as I feel like it’d be more efficient than telling each pixel to light up then call them with delays in each call. What do you guys recommend and how am I supposed to do this the right way as I don’t know where to go from here. Thank you guys so much!

#include <Adafruit_NeoPixel.h>
#define PIN 6
#define N_LEDS 135

Adafruit_NeoPixel strip = Adafruit_NeoPixel(N_LEDS, PIN, NEO_GRB + NEO_KHZ800);

int matrix[8][17] = {
  {16, 15, 14, 13, 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 1,0},
  {17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33},
  {50, 49, 48, 47, 46, 45, 44, 43, 42, 41, 40, 39, 38, 37, 36, 35, 34},
  {51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 66, 67},
  {84, 83, 82, 81, 80, 79, 78, 77, 76, 76, 74, 73, 72, 71, 70, 69, 68},
  {85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97, 98, 99, 100, 101},
  {118, 117, 116, 115, 114, 113, 112, 111, 110, 109, 108, 107, 106, 105, 104, 103, 102},
  {119, 120, 121, 122, 123, 124, 125, 126, 127, 128, 129, 130, 131, 132, 133, 134, 135}
  }
}

byte SAM(){
 {1, 1, 1, 0, 0, 1, 1, 1, 0, 0, 1, 0, 0, 0, 1, 0 ,0},
 {1, 0, 0, 0, 0, 1, 0, 1, 0, 0, 1, 1, 0, 1, 1, 0, 0},
 {1, 1, 1, 0, 0, 1, 1, 1, 0, 0, 1, 0, 1, 0, 1, 0, 0},
 {0, 0, 1, 0, 0, 1, 0, 1, 0, 0, 1, 0, 0, 0, 1, 0, 0},
 {1, 1, 1, 0, 0, 1, 0, 1, 0, 0, 1, 0, 0, 0, 1, 0, 0},
 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
 {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}
 
  
}


void setup() {
  strip.begin();
  strip.show();
}
void loop() {
  strip.SAM();
  strip.show();
}-

neopixels in a zigzag pattern.

That is called a serpentine raster.

There are two ways of making a matrix like this, one is with strips on the columns, the other with the strip on the rows. This is a column matrix.
serpentine.jpg

Now the way to drive this is to write a function to translate the X and Y coordinates into the LED number.

LED number = Y + (X * number of LEDs in a column)
However for odd numbered columns the conversion is :-
LED number = (X * number of LEDs in a column) + (number of LEDs in a column -1 -Y)
To determine if the X coordinate is odd or even, simply look at the least significant bit of the X value and if it is a zero then it is an even column or if it is a one it is an odd column. So all the software has to do is to examine the X - coordinate and decide what formula to use. It is simple enough to make a function that returns the LED number given the X & Y values.

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

Where yMax is the number of LEDs in a column.

Then you can treat your matrix just like a two dimensional display. Of course if you have a row serpentine matrix or wire your matrix backwards, that is from right to left, you have to reflect that in the above function.

Now to get something to scroll you transfer the matrix defining the display you want with a one column offset into the LED buffer. This shifts the whole pattern over to the right or left depending on the sign of the offset.