Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Dependencies: mbed miniFont wsDrive
Revision 0:bada179a0b70, committed 2014-11-06
- Comitter:
- AndyA
- Date:
- Thu Nov 06 13:55:51 2014 +0000
- Child:
- 1:2014f027ed6f
- Commit message:
- First commit;
Changed in this revision
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/main.cpp Thu Nov 06 13:55:51 2014 +0000
@@ -0,0 +1,286 @@
+#include "mbed.h"
+#include "wsDrive.h"
+#include "miniFont.h"
+
+#define updatePeriodMS 2000
+
+
+/*
+LED config - Assume all LEDs are in one logical chain of len*count leds.
+Physical layout is:
+
+ChainLen = 4, ChainCount = 2, cascadeZigZag undefined
+
+ D1 -> D2 -> D3 -> D4
+ D5 -> D6 -> D7 -> D8
+
+ChainLen = 4, ChainCount = 3, cascadeZigZag defined
+
+ D1 -> D2 -> D3 -> D4
+ D8 <- D7 <- D6 <- D5
+ D9 -> D10 -> D11 -> D12
+
+Text will use the top 5 rows. Text displayed on a chainCount of < 5 will be trimmed.
+Letters are generally 5 pixels wide, numbers and punctuation are 5 or less.
+The default is for a 1 pixel gap between characters so you will need 6 leds per letter displayed.
+
+System uses two buffers, one for that data to display, one to calculate the next data.
+This allows shifts in either direction without overwriting values we haven't used yet.
+Rather than do lots of copying each frame we toggle between which one is being displayed
+and which calculated.
+
+*/
+
+// LED config options:
+
+//#define cascadeZigZag
+
+#define chainLen 35
+#define chainCount 5
+
+// IO setup - currently set for mbuino.
+
+DigitalIn dummy(P0_21,PullDown);
+wsDrive ledDriver(P0_21,P0_22,P1_15);
+DigitalIn progMode(P0_3,PullDown);
+BusOut LEDs(LED1, LED2, LED3, LED4, LED5, LED6, LED7);
+
+
+// globals
+
+miniFont pixelText;
+
+Timer updateRateTimer;
+
+pixelInfo pixelData1[chainLen * chainCount];
+pixelInfo pixelData2[chainLen * chainCount];
+pixelInfo *livePixels;
+pixelInfo *nextPixels;
+
+
+
+inline uint16_t xy2index(uint16_t x, uint16_t y)
+{
+ if (x >= chainLen)
+ x = 0;
+ if (y >= chainCount)
+ y =0;
+#ifdef cascadeZigZag
+ if (y%2)
+ return (y+1)*chainLen - x - 1;
+ else
+ return y*chainLen + x;
+#else
+ return y*chainLen + x;
+#endif
+}
+
+
+void blankBuffer(pixelInfo *Ptr)
+{
+ memset( (void *) Ptr, 00, sizeof(pixelInfo)*chainCount*chainLen );
+}
+
+
+void initColour(pixelInfo *colour)
+{
+ for (int i = 0; i<(chainLen * chainCount); i++) {
+ nextPixels[i].R = colour->R;
+ nextPixels[i].G = colour->G;
+ nextPixels[i].B = colour->B;
+ }
+}
+
+
+uint16_t initText(const char *text, pixelInfo colour, int16_t startPixel = 0, int16_t startRow = 0)
+{
+
+ uint8_t charIndex = 0;
+ uint8_t thisWidth;
+ uint8_t thisHeight;
+ uint16_t pixelY;
+ uint16_t pixelX;
+ uint16_t thisPixIndex;
+ const char *charData;
+
+
+ if (startRow >= chainCount)
+ return startPixel;
+
+ while (*(text+charIndex)) {
+
+
+ if (startPixel >= chainLen)
+ return chainLen;
+
+ thisHeight = pixelText.getPixHeight(*(text+charIndex));
+ thisWidth = pixelText.getPixWidth(*(text+charIndex));
+
+ if (pixelText.getChar(*(text+charIndex),&charData)) {
+
+ if ((startPixel + thisWidth) > chainLen)
+ thisWidth = chainLen - startPixel;
+
+ for (uint8_t row = 0; row < thisHeight; row++) {
+
+ pixelY = row + startRow;
+ if (pixelY >= chainCount)
+ break;
+
+ for (int16_t col = 0; col < thisWidth; col++) {
+ pixelX = startPixel + col;
+ if (pixelX >= chainLen)
+ break;
+
+ thisPixIndex = xy2index(pixelX,pixelY);
+
+ if (*(charData+row) & (1<<(thisWidth-col-1)) ) {
+ nextPixels[thisPixIndex].R = colour.R;
+ nextPixels[thisPixIndex].G = colour.G;
+ nextPixels[thisPixIndex].B = colour.B;
+ }
+
+ } // end for col
+ } //end for each row
+ } // end if we got data for that character
+ startPixel += thisWidth + 1;
+ charIndex++;
+ } // end while characters left
+ return startPixel;
+}
+
+void initChain ()
+{
+ pixelInfo textColour;
+
+ // optionally use initColour to set a background colour
+
+ // set text colour
+ textColour.R = 0x30;
+ textColour.G = 0x30;
+ textColour.B = 0x00;
+
+ // add text keeping the index for the next character.
+ uint16_t nextChar = initText("H", textColour);
+
+
+ // change the colour
+ textColour.R = 0x10;
+ textColour.G = 0x10;
+ textColour.B = 0x30;
+ // add more text.
+ nextChar = initText("ell", textColour, nextChar);
+
+
+ // one more colour
+ textColour.R = 0x40;
+ textColour.G = 0x00;
+ textColour.B = 0x00;
+ // and a final letter.
+ initText("0", textColour, nextChar);
+
+}
+
+
+// in theory lets you rotate red green and blue independantly an arbitary number of places in either direction.
+// not well tested.
+void rotateChain (int redStep, int greenStep, int blueStep)
+{
+ while (redStep < 0)
+ redStep += chainLen;
+
+ while (greenStep < 0)
+ greenStep += chainLen;
+
+ while (blueStep < 0)
+ blueStep += chainLen;
+
+ uint16_t thisPixIndex;
+ uint16_t redPixIndex;
+ uint16_t bluePixIndex;
+ uint16_t greenPixIndex;
+
+ for (uint16_t col = 0; col<chainLen; col++) {
+ for (uint8_t row = 0; row < chainCount; row++) {
+
+#ifdef cascadeZigZag
+ if (row % 2) {
+ thisPixIndex = chainLen - col - 1 + row*chainLen;
+ redPixIndex = chainLen - redStep - 1 + row*chainLen;
+ greenPixIndex = chainLen - greenStep - 1 + row*chainLen;
+ bluePixIndex = chainLen - blueStep - 1 + row*chainLen;
+ } else
+#endif
+ {
+ thisPixIndex = col + row*chainLen;
+ redPixIndex = redStep + row*chainLen;
+ greenPixIndex = greenStep + row*chainLen;
+ bluePixIndex = blueStep + row*chainLen;
+ }
+
+ nextPixels[thisPixIndex].R = livePixels[redPixIndex].R;
+ nextPixels[thisPixIndex].G = livePixels[greenPixIndex].G;
+ nextPixels[thisPixIndex].B = livePixels[bluePixIndex].B;
+ }
+ redStep = (redStep+1) % chainLen;
+ greenStep = (greenStep+1) % chainLen;
+ blueStep = (blueStep+1) % chainLen;
+ }
+}
+
+void rotateChain (int stepsLeft)
+{
+ rotateChain(stepsLeft,stepsLeft,stepsLeft);
+}
+
+
+void swapBuffer()
+{
+ pixelInfo *tmpPtr = nextPixels;
+ nextPixels = livePixels;
+ livePixels = tmpPtr;
+}
+
+
+int main ()
+{
+ LEDs = 1;
+
+// setup buffers
+ livePixels = pixelData1;
+ nextPixels = pixelData2;
+
+ blankBuffer(livePixels);
+ blankBuffer(nextPixels);
+
+ ledDriver.setData(livePixels, chainLen*chainCount);
+ LEDs = LEDs+1;
+
+// create the data to display
+ initChain();
+ LEDs = LEDs+1;
+
+// set the active buffer to be displayed.
+ swapBuffer();
+ LEDs = LEDs+1;
+
+ updateRateTimer.start();
+ while (true) {
+
+ // update which buffer to use.
+ ledDriver.setData(livePixels, chainLen*chainCount);
+ // send the data
+ ledDriver.sendData();
+
+ LEDs = LEDs + 1;
+
+ // Copy move everthing to the left
+ rotateChain(1);
+
+ // change which buffer to use.
+ swapBuffer();
+ while (updateRateTimer.read_ms() < updatePeriodMS) {
+ }
+ updateRateTimer.reset();
+ }
+}
\ No newline at end of file
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/mbed.lib Thu Nov 06 13:55:51 2014 +0000 @@ -0,0 +1,1 @@ +http://mbed.org/users/mbed_official/code/mbed/#031413cf7a89
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/miniFont/miniFont.cpp Thu Nov 06 13:55:51 2014 +0000
@@ -0,0 +1,167 @@
+#include "miniFont.h"
+
+const char miniFont::dot[5] = { 0x00,0x00,0x00,0x03,0x03};
+const char miniFont::space[5] = { 0x00,0x00,0x00,0x00,0x00};
+const char miniFont::exclam[5] = { 0x01,0x01,0x01,0x00,0x01};
+const char miniFont::quest[5] = { 0x0f,0x09,0x02,0x00,0x02};
+
+const char miniFont::numbers[10][5] = {
+ { 0x0e, 0x11, 0x11, 0x11, 0x08 }, // 0
+ { 0x06, 0x02, 0x02, 0x02, 0x07 }, // 1
+ { 0x1f, 0x01, 0x06, 0x18, 0x1f }, // 2
+ { 0x1f, 0x01, 0x0f, 0x01, 0x1f }, // 3
+ { 0x10, 0x10, 0x14, 0x1f, 0x04 }, // 4
+ { 0x1f, 0x10, 0x1e, 0x01, 0x1e }, // 5
+ { 0x1f, 0x10, 0x1f, 0x11, 0x1f }, // 6
+ { 0x1f, 0x01, 0x01, 0x02, 0x02 }, // 7
+ { 0x1f, 0x11, 0x08, 0x11, 0x1f }, // 8
+ { 0x1f, 0x11, 0x1f, 0x01, 0x1f } // 9
+};
+
+const char miniFont::letters[26][5] = {
+ { 0x1f, 0x11, 0x1f, 0x11, 0x11 }, // A
+ { 0x1e, 0x11, 0x1e, 0x11, 0x1e }, // B
+ { 0x1f, 0x10, 0x10, 0x10, 0x1f }, // C
+ { 0x1e, 0x11, 0x11, 0x11, 0x1e }, // D
+ { 0x1f, 0x10, 0x1e, 0x10, 0x1f }, // E
+ { 0x1f, 0x10, 0x1e, 0x10, 0x10 }, // F
+ { 0x1f, 0x10, 0x13, 0x11, 0x1f }, // G
+ { 0x11, 0x11, 0x1f, 0x11, 0x11 }, // H
+ { 0x07, 0x02, 0x02, 0x02, 0x07 }, // I
+ { 0x01, 0x01, 0x01, 0x11, 0x1f }, // J
+ { 0x11, 0x12, 0x1c, 0x12, 0x11 }, // K
+ { 0x10, 0x10, 0x10, 0x10, 0x1f }, // L
+ { 0x11, 0x1b, 0x15, 0x11, 0x11 }, // M
+ { 0x11, 0x19, 0x15, 0x13, 0x11 }, // N
+ { 0x1f, 0x11, 0x11, 0x11, 0x1f }, // O
+ { 0x1f, 0x11, 0x1f, 0x10, 0x10 }, // P
+ { 0x1f, 0x11, 0x15, 0x1f, 0x04 }, // Q
+ { 0x1f, 0x11, 0x1f, 0x12, 0x11 }, // R
+ { 0x1f, 0x10, 0x1f, 0x01, 0x1F }, // S
+ { 0x1f, 0x04, 0x04, 0x04, 0x04 }, // T
+ { 0x11, 0x11, 0x11, 0x11, 0x1F }, // U
+ { 0x11, 0x11, 0x11, 0x0a, 0x04 }, // V
+ { 0x11, 0x11, 0x15, 0x1b, 0x11 }, // W
+ { 0x11, 0x0a, 0x04, 0x0a, 0x11 }, // X
+ { 0x11, 0x11, 0x1f, 0x04, 0x04 }, // Y
+ { 0x1f, 0x02, 0x04, 0x08, 0x1f } // Z
+};
+
+
+miniFont::miniFont() {
+
+ rotate90 = false;
+ fixedWidth = false;
+ }
+
+
+uint8_t miniFont::getMinPixWidth(char letter)
+{
+ switch(letter) {
+ case '.':
+ return 2;
+ case ' ':
+ case '1':
+ case 'I':
+ case 'i':
+ return 3;
+ case '!':
+ return 1;
+ case '?':
+ return 4;
+ default:
+ return maxWidth;
+ }
+}
+
+
+uint8_t miniFont::getPixWidth(char letter)
+{
+ if (fixedWidth)
+ return maxWidth;
+ else
+ return getMinPixWidth(letter);
+}
+
+uint8_t miniFont::getPixHeight(char letter)
+{
+ return 5;
+}
+
+// gets the proportional letter
+bool miniFont::getRawChar(char letter, const char **rowArray)
+{
+
+ if ((letter>='A') && (letter<='Z')) { // upper
+ *rowArray = letters[letter-'A'];
+ return true;
+ }
+ if ((letter>='a') && (letter<='z')) { // lower
+ *rowArray = letters[letter-'a'];
+ return true;
+ }
+ if ((letter>='0') && (letter <='9')) {
+ *rowArray = numbers[letter-'0'];
+ return true;
+ }
+ if (letter == '.') {
+ *rowArray = dot;
+ return true;
+ }
+ if (letter == '!') {
+ *rowArray = exclam;
+ return true;
+ }
+ if (letter == '?') {
+ *rowArray = quest;
+ return true;
+ }
+ if (letter == ' ') {
+ *rowArray = space;
+ return true;
+ }
+ return false;
+}
+
+// converts to fixed width if needed.
+bool miniFont::getVerticalChar(char letter, const char **rowArray)
+{
+ if (!fixedWidth)
+ return getRawChar(letter,rowArray);
+
+ uint8_t shift = (maxWidth - getMinPixWidth(letter)) / 2;
+ if (shift == 0)
+ return getRawChar(letter,rowArray);
+
+ const char *rawletter;
+ if (getRawChar(letter,&rawletter)) {
+ for (int i = 0; i < maxHeight; i++) {
+ letterBuffer[i] = rawletter[i]<<shift;
+ }
+ *rowArray = (const char *)letterBuffer;
+ return true;
+ }
+ return false;
+}
+
+// rotates if needed.
+bool miniFont::getChar(char letter, const char **rowArray)
+{
+ if (!rotate90) return getVerticalChar(letter,rowArray);
+
+ const char *vertical;
+ if (!getVerticalChar(letter,&vertical))
+ return false;
+
+ for (int i = 0; i < maxWidth; i++) {
+ rotateBuffer[i] = 0;
+ }
+
+ for (int i = 0; i < maxHeight; i++) {
+ for (int j = 0; j < maxWidth; j++) {
+ rotateBuffer[i] = vertical[j] << j;
+ }
+ }
+ *rowArray = vertical;
+ return true;
+}
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/miniFont/miniFont.h Thu Nov 06 13:55:51 2014 +0000
@@ -0,0 +1,49 @@
+#ifndef __miniFont_h__
+#define __miniFont_h__
+
+#include "mbed.h"
+
+class miniFont
+{
+public:
+
+ miniFont();
+ uint8_t getPixWidth(char letter);
+ uint8_t getPixHeight(char letter);
+ bool getChar(char letter, const char **rowArray);
+
+ bool isFixedWidth() {return fixedWidth;};
+ void setFixedWidth(bool newValue) {fixedWidth = newValue;};
+
+ bool isRotated() {return rotate90;};
+ void setRotated(bool newValue) {rotate90 = newValue;};
+
+private:
+
+
+ uint8_t getMinPixWidth(char letter);
+ bool getRawChar(char letter, const char **rowArray);
+ bool getVerticalChar(char letter, const char **rowArray);
+
+ static const uint8_t maxWidth = 5;
+ static const uint8_t maxHeight = 5;
+
+ bool rotate90;
+ bool fixedWidth;
+ char letterBuffer[5];
+ char rotateBuffer[5];
+
+
+ static const char letters[26][5];
+
+ static const char numbers[10][5];
+
+ static const char dot[5];
+ static const char space[5];
+ static const char exclam[5];
+ static const char quest[5];
+
+};
+
+
+#endif
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/wsDrive.lib Thu Nov 06 13:55:51 2014 +0000 @@ -0,0 +1,1 @@ +http://developer.mbed.org/users/AndyA/code/wsDrive/#b3665f91bedc