AaronLiddiment / LEDText

FastLED Flexible Text Message Class requires LEDMatrix Class
89 stars 32 forks source link

Way to have text scroll across two matrix? #27

Open CobaltEcho opened 2 years ago

CobaltEcho commented 2 years ago

Is there a way to have text scroll from one screen to another? I've looked at the LEDMatrix example where it calls out:

FastLED.addLeds<CHIPSET, 9, COLOR_ORDER>(leds[0], 0, NUM_LEDS_PER_STRIP); 
FastLED.addLeds<CHIPSET, 9, COLOR_ORDER>(leds[0], NUM_LEDS_PER_STRIP, NUM_LEDS_PER_STRIP); 

and so on. It looks like this sets it up as one giant matrix (which I'm ok with as long as I can get my text to scroll from one screen to the other).

I see that FASTLed has it set up as:

FastLED.addLeds<CHIPSET, PIN>(leds[0], NUM_LEDS_PER_STRIP);
FastLED.addLeds<CHIPSET, PIN>(leds[1], NUM_LEDS_PER_STRIP);
called as:
leds[x][i] = CRGB::Red;  //  x=led strip

But can't seem to get the [x][i] method to work in LEDText

I've tried playing with the matrix width and number of LED's per strip, but it ends up scrambled (probably due to the LED numbering being off).

Any ideas on this one? Thanks again!

Pic of screen setup: ScreenSetup

AaronLiddiment commented 2 years ago

If they had been vertical matrix it would have been easy! The easiest way it to declare 2 cLEDMatrix arrays: cLEDMatrix<MATRIX_WIDTH, MATRIX_HEIGHT, MATRIX_TYPE> leds1; cLEDMatrix<MATRIX_WIDTH, MATRIX_HEIGHT, MATRIX_TYPE> leds2; And to setup the 2 Fastleds: FastLED.addLeds<CHIPSET, 10>(leds1[0], leds1.Size()); FastLED.addLeds<CHIPSET, 9>(leds2[0], leds2.Size()); Then you need to setup 2 cLEDTexts for each of the cLEDMatrix's: cLEDText Msg1; cLEDText Msg2; Msg1.Init(&leds1, leds1.Width(), leds1.Height() + 1, 0, 0); Msg1.SetText((unsigned char *)TxtDemo, sizeof(TxtDemo) - 1); Msg2.Init(&leds2, leds2.Width(), leds2.Height() + 1, 0, 0); Msg2.SetText((unsigned char *)TxtDemo, sizeof(TxtDemo) - 1); So you are setting the same text message to both displays but we are going to call UpdateText() on the left most display 14 times to advance it ahead of the right most display: for (int i=0; i<14; i++) Msg1.UpdateText(); Then in your loop you need to update both the Msg's at the same time.

You are still using [] brackets and also using 2 dimensions on a single dimension array so you LED assignment will not work, use: leds1(0) = CRGB::Red to set the first led of the left matrix Red leds2(0) = CRGB::Blue to set the first led of the right matrix Blue

CobaltEcho commented 2 years ago

Got it! Don't worry, I can't do anything easy :p

Once again, appreciate your help!

On Mon, Dec 6, 2021, 5:23 PM Aaron Liddiment @.***> wrote:

If they had been vertical matrix it would have been easy! The easiest way it to declare 2 cLEDMatrix arrays: cLEDMatrix<MATRIX_WIDTH, MATRIX_HEIGHT, MATRIX_TYPE> leds1; cLEDMatrix<MATRIX_WIDTH, MATRIX_HEIGHT, MATRIX_TYPE> leds2; And to setup the 2 Fastleds: FastLED.addLeds<CHIPSET, 10>(leds1[0], leds1.Size()); FastLED.addLeds<CHIPSET, 9>(leds2[0], leds2.Size()); Then you need to setup 2 cLEDTexts for each of the cLEDMatrix's: cLEDText Msg1; cLEDText Msg2; Msg1.Init(&leds1, leds1.Width(), leds1.Height() + 1, 0, 0); Msg1.SetText((unsigned char )TxtDemo, sizeof(TxtDemo) - 1); Msg2.Init(&leds2, leds2.Width(), leds2.Height() + 1, 0, 0); Msg2.SetText((unsigned char )TxtDemo, sizeof(TxtDemo) - 1); So you are setting the same text message to both displays but we are going to call UpdateText() on the left most display 14 times to advance it ahead of the right most display: for (int i=0; i<14; i++) Msg1.UpdateText(); Then in your loop you need to update both the Msg's at the same time.

You are still using [] brackets and also using 2 dimensions on a single dimension array so you LED assignment will not work, use: leds1(0) = CRGB::Red to set the first led of the left matrix Red leds2(0) = CRGB::Blue to set the first led of the right matrix Blue

— You are receiving this because you authored the thread. Reply to this email directly, view it on GitHub https://github.com/AaronLiddiment/LEDText/issues/27#issuecomment-987295359, or unsubscribe https://github.com/notifications/unsubscribe-auth/AGH7JKT3SCRNJM5PI4AXJD3UPUZUNANCNFSM5JPGECGQ . Triage notifications on the go with GitHub Mobile for iOS https://apps.apple.com/app/apple-store/id1477376905?ct=notification-email&mt=8&pt=524675 or Android https://play.google.com/store/apps/details?id=com.github.android&referrer=utm_campaign%3Dnotification-email%26utm_medium%3Demail%26utm_source%3Dgithub.

CobaltEcho commented 2 years ago

As far as using the [x] brackets, I just typed the code for these examples and didn't catch it, I have the correct (x) brackets in my real code.

CobaltEcho commented 2 years ago

Incase someone in the future is trying to do this...

//Nano Every - megaAVR - ATMega4809

#include <FastLED.h>
#include <LEDMatrix.h>
#include <FontMatrise.h>
#include <LEDText.h>

const uint8_t DisplayWidth = 14;
const uint8_t DisplayHeight = 10;
const uint8_t NumLeds = DisplayWidth * DisplayHeight;

uint8_t Brightness = 100;

//---------------------cLEDMatrix and Text --------------------

//cLEDMatrix < DisplayWidth, -DisplayHeight, HORIZONTAL_ZIGZAG_MATRIX > leds;
cLEDMatrix < DisplayWidth, -DisplayHeight, HORIZONTAL_ZIGZAG_MATRIX > ledsL;  //Screen/Matrix on Left
cLEDMatrix < DisplayWidth, -DisplayHeight, HORIZONTAL_ZIGZAG_MATRIX > ledsR;  //Screen/Matrix on Right

cLEDText ScreenL;
cLEDText ScreenR;

const unsigned char MsgText[] = {
  EFFECT_FRAME_RATE "\x01"                  //setting fram rate
  EFFECT_SCROLL_LEFT                        //Setting scroll direction
  EFFECT_HSV_CV "\x00\xff\xff\x40\xff\xff"  //setting color
  "  I AM TEXT"                           //Text to show
};

const uint16_t FrameRate = 2;  //This should be whatever your EFFECT_FRAME_RATE is + 1.  Needed in order to make sure the second screen is advanced the correct pixels.

//---------------------SETUP--------------------
void setup() {
  //Setting up two seperate screens so text can scroll from one to the other
  FastLED.addLeds<WS2812B, 9, GRB>(ledsL[0], ledsL.Size()).setCorrection(TypicalLEDStrip);  //Screen on the left
  FastLED.addLeds<WS2812B, 10, GRB>(ledsR[0], ledsR.Size()).setCorrection(TypicalLEDStrip);  //Screen on the right

  FastLED.setBrightness(Brightness);  //Set Default brightness of LEDs

  FastLED.clear(true);  //Pushes the clear out to the LED's in case you restarted the Arduino and LED's are still on.

  ScreenL.SetFont(MatriseFontData);  //Left Screen/Matrix
  ScreenL.Init(&ledsL, ledsL.Width(), ledsL.Height() + 1, 0, 0);
  ScreenL.SetText((unsigned char *)MsgText, sizeof(MsgText) - 1);

  ScreenR.SetFont(MatriseFontData);  //Right Screen/Matrix
  ScreenR.Init(&ledsR, ledsR.Width(), ledsR.Height() + 1, 0, 0);
  ScreenR.SetText((unsigned char *)MsgText, sizeof(MsgText) - 1);
  for (int i = 0; i < (DisplayWidth * FrameRate); i++) //Move the text forward on the screen on the right before showing in loop
    ScreenR.UpdateText();

  ScreenTest();

}

//---------------------Screen Test--------------------
void ScreenTest(){
  for (int i = 0; i < NumLeds; i++){
    ledsL(i) = CRGB::Red;
    ledsR(i) = CRGB::Blue;
  }
  FastLED.show();
  MilliDelay(2000);
  FastLED.clear();
}

//---------------------Loop--------------------
void loop() {
  DisplayText();
  MilliDelay(10);
}

//---------------------Display Text Funtion--------------------
void DisplayText() {
  if (ScreenL.UpdateText() == -1)
    ScreenL.SetText((unsigned char *)MsgText, sizeof(MsgText) - 1);
  else
    FastLED.show();

  if (ScreenR.UpdateText() == -1) {
    ScreenR.SetText((unsigned char *)MsgText, sizeof(MsgText) - 1);
  }
  else
    FastLED.show();
}

//---------------------MilliDelay - Fixes some interupt issues from using regular delay.
void MilliDelay(int DelayTime) {
  unsigned long time_now = millis();
  while (millis() < time_now + DelayTime) {}
}
CobaltEcho commented 2 years ago

@AaronLiddiment Above you'll see that I got the text to scroll across two different matrix's by using ledsR and ledsL on the setup.

This works great, but do you know a way to set it up where I could use the screens independently and in parallel, depending on the situation?

Preferably without having to do ledsR(x) ledsL(x)

This seems OK until you address each led (140x2) individually and 140 lines turns into 280.

AaronLiddiment commented 2 years ago

An alternative way to handle your dual displays would be to declare another LEDMatrix that covers both displays. You could then use this Matrix class when you want the displays as one and still use the seperate Left & Right ones when using them independantly. You would find using text on the single display much easier in this case but would need to add a copy function to extract the Led data from the single Matrix to the seperate Left & Right ones after each update. cLEDMatrix < DisplayWidth * 2, -DisplayHeight, HORIZONTAL_ZIGZAG_MATRIX > ledsSingle for (int h=0; h<ledsSingle.Height(); h+=2) { memcpy(ledsL[h * ledsL.Width()], ledsSingle[h * ledsSingle.Width()], ledsL.Width() * sizeof(CRGB)); memcpy(ledsR[h * ledsR.Width()], ledsSingle[ledsL.Width() + (h * ledsSingle.Width())], ledsR.Width() * 2 * sizeof(CRGB)); memcpy(ledsL[(h + 1) * ledsL.Width()], ledsSingle[ledsR.Width() + ((h + 1) * ledsSingle.Width())], ledsL.Width() * sizeof(CRGB)); }

You would then use the ledsSingle Matrix with the cLEDText class and after any updates are finished you would need to use the for loop code above to copy over the updated CRGB data to the Left & Right displays that FastLed is using.