|
@@ -16,6 +16,122 @@
|
|
|
#include <util/delay.h>
|
|
|
#include "debug.h"
|
|
|
|
|
|
+#define RGBW_BB_TWI 1
|
|
|
+
|
|
|
+#ifdef RGBW_BB_TWI
|
|
|
+
|
|
|
+// Port for the I2C
|
|
|
+#define I2C_DDR DDRD
|
|
|
+#define I2C_PIN PIND
|
|
|
+#define I2C_PORT PORTD
|
|
|
+
|
|
|
+// Pins to be used in the bit banging
|
|
|
+#define I2C_CLK 0
|
|
|
+#define I2C_DAT 1
|
|
|
+
|
|
|
+#define I2C_DATA_HI()\
|
|
|
+I2C_DDR &= ~ (1 << I2C_DAT);\
|
|
|
+I2C_PORT |= (1 << I2C_DAT);
|
|
|
+#define I2C_DATA_LO()\
|
|
|
+I2C_DDR |= (1 << I2C_DAT);\
|
|
|
+I2C_PORT &= ~ (1 << I2C_DAT);
|
|
|
+
|
|
|
+#define I2C_CLOCK_HI()\
|
|
|
+I2C_DDR &= ~ (1 << I2C_CLK);\
|
|
|
+I2C_PORT |= (1 << I2C_CLK);
|
|
|
+#define I2C_CLOCK_LO()\
|
|
|
+I2C_DDR |= (1 << I2C_CLK);\
|
|
|
+I2C_PORT &= ~ (1 << I2C_CLK);
|
|
|
+
|
|
|
+#define I2C_DELAY 1
|
|
|
+
|
|
|
+void I2C_WriteBit(unsigned char c)
|
|
|
+{
|
|
|
+ if (c > 0)
|
|
|
+ {
|
|
|
+ I2C_DATA_HI();
|
|
|
+ }
|
|
|
+ else
|
|
|
+ {
|
|
|
+ I2C_DATA_LO();
|
|
|
+ }
|
|
|
+
|
|
|
+ I2C_CLOCK_HI();
|
|
|
+ _delay_us(I2C_DELAY);
|
|
|
+
|
|
|
+ I2C_CLOCK_LO();
|
|
|
+ _delay_us(I2C_DELAY);
|
|
|
+
|
|
|
+ if (c > 0)
|
|
|
+ {
|
|
|
+ I2C_DATA_LO();
|
|
|
+ }
|
|
|
+
|
|
|
+ _delay_us(I2C_DELAY);
|
|
|
+}
|
|
|
+
|
|
|
+// Inits bitbanging port, must be called before using the functions below
|
|
|
+//
|
|
|
+void I2C_Init()
|
|
|
+{
|
|
|
+ I2C_PORT &= ~ ((1 << I2C_DAT) | (1 << I2C_CLK));
|
|
|
+
|
|
|
+ I2C_CLOCK_HI();
|
|
|
+ I2C_DATA_HI();
|
|
|
+
|
|
|
+ _delay_us(I2C_DELAY);
|
|
|
+}
|
|
|
+
|
|
|
+// Send a START Condition
|
|
|
+//
|
|
|
+void I2C_Start()
|
|
|
+{
|
|
|
+ // set both to high at the same time
|
|
|
+ I2C_DDR &= ~ ((1 << I2C_DAT) | (1 << I2C_CLK));
|
|
|
+ _delay_us(I2C_DELAY);
|
|
|
+
|
|
|
+ I2C_DATA_LO();
|
|
|
+ _delay_us(I2C_DELAY);
|
|
|
+
|
|
|
+ I2C_CLOCK_LO();
|
|
|
+ _delay_us(I2C_DELAY);
|
|
|
+}
|
|
|
+
|
|
|
+// Send a STOP Condition
|
|
|
+//
|
|
|
+void I2C_Stop()
|
|
|
+{
|
|
|
+ I2C_CLOCK_HI();
|
|
|
+ _delay_us(I2C_DELAY);
|
|
|
+
|
|
|
+ I2C_DATA_HI();
|
|
|
+ _delay_us(I2C_DELAY);
|
|
|
+}
|
|
|
+
|
|
|
+// write a byte to the I2C slave device
|
|
|
+//
|
|
|
+unsigned char I2C_Write(unsigned char c)
|
|
|
+{
|
|
|
+ for (char i = 0; i < 8; i++)
|
|
|
+ {
|
|
|
+ I2C_WriteBit(c & 128);
|
|
|
+
|
|
|
+ c <<= 1;
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+ I2C_WriteBit(0);
|
|
|
+ _delay_us(I2C_DELAY);
|
|
|
+ _delay_us(I2C_DELAY);
|
|
|
+
|
|
|
+ // _delay_us(I2C_DELAY);
|
|
|
+ //return I2C_ReadBit();
|
|
|
+ return 0;
|
|
|
+}
|
|
|
+
|
|
|
+
|
|
|
+#endif
|
|
|
+
|
|
|
// Setleds for standard RGB
|
|
|
void inline ws2812_setleds(struct cRGB *ledarray, uint16_t leds)
|
|
|
{
|
|
@@ -41,6 +157,25 @@ void inline ws2812_setleds_rgbw(struct cRGBW *ledarray, uint16_t leds)
|
|
|
_SFR_IO8((RGB_DI_PIN >> 4) + 1) |= _BV(RGB_DI_PIN & 0xF);
|
|
|
|
|
|
ws2812_sendarray_mask((uint8_t*)ledarray,leds<<2,_BV(RGB_DI_PIN & 0xF));
|
|
|
+
|
|
|
+ #ifdef RGBW_BB_TWI
|
|
|
+ cli();
|
|
|
+ TWCR = 0;
|
|
|
+ I2C_Init();
|
|
|
+ I2C_Start();
|
|
|
+ I2C_Write(0x84);
|
|
|
+ uint16_t datlen = leds<<2;
|
|
|
+ uint8_t curbyte;
|
|
|
+ uint8_t * data = (uint8_t*)ledarray;
|
|
|
+ while (datlen--) {
|
|
|
+ curbyte=*data++;
|
|
|
+ I2C_Write(curbyte % 0x10);
|
|
|
+ }
|
|
|
+ I2C_Stop();
|
|
|
+ sei();
|
|
|
+ #endif
|
|
|
+
|
|
|
+
|
|
|
_delay_us(80);
|
|
|
}
|
|
|
|
|
@@ -123,7 +258,7 @@ void inline ws2812_sendarray_mask(uint8_t *data,uint16_t datlen,uint8_t maskhi)
|
|
|
cli();
|
|
|
|
|
|
while (datlen--) {
|
|
|
- curbyte=*data++;
|
|
|
+ curbyte=(*data++) % 0x10;
|
|
|
|
|
|
asm volatile(
|
|
|
" ldi %0,8 \n\t"
|