mirror of
				https://github.com/deruiter/DCF77-Analyzer-Clock-V2.0.git
				synced 2025-11-04 16:17:45 +01:00 
			
		
		
		
	With this library, you can use Common ANODE displays if you want with the Maxim 72xx chips!
		
			
				
	
	
		
			229 lines
		
	
	
		
			7.1 KiB
		
	
	
	
		
			Diff
		
	
	
	
	
	
			
		
		
	
	
			229 lines
		
	
	
		
			7.1 KiB
		
	
	
	
		
			Diff
		
	
	
	
	
	
Common subdirectories: LedControl-unpatched/examples and LedControl/examples
 | 
						|
diff -u LedControl-unpatched/LedControl.cpp LedControl/LedControl.cpp
 | 
						|
--- LedControl-unpatched/LedControl.cpp	2008-10-14 02:21:21.000000000 -0700
 | 
						|
+++ LedControl/LedControl.cpp	2012-09-02 01:24:35.000000000 -0700
 | 
						|
@@ -35,20 +35,23 @@
 | 
						|
 #define OP_SHUTDOWN    12
 | 
						|
 #define OP_DISPLAYTEST 15
 | 
						|
 
 | 
						|
-LedControl::LedControl(int dataPin, int clkPin, int csPin, int numDevices) {
 | 
						|
+LedControl::LedControl(int dataPin, int clkPin, int csPin, int numDevices, bool anode) {
 | 
						|
     SPI_MOSI=dataPin;
 | 
						|
     SPI_CLK=clkPin;
 | 
						|
     SPI_CS=csPin;
 | 
						|
     if(numDevices<=0 || numDevices>8 )
 | 
						|
 	numDevices=8;
 | 
						|
     maxDevices=numDevices;
 | 
						|
+    anodeMode=anode;
 | 
						|
     pinMode(SPI_MOSI,OUTPUT);
 | 
						|
     pinMode(SPI_CLK,OUTPUT);
 | 
						|
     pinMode(SPI_CS,OUTPUT);
 | 
						|
     digitalWrite(SPI_CS,HIGH);
 | 
						|
     SPI_MOSI=dataPin;
 | 
						|
-    for(int i=0;i<64;i++) 
 | 
						|
+    for(int i=0;i<64;i++) { 
 | 
						|
 	status[i]=0x00;
 | 
						|
+	statusTransposed[i]=0x00;
 | 
						|
+    }
 | 
						|
     for(int i=0;i<maxDevices;i++) {
 | 
						|
 	spiTransfer(i,OP_DISPLAYTEST,0);
 | 
						|
 	//scanlimit is set to max on startup
 | 
						|
@@ -97,7 +100,16 @@
 | 
						|
     offset=addr*8;
 | 
						|
     for(int i=0;i<8;i++) {
 | 
						|
 	status[offset+i]=0;
 | 
						|
-	spiTransfer(addr, i+1,status[offset+i]);
 | 
						|
+    }
 | 
						|
+    if (anodeMode) {
 | 
						|
+    	transposeData(addr);
 | 
						|
+    	for(int i=0;i<8;i++) {
 | 
						|
+	    spiTransfer(addr, i+1, statusTransposed[offset+i]);
 | 
						|
+    	}
 | 
						|
+    } else {
 | 
						|
+    	for(int i=0;i<8;i++) {
 | 
						|
+	    spiTransfer(addr, i+1, status[offset+i]);
 | 
						|
+    	}
 | 
						|
     }
 | 
						|
 }
 | 
						|
 
 | 
						|
@@ -158,8 +170,16 @@
 | 
						|
     if(dp)
 | 
						|
 	v|=B10000000;
 | 
						|
     status[offset+digit]=v;
 | 
						|
-    spiTransfer(addr, digit+1,v);
 | 
						|
-    
 | 
						|
+    if (anodeMode) {
 | 
						|
+    	//transpose the digit matrix
 | 
						|
+    	transposeData(addr);
 | 
						|
+    	//send the entire set of digits
 | 
						|
+    	for(int i=0;i<8;i++) {
 | 
						|
+	    spiTransfer(addr, i+1, statusTransposed[offset+i]);
 | 
						|
+    	}
 | 
						|
+    } else {
 | 
						|
+    	spiTransfer(addr, digit+1, v);
 | 
						|
+    }
 | 
						|
 }
 | 
						|
 
 | 
						|
 void LedControl::setChar(int addr, int digit, char value, boolean dp) {
 | 
						|
@@ -173,14 +193,23 @@
 | 
						|
     offset=addr*8;
 | 
						|
     index=(byte)value;
 | 
						|
     if(index >127) {
 | 
						|
-	//nothing define we use the space char
 | 
						|
+	//nothing defined we use the space char
 | 
						|
 	value=32;
 | 
						|
     }
 | 
						|
     v=charTable[index];
 | 
						|
     if(dp)
 | 
						|
 	v|=B10000000;
 | 
						|
     status[offset+digit]=v;
 | 
						|
-    spiTransfer(addr, digit+1,v);
 | 
						|
+    if (anodeMode) {
 | 
						|
+    	//transpose the digit matrix
 | 
						|
+    	transposeData(addr);
 | 
						|
+    	//send the entire set of digits
 | 
						|
+    	for(int i=0;i<8;i++) {
 | 
						|
+	    spiTransfer(addr, i+1, statusTransposed[offset+i]);
 | 
						|
+    	}
 | 
						|
+    } else {
 | 
						|
+    	spiTransfer(addr, digit+1, v);
 | 
						|
+    }
 | 
						|
 }
 | 
						|
 
 | 
						|
 void LedControl::spiTransfer(int addr, volatile byte opcode, volatile byte data) {
 | 
						|
@@ -202,4 +231,73 @@
 | 
						|
     digitalWrite(SPI_CS,HIGH);
 | 
						|
 }    
 | 
						|
 
 | 
						|
+void LedControl::transposeData(int addr) {
 | 
						|
+  int offset=addr*8;
 | 
						|
+  byte a0, a1, a2, a3, a4, a5, a6, a7,
 | 
						|
+       b0, b1, b2, b3, b4, b5, b6, b7;
 | 
						|
+  
 | 
						|
+  // Perform a bitwise transpose operation on an 8x8 bit matrix, stored as 8-byte array.
 | 
						|
+  // We have to use the naive method because we're working on a 16-bit microprocessor.
 | 
						|
+
 | 
						|
+  // Load the array into eight one-byte variables.
 | 
						|
+  a0 = status[offset];
 | 
						|
+  a1 = status[offset+1];
 | 
						|
+  a2 = status[offset+2];
 | 
						|
+  a3 = status[offset+3];
 | 
						|
+  a4 = status[offset+4];
 | 
						|
+  a5 = status[offset+5];
 | 
						|
+  a6 = status[offset+6];
 | 
						|
+  a7 = status[offset+7];
 | 
						|
+  
 | 
						|
+  // Magic happens. Credit goes to: http://www.hackersdelight.org/HDcode/transpose8.c.txt
 | 
						|
+  b0 = (a0 & 128)    | (a1 & 128)/2  | (a2 & 128)/4  | (a3 & 128)/8 |
 | 
						|
+       (a4 & 128)/16 | (a5 & 128)/32 | (a6 & 128)/64 | (a7      )/128;
 | 
						|
+  b1 = (a0 &  64)*2  | (a1 &  64)    | (a2 &  64)/2  | (a3 &  64)/4 |
 | 
						|
+       (a4 &  64)/8  | (a5 &  64)/16 | (a6 &  64)/32 | (a7 &  64)/64;
 | 
						|
+  b2 = (a0 &  32)*4  | (a1 &  32)*2  | (a2 &  32)    | (a3 &  32)/2 |
 | 
						|
+       (a4 &  32)/4  | (a5 &  32)/8  | (a6 &  32)/16 | (a7 &  32)/32;
 | 
						|
+  b3 = (a0 &  16)*8  | (a1 &  16)*4  | (a2 &  16)*2  | (a3 &  16)   |
 | 
						|
+       (a4 &  16)/2  | (a5 &  16)/4  | (a6 &  16)/8  | (a7 &  16)/16;
 | 
						|
+  b4 = (a0 &   8)*16 | (a1 &   8)*8  | (a2 &   8)*4  | (a3 &   8)*2 |
 | 
						|
+       (a4 &   8)    | (a5 &   8)/2  | (a6 &   8)/4  | (a7 &   8)/8;
 | 
						|
+  b5 = (a0 &   4)*32 | (a1 &   4)*16 | (a2 &   4)*8  | (a3 &   4)*4 |
 | 
						|
+       (a4 &   4)*2  | (a5 &   4)    | (a6 &   4)/2  | (a7 &   4)/4;
 | 
						|
+  b6 = (a0 &   2)*64 | (a1 &   2)*32 | (a2 &   2)*16 | (a3 &   2)*8 |
 | 
						|
+       (a4 &   2)*4  | (a5 &   2)*2  | (a6 &   2)    | (a7 &   2)/2;
 | 
						|
+  b7 = (a0      )*128| (a1 &   1)*64 | (a2 &   1)*32 | (a3 &   1)*16|
 | 
						|
+       (a4 &   1)*8  | (a5 &   1)*4  | (a6 &   1)*2  | (a7 &   1);
 | 
						|
+
 | 
						|
+  // Assemble into output array.
 | 
						|
+  statusTransposed[offset] = b0;
 | 
						|
+  statusTransposed[offset+1] = b1;
 | 
						|
+  statusTransposed[offset+2] = b2;
 | 
						|
+  statusTransposed[offset+3] = b3;
 | 
						|
+  statusTransposed[offset+4] = b4;
 | 
						|
+  statusTransposed[offset+5] = b5;
 | 
						|
+  statusTransposed[offset+6] = b6;
 | 
						|
+  statusTransposed[offset+7] = b7;
 | 
						|
+
 | 
						|
+}
 | 
						|
+
 | 
						|
+void LedControl::setDirectDigit(int addr, int digit, byte value) {
 | 
						|
+    int offset;
 | 
						|
+
 | 
						|
+    if(addr<0 || addr>=maxDevices)
 | 
						|
+	return;
 | 
						|
+    if(digit<0 || digit>7)
 | 
						|
+	return;
 | 
						|
+    offset=addr*8;
 | 
						|
+    status[offset+digit]=value;
 | 
						|
+    if (anodeMode) {
 | 
						|
+    	transposeData(addr);
 | 
						|
+    	for(int i=0;i<8;i++) {
 | 
						|
+	    spiTransfer(addr, i+1, statusTransposed[offset+i]);
 | 
						|
+    	}
 | 
						|
+    } else {
 | 
						|
+    	spiTransfer(addr, digit+1, value);
 | 
						|
+    }
 | 
						|
+}
 | 
						|
+
 | 
						|
+
 | 
						|
+
 | 
						|
 
 | 
						|
diff -u LedControl-unpatched/LedControl.h LedControl/LedControl.h
 | 
						|
--- LedControl-unpatched/LedControl.h	2011-09-20 23:49:06.000000000 -0700
 | 
						|
+++ LedControl/LedControl.h	2012-09-02 00:18:47.000000000 -0700
 | 
						|
@@ -58,6 +58,8 @@
 | 
						|
 
 | 
						|
     /* We keep track of the led-status for all 8 devices in this array */
 | 
						|
     byte status[64];
 | 
						|
+    /* We also keep track of the transposed version */
 | 
						|
+    byte statusTransposed[64];
 | 
						|
     /* Data is shifted out of this pin*/
 | 
						|
     int SPI_MOSI;
 | 
						|
     /* The clock is signaled on this pin */
 | 
						|
@@ -66,6 +68,8 @@
 | 
						|
     int SPI_CS;
 | 
						|
     /* The maximum number of devices we use */
 | 
						|
     int maxDevices;
 | 
						|
+    /* Choose whether we're using common cathode or common anode displays */
 | 
						|
+    bool anodeMode;
 | 
						|
     
 | 
						|
  public:
 | 
						|
     /* 
 | 
						|
@@ -75,8 +79,9 @@
 | 
						|
      * clockPin		pin for the clock
 | 
						|
      * csPin		pin for selecting the device 
 | 
						|
      * numDevices	maximum number of devices that can be controled
 | 
						|
+     * anode		false for common-cathode displays, true for common-anode displays
 | 
						|
      */
 | 
						|
-    LedControl(int dataPin, int clkPin, int csPin, int numDevices=1);
 | 
						|
+    LedControl(int dataPin, int clkPin, int csPin, int numDevices=1, bool anode=false);
 | 
						|
 
 | 
						|
     /*
 | 
						|
      * Gets the number of devices attached to this LedControl.
 | 
						|
@@ -173,9 +178,25 @@
 | 
						|
      * dp	sets the decimal point.
 | 
						|
      */
 | 
						|
     void setChar(int addr, int digit, char value, boolean dp);
 | 
						|
+    
 | 
						|
+    /*
 | 
						|
+     * Transpose data matrix for use with common-anode displays.
 | 
						|
+     * Params:
 | 
						|
+     * addr	address of the display
 | 
						|
+     */
 | 
						|
+    void transposeData(int addr);
 | 
						|
+    
 | 
						|
+    /*
 | 
						|
+     * Light up segments of a 7-segment display directly by passing a binary value.
 | 
						|
+     * The eight bits of the byte each refer to a segment:
 | 
						|
+     *     Byte:   0 0 0 0 0 0 0 0
 | 
						|
+     *  Segments: DP A B C D E F G
 | 
						|
+     * Params:
 | 
						|
+     * addr	address of the display
 | 
						|
+     * digit	the position of the character on the display (0..7)
 | 
						|
+     * value	the binary value to be displayed
 | 
						|
+     */
 | 
						|
+    void setDirectDigit(int addr, int digit, byte value);
 | 
						|
 };
 | 
						|
 
 | 
						|
 #endif	//LedControl.h
 | 
						|
-
 | 
						|
-
 | 
						|
-
 |