Angepasstes Adafruit_Neomatrix, mit zusätzlichem Scrolltext als Effekt analog zu NeoPatterns
This commit is contained in:
parent
9275db4e3c
commit
fc4c478c30
|
@ -0,0 +1,262 @@
|
||||||
|
/*-------------------------------------------------------------------------
|
||||||
|
Arduino library to control single and tiled matrices of WS2811- and
|
||||||
|
WS2812-based RGB LED devices such as the Adafruit NeoPixel Shield or
|
||||||
|
displays assembled from NeoPixel strips, making them compatible with
|
||||||
|
the Adafruit_GFX graphics library. Requires both the Adafruit_NeoPixel
|
||||||
|
and Adafruit_GFX libraries.
|
||||||
|
|
||||||
|
Written by Phil Burgess / Paint Your Dragon for Adafruit Industries.
|
||||||
|
|
||||||
|
Adafruit invests time and resources providing this open source code,
|
||||||
|
please support Adafruit and open-source hardware by purchasing products
|
||||||
|
from Adafruit!
|
||||||
|
|
||||||
|
-------------------------------------------------------------------------
|
||||||
|
This file is part of the Adafruit NeoMatrix library.
|
||||||
|
|
||||||
|
NeoMatrix is free software: you can redistribute it and/or modify
|
||||||
|
it under the terms of the GNU Lesser General Public License as
|
||||||
|
published by the Free Software Foundation, either version 3 of
|
||||||
|
the License, or (at your option) any later version.
|
||||||
|
|
||||||
|
NeoMatrix is distributed in the hope that it will be useful,
|
||||||
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
GNU Lesser General Public License for more details.
|
||||||
|
|
||||||
|
You should have received a copy of the GNU Lesser General Public
|
||||||
|
License along with NeoMatrix. If not, see
|
||||||
|
<http://www.gnu.org/licenses/>.
|
||||||
|
-------------------------------------------------------------------------*/
|
||||||
|
|
||||||
|
#include <Adafruit_NeoPixel.h>
|
||||||
|
#include "Adafruit_NeoMatrix.h"
|
||||||
|
#include "gamma.h"
|
||||||
|
#ifdef __AVR__
|
||||||
|
#include <avr/pgmspace.h>
|
||||||
|
#elif defined(ESP8266)
|
||||||
|
#include <pgmspace.h>
|
||||||
|
#else
|
||||||
|
#ifndef pgm_read_byte
|
||||||
|
#define pgm_read_byte(addr) (*(const unsigned char *)(addr))
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#ifndef _swap_uint16_t
|
||||||
|
#define _swap_uint16_t(a, b) { uint16_t t = a; a = b; b = t; }
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// Constructor for single matrix:
|
||||||
|
Adafruit_NeoMatrix::Adafruit_NeoMatrix(int w, int h, uint8_t pin,
|
||||||
|
uint8_t matrixType, neoPixelType ledType) : Adafruit_GFX(w, h),
|
||||||
|
Adafruit_NeoPixel(w * h, pin, ledType), type(matrixType), matrixWidth(w),
|
||||||
|
matrixHeight(h), tilesX(0), tilesY(0), remapFn(NULL) { }
|
||||||
|
|
||||||
|
// Constructor for tiled matrices:
|
||||||
|
Adafruit_NeoMatrix::Adafruit_NeoMatrix(uint8_t mW, uint8_t mH, uint8_t tX,
|
||||||
|
uint8_t tY, uint8_t pin, uint8_t matrixType, neoPixelType ledType) :
|
||||||
|
Adafruit_GFX(mW * tX, mH * tY), Adafruit_NeoPixel(mW * mH * tX * tY, pin,
|
||||||
|
ledType), type(matrixType), matrixWidth(mW), matrixHeight(mH), tilesX(tX),
|
||||||
|
tilesY(tY), remapFn(NULL) { }
|
||||||
|
|
||||||
|
// Expand 16-bit input color (Adafruit_GFX colorspace) to 24-bit (NeoPixel)
|
||||||
|
// (w/gamma adjustment)
|
||||||
|
static uint32_t expandColor(uint16_t color) {
|
||||||
|
return ((uint32_t)pgm_read_byte(&gamma5[ color >> 11 ]) << 16) |
|
||||||
|
((uint32_t)pgm_read_byte(&gamma6[(color >> 5) & 0x3F]) << 8) |
|
||||||
|
pgm_read_byte(&gamma5[ color & 0x1F]);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Downgrade 24-bit color to 16-bit (add reverse gamma lookup here?)
|
||||||
|
uint16_t Adafruit_NeoMatrix::Color(uint8_t r, uint8_t g, uint8_t b) {
|
||||||
|
return ((uint16_t)(r & 0xF8) << 8) |
|
||||||
|
((uint16_t)(g & 0xFC) << 3) |
|
||||||
|
(b >> 3);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Pass-through is a kludge that lets you override the current drawing
|
||||||
|
// color with a 'raw' RGB (or RGBW) value that's issued directly to
|
||||||
|
// pixel(s), side-stepping the 16-bit color limitation of Adafruit_GFX.
|
||||||
|
// This is not without some limitations of its own -- for example, it
|
||||||
|
// won't work in conjunction with the background color feature when
|
||||||
|
// drawing text or bitmaps (you'll just get a solid rect of color),
|
||||||
|
// only 'transparent' text/bitmaps. Also, no gamma correction.
|
||||||
|
// Remember to UNSET the passthrough color immediately when done with
|
||||||
|
// it (call with no value)!
|
||||||
|
|
||||||
|
// Pass raw color value to set/enable passthrough
|
||||||
|
void Adafruit_NeoMatrix::setPassThruColor(uint32_t c) {
|
||||||
|
passThruColor = c;
|
||||||
|
passThruFlag = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Call without a value to reset (disable passthrough)
|
||||||
|
void Adafruit_NeoMatrix::setPassThruColor(void) {
|
||||||
|
passThruFlag = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Adafruit_NeoMatrix::drawPixel(int16_t x, int16_t y, uint16_t color) {
|
||||||
|
|
||||||
|
if ((x < 0) || (y < 0) || (x >= _width) || (y >= _height)) return;
|
||||||
|
|
||||||
|
int16_t t;
|
||||||
|
switch (rotation) {
|
||||||
|
case 1:
|
||||||
|
t = x;
|
||||||
|
x = WIDTH - 1 - y;
|
||||||
|
y = t;
|
||||||
|
break;
|
||||||
|
case 2:
|
||||||
|
x = WIDTH - 1 - x;
|
||||||
|
y = HEIGHT - 1 - y;
|
||||||
|
break;
|
||||||
|
case 3:
|
||||||
|
t = x;
|
||||||
|
x = y;
|
||||||
|
y = HEIGHT - 1 - t;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
int tileOffset = 0, pixelOffset;
|
||||||
|
|
||||||
|
if (remapFn) { // Custom X/Y remapping function
|
||||||
|
pixelOffset = (*remapFn)(x, y);
|
||||||
|
} else { // Standard single matrix or tiled matrices
|
||||||
|
|
||||||
|
uint8_t corner = type & NEO_MATRIX_CORNER;
|
||||||
|
uint16_t minor, major, majorScale;
|
||||||
|
|
||||||
|
if (tilesX) { // Tiled display, multiple matrices
|
||||||
|
uint16_t tile;
|
||||||
|
|
||||||
|
minor = x / matrixWidth; // Tile # X/Y; presume row major to
|
||||||
|
major = y / matrixHeight, // start (will swap later if needed)
|
||||||
|
x = x - (minor * matrixWidth); // Pixel X/Y within tile
|
||||||
|
y = y - (major * matrixHeight); // (-* is less math than modulo)
|
||||||
|
|
||||||
|
// Determine corner of entry, flip axes if needed
|
||||||
|
if (type & NEO_TILE_RIGHT) minor = tilesX - 1 - minor;
|
||||||
|
if (type & NEO_TILE_BOTTOM) major = tilesY - 1 - major;
|
||||||
|
|
||||||
|
// Determine actual major axis of tiling
|
||||||
|
if ((type & NEO_TILE_AXIS) == NEO_TILE_ROWS) {
|
||||||
|
majorScale = tilesX;
|
||||||
|
} else {
|
||||||
|
_swap_uint16_t(major, minor);
|
||||||
|
majorScale = tilesY;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Determine tile number
|
||||||
|
if ((type & NEO_TILE_SEQUENCE) == NEO_TILE_PROGRESSIVE) {
|
||||||
|
// All tiles in same order
|
||||||
|
tile = major * majorScale + minor;
|
||||||
|
} else {
|
||||||
|
// Zigzag; alternate rows change direction. On these rows,
|
||||||
|
// this also flips the starting corner of the matrix for the
|
||||||
|
// pixel math later.
|
||||||
|
if (major & 1) {
|
||||||
|
corner ^= NEO_MATRIX_CORNER;
|
||||||
|
tile = (major + 1) * majorScale - 1 - minor;
|
||||||
|
} else {
|
||||||
|
tile = major * majorScale + minor;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Index of first pixel in tile
|
||||||
|
tileOffset = tile * matrixWidth * matrixHeight;
|
||||||
|
|
||||||
|
} // else no tiling (handle as single tile)
|
||||||
|
|
||||||
|
// Find pixel number within tile
|
||||||
|
minor = x; // Presume row major to start (will swap later if needed)
|
||||||
|
major = y;
|
||||||
|
|
||||||
|
// Determine corner of entry, flip axes if needed
|
||||||
|
if (corner & NEO_MATRIX_RIGHT) minor = matrixWidth - 1 - minor;
|
||||||
|
if (corner & NEO_MATRIX_BOTTOM) major = matrixHeight - 1 - major;
|
||||||
|
|
||||||
|
// Determine actual major axis of matrix
|
||||||
|
if ((type & NEO_MATRIX_AXIS) == NEO_MATRIX_ROWS) {
|
||||||
|
majorScale = matrixWidth;
|
||||||
|
} else {
|
||||||
|
_swap_uint16_t(major, minor);
|
||||||
|
majorScale = matrixHeight;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Determine pixel number within tile/matrix
|
||||||
|
if ((type & NEO_MATRIX_SEQUENCE) == NEO_MATRIX_PROGRESSIVE) {
|
||||||
|
// All lines in same order
|
||||||
|
pixelOffset = major * majorScale + minor;
|
||||||
|
} else {
|
||||||
|
// Zigzag; alternate rows change direction.
|
||||||
|
if (major & 1) pixelOffset = (major + 1) * majorScale - 1 - minor;
|
||||||
|
else pixelOffset = major * majorScale + minor;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
setPixelColor(tileOffset + pixelOffset,
|
||||||
|
passThruFlag ? passThruColor : expandColor(color));
|
||||||
|
}
|
||||||
|
|
||||||
|
void Adafruit_NeoMatrix::fillScreen(uint16_t color) {
|
||||||
|
uint16_t i, n;
|
||||||
|
uint32_t c;
|
||||||
|
|
||||||
|
c = passThruFlag ? passThruColor : expandColor(color);
|
||||||
|
n = numPixels();
|
||||||
|
for (i = 0; i < n; i++) setPixelColor(i, c);
|
||||||
|
}
|
||||||
|
|
||||||
|
void Adafruit_NeoMatrix::setRemapFunction(uint16_t (*fn)(uint16_t, uint16_t)) {
|
||||||
|
remapFn = fn;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Adafruit_NeoMatrix::Update() {
|
||||||
|
if (active)
|
||||||
|
{
|
||||||
|
if ((millis() - lastUpdate) > Interval) // time to update
|
||||||
|
{
|
||||||
|
lastUpdate = millis();
|
||||||
|
// Next Interval step for text scroll
|
||||||
|
Serial.print(scrolltextpos);
|
||||||
|
Serial.print(" - ");
|
||||||
|
Serial.println((8 * scrolltext.length() + 10));
|
||||||
|
scrolltextpos--;
|
||||||
|
int16_t maxpos = 8 * scrolltext.length() + 10;
|
||||||
|
if (scrolltextpos < -(maxpos)) {
|
||||||
|
Serial.println();
|
||||||
|
Serial.print(scrolltextpos);
|
||||||
|
Serial.print(" is smaller than: ");
|
||||||
|
Serial.println(-(maxpos));
|
||||||
|
scrolltextpos = width();
|
||||||
|
}
|
||||||
|
fillScreen(0);
|
||||||
|
setCursor(scrolltextpos, 0);
|
||||||
|
print(scrolltext);
|
||||||
|
show();
|
||||||
|
|
||||||
|
} else {
|
||||||
|
delay(1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void Adafruit_NeoMatrix::ScrollText(String text, uint16_t interval, String color) {
|
||||||
|
Serial.print("Scrolltext triggered: ");
|
||||||
|
Serial.println(text);
|
||||||
|
active = true;
|
||||||
|
Interval = interval;
|
||||||
|
scrolltext = text;
|
||||||
|
scrolltextpos = width();
|
||||||
|
fillScreen(0);
|
||||||
|
setCursor(scrolltextpos, 0);
|
||||||
|
print(scrolltext);
|
||||||
|
if (--scrolltextpos < -(5 * scrolltext.length() + 10)) {
|
||||||
|
scrolltextpos = width();
|
||||||
|
}
|
||||||
|
show();
|
||||||
|
}
|
||||||
|
|
||||||
|
void Adafruit_NeoMatrix::None() {
|
||||||
|
active = false;
|
||||||
|
}
|
|
@ -0,0 +1,115 @@
|
||||||
|
/*--------------------------------------------------------------------
|
||||||
|
This file is part of the Adafruit NeoMatrix library.
|
||||||
|
|
||||||
|
NeoMatrix is free software: you can redistribute it and/or modify
|
||||||
|
it under the terms of the GNU Lesser General Public License as
|
||||||
|
published by the Free Software Foundation, either version 3 of
|
||||||
|
the License, or (at your option) any later version.
|
||||||
|
|
||||||
|
NeoMatrix is distributed in the hope that it will be useful,
|
||||||
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
GNU Lesser General Public License for more details.
|
||||||
|
|
||||||
|
You should have received a copy of the GNU Lesser General Public
|
||||||
|
License along with NeoMatrix. If not, see
|
||||||
|
<http://www.gnu.org/licenses/>.
|
||||||
|
--------------------------------------------------------------------*/
|
||||||
|
|
||||||
|
#ifndef _ADAFRUIT_NEOMATRIX_H_
|
||||||
|
#define _ADAFRUIT_NEOMATRIX_H_
|
||||||
|
|
||||||
|
#if ARDUINO >= 100
|
||||||
|
#include <Arduino.h>
|
||||||
|
#else
|
||||||
|
#include <WProgram.h>
|
||||||
|
#include <pins_arduino.h>
|
||||||
|
#endif
|
||||||
|
#include <Adafruit_GFX.h>
|
||||||
|
#include <Adafruit_NeoPixel.h>
|
||||||
|
|
||||||
|
// Matrix layout information is passed in the 'matrixType' parameter for
|
||||||
|
// each constructor (the parameter immediately following is the LED type
|
||||||
|
// from NeoPixel.h).
|
||||||
|
|
||||||
|
// These define the layout for a single 'unified' matrix (e.g. one made
|
||||||
|
// from NeoPixel strips, or a single NeoPixel shield), or for the pixels
|
||||||
|
// within each matrix of a tiled display (e.g. multiple NeoPixel shields).
|
||||||
|
|
||||||
|
#define NEO_MATRIX_TOP 0x00 // Pixel 0 is at top of matrix
|
||||||
|
#define NEO_MATRIX_BOTTOM 0x01 // Pixel 0 is at bottom of matrix
|
||||||
|
#define NEO_MATRIX_LEFT 0x00 // Pixel 0 is at left of matrix
|
||||||
|
#define NEO_MATRIX_RIGHT 0x02 // Pixel 0 is at right of matrix
|
||||||
|
#define NEO_MATRIX_CORNER 0x03 // Bitmask for pixel 0 matrix corner
|
||||||
|
#define NEO_MATRIX_ROWS 0x00 // Matrix is row major (horizontal)
|
||||||
|
#define NEO_MATRIX_COLUMNS 0x04 // Matrix is column major (vertical)
|
||||||
|
#define NEO_MATRIX_AXIS 0x04 // Bitmask for row/column layout
|
||||||
|
#define NEO_MATRIX_PROGRESSIVE 0x00 // Same pixel order across each line
|
||||||
|
#define NEO_MATRIX_ZIGZAG 0x08 // Pixel order reverses between lines
|
||||||
|
#define NEO_MATRIX_SEQUENCE 0x08 // Bitmask for pixel line order
|
||||||
|
|
||||||
|
// These apply only to tiled displays (multiple matrices):
|
||||||
|
|
||||||
|
#define NEO_TILE_TOP 0x00 // First tile is at top of matrix
|
||||||
|
#define NEO_TILE_BOTTOM 0x10 // First tile is at bottom of matrix
|
||||||
|
#define NEO_TILE_LEFT 0x00 // First tile is at left of matrix
|
||||||
|
#define NEO_TILE_RIGHT 0x20 // First tile is at right of matrix
|
||||||
|
#define NEO_TILE_CORNER 0x30 // Bitmask for first tile corner
|
||||||
|
#define NEO_TILE_ROWS 0x00 // Tiles ordered in rows
|
||||||
|
#define NEO_TILE_COLUMNS 0x40 // Tiles ordered in columns
|
||||||
|
#define NEO_TILE_AXIS 0x40 // Bitmask for tile H/V orientation
|
||||||
|
#define NEO_TILE_PROGRESSIVE 0x00 // Same tile order across each line
|
||||||
|
#define NEO_TILE_ZIGZAG 0x80 // Tile order reverses between lines
|
||||||
|
#define NEO_TILE_SEQUENCE 0x80 // Bitmask for tile line order
|
||||||
|
|
||||||
|
class Adafruit_NeoMatrix : public Adafruit_GFX, public Adafruit_NeoPixel {
|
||||||
|
|
||||||
|
public:
|
||||||
|
|
||||||
|
// Constructor for single matrix:
|
||||||
|
Adafruit_NeoMatrix(int w, int h, uint8_t pin = 6,
|
||||||
|
uint8_t matrixType = NEO_MATRIX_TOP + NEO_MATRIX_LEFT + NEO_MATRIX_ROWS,
|
||||||
|
neoPixelType ledType = NEO_GRB + NEO_KHZ800);
|
||||||
|
|
||||||
|
// Constructor for tiled matrices:
|
||||||
|
Adafruit_NeoMatrix(uint8_t matrixW, uint8_t matrixH, uint8_t tX,
|
||||||
|
uint8_t tY, uint8_t pin = 6,
|
||||||
|
uint8_t matrixType = NEO_MATRIX_TOP + NEO_MATRIX_LEFT + NEO_MATRIX_ROWS +
|
||||||
|
NEO_TILE_TOP + NEO_TILE_LEFT + NEO_TILE_ROWS,
|
||||||
|
neoPixelType ledType = NEO_GRB + NEO_KHZ800);
|
||||||
|
|
||||||
|
void
|
||||||
|
drawPixel(int16_t x, int16_t y, uint16_t color),
|
||||||
|
fillScreen(uint16_t color),
|
||||||
|
setPassThruColor(uint32_t c),
|
||||||
|
setPassThruColor(void),
|
||||||
|
setRemapFunction(uint16_t (*fn)(uint16_t, uint16_t)),
|
||||||
|
Update(),
|
||||||
|
None(),
|
||||||
|
ScrollText(String text, uint16_t Interval = 60, String color);
|
||||||
|
|
||||||
|
static uint16_t
|
||||||
|
Color(uint8_t r, uint8_t g, uint8_t b);
|
||||||
|
|
||||||
|
boolean active = false;
|
||||||
|
|
||||||
|
private:
|
||||||
|
|
||||||
|
const uint8_t
|
||||||
|
type;
|
||||||
|
const uint8_t
|
||||||
|
matrixWidth, matrixHeight, tilesX, tilesY;
|
||||||
|
uint16_t
|
||||||
|
(*remapFn)(uint16_t x, uint16_t y);
|
||||||
|
|
||||||
|
uint32_t passThruColor;
|
||||||
|
boolean passThruFlag = false;
|
||||||
|
String scrolltext;
|
||||||
|
int16_t scrolltextpos;
|
||||||
|
|
||||||
|
uint16_t Interval; // milliseconds between updates
|
||||||
|
uint16_t lastUpdate; // last update of position
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif // _ADAFRUIT_NEOMATRIX_H_
|
|
@ -0,0 +1,30 @@
|
||||||
|
#ifndef _GAMMA_H_
|
||||||
|
#define _GAMMA_H_
|
||||||
|
|
||||||
|
#ifdef __AVR
|
||||||
|
#include <avr/pgmspace.h>
|
||||||
|
#elif defined(ESP8266)
|
||||||
|
#include <pgmspace.h>
|
||||||
|
#else
|
||||||
|
#ifndef PROGMEM
|
||||||
|
#define PROGMEM
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
|
||||||
|
static const uint8_t PROGMEM
|
||||||
|
gamma5[] = {
|
||||||
|
0x00,0x01,0x02,0x03,0x05,0x07,0x09,0x0b,
|
||||||
|
0x0e,0x11,0x14,0x18,0x1d,0x22,0x28,0x2e,
|
||||||
|
0x36,0x3d,0x46,0x4f,0x59,0x64,0x6f,0x7c,
|
||||||
|
0x89,0x97,0xa6,0xb6,0xc7,0xd9,0xeb,0xff },
|
||||||
|
gamma6[] = {
|
||||||
|
0x00,0x01,0x02,0x03,0x04,0x05,0x06,0x08,
|
||||||
|
0x09,0x0a,0x0b,0x0d,0x0e,0x10,0x12,0x13,
|
||||||
|
0x15,0x17,0x19,0x1b,0x1d,0x20,0x22,0x25,
|
||||||
|
0x27,0x2a,0x2d,0x30,0x33,0x37,0x3a,0x3e,
|
||||||
|
0x41,0x45,0x49,0x4d,0x52,0x56,0x5b,0x5f,
|
||||||
|
0x64,0x69,0x6e,0x74,0x79,0x7f,0x85,0x8b,
|
||||||
|
0x91,0x97,0x9d,0xa4,0xab,0xb2,0xb9,0xc0,
|
||||||
|
0xc7,0xcf,0xd6,0xde,0xe6,0xee,0xf7,0xff };
|
||||||
|
|
||||||
|
#endif // _GAMMA_H_
|
Loading…
Reference in New Issue