Led Matrix Sequencer single row nonfunctional

I’m making my first real project with my custom shield I made, see it in exhibition.

I’m making a 16 step musical sequencer that has a combination of 4 drum noises and 4 notes.
So far, I’m just working on making it play the audio (no interactivity yet), which it does fine, but the display does not function correctly.
I tried to program it in a way that the arrays for the beat and for the music directly affect the display, and it works well, except for one little thing. The fifth row from the top, the one for the note C4, does not display.

It should show a scanning red line, the playhead, and it should also show a green dot representing a note.
The top four lines are the drum tracks, the bottom four are the tones.
I’ve been puzzled for a while now, and I have no clue!
Here is the code, with only the parts related to the display: (I’ve ensured that the problem still remains, and that the row is functional.):

#include <Tone.h>



const int clockPin = 2;
const int dataPin = 3;
const int latch1 = 4;
const int latch2 = 5;
#define PAUSE 0
#define BASS 1
#define SNARE 2
#define HHATC 3
#define HHATO 4
int beat[16] = {
  BASS, HHATC, HHATC, HHATC,
  SNARE, PAUSE, BASS, HHATC,
  HHATC, HHATC, BASS, PAUSE,
  SNARE, BASS, HHATO, PAUSE
};

#define REST 99
int music[16] = {
  NOTE_C3, NOTE_C3, NOTE_C3, NOTE_C3,
  NOTE_C4, REST, NOTE_DS3, NOTE_DS3,
  NOTE_DS3, NOTE_C3, NOTE_G3, REST,
  NOTE_C4, NOTE_C4, NOTE_C4, REST
};
int row=0;
byte redCol1;
byte greenCol1;
byte redCol2;
byte greenCol2;
int tempo = 125;
int position;

void setup()  {

  randomSeed(analogRead(0));
  position = 0;

  for(int i = 2; i<=5; i++)   {
    pinMode(i, OUTPUT);
  }
  Serial.begin(9600);
}

void loop()  {
  unsigned long time = millis();
  while(millis() - time <= tempo)  {
    allStep(position, time);
  }

  if(position < 15)  {
    position++;
  }
  else  {
    position = 0;
  }

}

void allStep(int position, unsigned long startTime)  {
  //silencer(position);
  //snareStep(position, startTime);
  //bassStep(position);
  //hhcStep(position, startTime);
  //hhoStep(position, startTime);
  //leadStep(position);
  displayStep(position);
  //etc...
}

void displayStep(int position)  {
  //row byte generator
  row++;
  if(row==8)  {
    row=0;
  }
  byte rowByte = 1 << row;
  //red byte generator
  if(position <= 7)  {
    redCol1 = B10000000 >> position;
    redCol2 = B00000000;
  }
  else if(position >= 8)  {
    redCol2 = B10000000 >> (position - 8);
    redCol1 = B00000000;
  }
  //green byte generator
byte rowNote=0;
  switch(row)  {
  case 7:
    rowNote = NOTE_C3;
    break;
  case 6:
    rowNote = NOTE_DS3;
    break;
  case 5:
    rowNote = NOTE_G3;
    break;
  case 4:
    rowNote = NOTE_C4;
    break;
  }
  
           //matrix1
  greenCol1 = 0;
  for(int i = 0; i <=7; i++)  {
    if(row+1 == beat[i])  {
      greenCol1 = greenCol1 | B10000000 >> i;
    }
  }

  for(int i = 0; i <=7; i++)  {
    if(rowNote == music[i])  {
      greenCol1 = greenCol1 | B10000000 >> i;
    }
  }
            //matrix2
  greenCol2 = 0;
  for(int i = 0; i <=7; i++)  {
    if(row+1 == beat[i+8])  {
      greenCol2 = greenCol2 | B10000000 >> i;
    }
  }

  for(int i = 0; i <=7; i++)  {
    if(rowNote == music[i+8])  {
      greenCol2 = greenCol2 | B10000000 >> i;
    }
  }



  digitalWrite(latch1, LOW);
  shiftSwap(rowByte, MSBFIRST);
  shiftSwap(greenCol1, LSBFIRST);
  shiftSwap(redCol1, LSBFIRST);
  digitalWrite(latch1, HIGH);
  digitalWrite(latch2, LOW);
  shiftSwap(rowByte, MSBFIRST);
  shiftSwap(greenCol2, LSBFIRST);
  shiftSwap(redCol2, LSBFIRST);
  digitalWrite(latch2, HIGH);
}

//============================Misc Functions=========================

void shiftSwap(byte value, int byteOrder)  {
  byte newByte = ((value << 4) & 0xf0) | ((value >> 4) & 0x0f);
  shiftOut(dataPin, clockPin, byteOrder, newByte);
}

Sorry if this is not enough info, I can include more if needed.

Thanks!
:slight_smile:
[edit]Edit: I realized I had some extra stuff in the code that caused it not to compile. Fixed! (Well, the row still doesn’t work, so not really fixed.)[/edit]

Okay, I think I’ve narrowed the problem down.

Some facts I found:
The problem still exists if I comment out the code for the red line.
The problem still exists if I comment out the code for the display of the drum part. ( and the beat array and constants for it)
If I replace “greenCol1” and “greenCol2” in the shiftSwap functions with a byte (Bxxxxxxxx) it displays the proper thing on all rows.
If I change the case values in the switch(row) to other rows, the new row for the note C4 still doesn’t light, no matter which row I choose.

So after omissions all that is left is

#include <Tone.h>


const int clockPin = 2;
const int dataPin = 3;
const int latch1 = 4;
const int latch2 = 5;


#define REST 99
int music[16] = {
  NOTE_C3, NOTE_C3, NOTE_C3, NOTE_C3,
  NOTE_C4, REST, NOTE_DS3, NOTE_DS3,
  NOTE_DS3, NOTE_C3, NOTE_G3, REST,
  NOTE_C4, NOTE_C4, NOTE_C4, REST
};
int row=0;
byte redCol1;
byte greenCol1;
byte redCol2;
byte greenCol2;
int tempo = 125;
int position;

void setup()  {

  randomSeed(analogRead(0));
  position = 0;

  for(int i = 2; i<=5; i++)   {
    pinMode(i, OUTPUT);
  }
  Serial.begin(9600);
}

void loop()  {
  unsigned long time = millis();
  while(millis() - time <= tempo)  {
    allStep(position, time);
  }

  if(position < 15)  {
    position++;
  }
  else  {
    position = 0;
  }

}

void allStep(int position, unsigned long startTime)  {
  displayStep(position);

}

void displayStep(int position)  {
  //row byte generator
  row++;
  if(row==8)  {
    row=0;
  }
  byte rowByte = 1 << row;
  //red byte generator

  //green byte generator
byte rowNote=0;
  [glow]switch(row)  {
  case 7:
    rowNote = NOTE_C3;
    break;
  case 6:
    rowNote = NOTE_DS3;
    break;
  case 5:
    rowNote = NOTE_G3;
    break;
  case 4:
    rowNote = NOTE_C4;
    break;
  }[/glow]
  
           //matrix1
  greenCol1 = 0;

  [glow]for(int i = 0; i <=7; i++)  {
    if(rowNote == music[i])  {
      greenCol1 = greenCol1 | B10000000 >> i;
    }
  }[/glow]
            //matrix2
  greenCol2 = 0;
  [glow]for(int i = 0; i <=7; i++)  {
    if(rowNote == music[i+8])  {
      greenCol2 = greenCol2 | B10000000 >> i;
    }
  }
[/glow]


  digitalWrite(latch1, LOW);
  shiftSwap(rowByte, MSBFIRST);
  shiftSwap(greenCol1, LSBFIRST);
  shiftSwap(redCol1, LSBFIRST);
  digitalWrite(latch1, HIGH);
  digitalWrite(latch2, LOW);
  shiftSwap(rowByte, MSBFIRST);
  shiftSwap(greenCol2, LSBFIRST);
  shiftSwap(redCol2, LSBFIRST);
  digitalWrite(latch2, HIGH);
}

//============================Misc Functions=========================

void shiftSwap(byte value, int byteOrder)  {
  byte newByte = ((value << 4) & 0xf0) | ((value >> 4) & 0x0f);
  shiftOut(dataPin, clockPin, byteOrder, newByte);
}

I’m pretty sure that the problem is in the highlighted sections, but I could be wrong.

But I’m still puzzled!!!
:-?

[edit]Edit:
I think I have taken away any extra stuff in the code that is not necessary to display the music. BUT THE 5TH ROW (the one for the note C4) STILL DOESN"T WORK!!!
Here’s the bare-bones code, hopefully it is easier to spot the error now.

#include <Tone.h>


const int clockPin = 2;
const int dataPin = 3;
const int latch1 = 4;
const int latch2 = 5;


#define REST 99
int music[16] = {
  NOTE_C3, NOTE_C3, NOTE_C3, NOTE_C3,
  NOTE_C4, REST, NOTE_DS3, NOTE_DS3,
  NOTE_DS3, NOTE_C3, NOTE_G3, REST,
  NOTE_C4, NOTE_C4, NOTE_C4, REST
};
int row=0;
byte greenCol1;
byte greenCol2;

void setup()  {

  for(int i = 2; i<=5; i++)   {
    pinMode(i, OUTPUT);
  }
  Serial.begin(9600);
}

void loop()  {
    displayStep();
}



void displayStep()  {
  //row byte generator
  row++;
  if(row==8)  {
    row=0;
  }
  byte rowByte = 1 << row;

  //green byte generator
byte rowNote=0;
  switch(row)  {
  case 7:
    rowNote = NOTE_C3;
    break;
  case 6:
    rowNote = NOTE_DS3;
    break;
  case 5:
    rowNote = NOTE_G3;
    break;
  case 4:
    rowNote = NOTE_C4;
    break;
  }
  
           //matrix1
  greenCol1 = 0;
  for(int i = 0; i <=7; i++)  {
    if(rowNote == music[i])  {
      greenCol1 = greenCol1 | B10000000 >> i;
    }
  }
            //matrix2
  greenCol2 = 0;
  for(int i = 0; i <=7; i++)  {
    if(rowNote == music[i+8])  {
      greenCol2 = greenCol2 | B10000000 >> i;
    }
  }



  digitalWrite(latch1, LOW);
  shiftSwap(rowByte, MSBFIRST);
  shiftSwap(greenCol1, LSBFIRST);
  shiftSwap(0, LSBFIRST);
  digitalWrite(latch1, HIGH);
  digitalWrite(latch2, LOW);
  shiftSwap(rowByte, MSBFIRST);
  shiftSwap(greenCol2, LSBFIRST);
  shiftSwap(0, LSBFIRST);
  digitalWrite(latch2, HIGH);
}

//============================Misc Functions=========================

void shiftSwap(byte value, int byteOrder)  {
  byte newByte = ((value << 4) & 0xf0) | ((value >> 4) & 0x0f);
  shiftOut(dataPin, clockPin, byteOrder, newByte);
}

[/edit]

greenCol1 = greenCol1 | B10000000 >> i;

Operator priority isn't always obvious in C, so I'd recommend

greenCol1 = greenCol1 | (B10000000 >> i);

(this time the default priority got it right though).

Your real problem is this, from Tone.h:

#define NOTE_C4  262

You music array stores ints but your 'rownote' variable is a little byte that can't hold 262.

Wow, thanks!

That makes perfect sense, just something I overlooked.