{
// The data pin must be low for at least 50uS to reset the LED drivers
PIN_WS2812_LATCH = 0;
__delay_us(50);
#asm
MOVLB HIGH(_tmpData) // select memory bank 12, so we can access the relevant variables
MOVLW LED_ARRAY_SIZE // ledCount = total number of leds
MOVWF BANKMASK(_ledCount),b
LFSR 0, _ledData // initialise the ledData pointer to the start of the array (FSR0 = address of _ledData)
byteLoop: MOVF POSTINC0,W,c // get the next byte of ledData and increment the FSR0 pointer
MOVWF BANKMASK(_tmpData),b // save it in tmpData
MOVLW 0x08; // bitCount = 8;
MOVWF BANKMASK(_bitCount),b
bitLoop: BSF LATB, 0,c // set the output high
BTFSS BANKMASK(_tmpData), 7,b // test the m.s. bit of tmpData.
BRA writeZero
// logic ONE (long HIGH output, followed by short LOW)
writeOne: RLNCF BANKMASK(_tmpData),b // shift tmpData left one place
NOP
NOP
NOP
NOP
NOP
NOP
NOP
BCF LATB,0,c // set the output pin low
DECFSZ BANKMASK(_bitCount),b // decrement the bit counter
BRA bitLoop // if not zero, process the next bit.
BRA endByte // zero - goto the next byte
// logic ZERO (short HIGH output, followed by long LOW)
writeZero: BCF LATB,0,c // set output low
RLNCF BANKMASK(_tmpData),b // shift tmpData left one place
NOP
NOP
NOP
NOP
NOP
NOP
DECFSZ BANKMASK(_bitCount),b // decrement the bit counter
BRA bitLoop // if not zero process the next bit
// Move on to the next byte if any
endByte: DECFSZ BANKMASK(_ledCount),b // decrement the byte counter
BRA byteLoop // if non-zero, process the next byte
// finished
#endasm
}
forever loop
DIn = high -- high for 0.1250μS
DIn = low -- low for 0.5000μS
end loop
forever loop
DIn = !DIn -- high for 1.5000μS, low for 1.7500μS
end loop
forever loop
DIn = !DIn
DIn = !DIn
DIn = !DIn
DIn = !DIn
DIn = !DIn
DIn = !DIn
DIn = !DIn
DIn = !DIn
DIn = !DIn
DIn = !DIn
end loop
forever loop
DIn = on
DIn = off
DIn = on
DIn = off
DIn = on
DIn = off
DIn = on
DIn = off
DIn = on
DIn = off
DIn = on
DIn = off
DIn = on
DIn = off
DIn = on
DIn = off
end loop
forever loop
DIn = off
_usec_delay (55)
-- Green 1000 0000
DIn = on -- 0.1250 1
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- 0.5000
asm nop -- 0.6250
asm nop -- *0.7500* - 0.8000 indicates T1H
DIn = off -- 0.1250
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- *0.5000* - 0.4500 indicates T1L; should be a 1
DIn = on -- 0.1250 2
asm nop -- 0.2500
asm nop -- *0.3750* - 0.4000 indicates T0H
DIn = off -- 0.1250
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- 0.5000
asm nop -- 0.6250
asm nop -- 0.7500
asm nop -- *0.8750* - 0.8500 indicates T0L, should be a 0
DIn = on -- 0.1250 3
asm nop -- 0.2500
asm nop -- *0.3750* - 0.4000 indicates T0H
DIn = off -- 0.1250
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- 0.5000
asm nop -- 0.6250
asm nop -- 0.7500
asm nop -- *0.8750* - 0.8500 indicates T0L, should be a 0
DIn = on -- 0.1250 4
asm nop -- 0.2500
asm nop -- *0.3750* - 0.4000 indicates T0H
DIn = off -- 0.1250
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- 0.5000
asm nop -- 0.6250
asm nop -- 0.7500
asm nop -- *0.8750* - 0.8500 indicates T0L, should be a 0
DIn = on -- 0.1250 5
asm nop -- 0.2500
asm nop -- *0.3750* - 0.4000 indicates T0H
DIn = off -- 0.1250
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- 0.5000
asm nop -- 0.6250
asm nop -- 0.7500
asm nop -- *0.8750* - 0.8500 indicates T0L, should be a 0
DIn = on -- 0.1250 6
asm nop -- 0.2500
asm nop -- *0.3750* - 0.4000 indicates T0H
DIn = off -- 0.1250
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- 0.5000
asm nop -- 0.6250
asm nop -- 0.7500
asm nop -- *0.8750* - 0.8500 indicates T0L, should be a 0
DIn = on -- 0.1250 7
asm nop -- 0.2500
asm nop -- *0.3750* - 0.4000 indicates T0H
DIn = off -- 0.1250
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- 0.5000
asm nop -- 0.6250
asm nop -- 0.7500
asm nop -- *0.8750* - 0.8500 indicates T0L, should be a 0
DIn = on -- 0.1250 8
asm nop -- 0.2500
asm nop -- *0.3750* - 0.4000 indicates T0H
DIn = off -- 0.1250
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- 0.5000
asm nop -- 0.6250
asm nop -- 0.7500
asm nop -- *0.8750* - 0.8500 indicates T0L, should be a 0
-- Red 1000 0000
DIn = on -- 0.1250 1
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- 0.5000
asm nop -- 0.6250
asm nop -- *0.7500* - 0.8000 indicates T1H
DIn = off -- 0.1250
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- *0.5000* - 0.4500 indicates T1L; should be a 1
DIn = on -- 0.1250 2
asm nop -- 0.2500
asm nop -- *0.3750* - 0.4000 indicates T0H
DIn = off -- 0.1250
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- 0.5000
asm nop -- 0.6250
asm nop -- 0.7500
asm nop -- *0.8750* - 0.8500 indicates T0L, should be a 0
DIn = on -- 0.1250 3
asm nop -- 0.2500
asm nop -- *0.3750* - 0.4000 indicates T0H
DIn = off -- 0.1250
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- 0.5000
asm nop -- 0.6250
asm nop -- 0.7500
asm nop -- *0.8750* - 0.8500 indicates T0L, should be a 0
DIn = on -- 0.1250 4
asm nop -- 0.2500
asm nop -- *0.3750* - 0.4000 indicates T0H
DIn = off -- 0.1250
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- 0.5000
asm nop -- 0.6250
asm nop -- 0.7500
asm nop -- *0.8750* - 0.8500 indicates T0L, should be a 0
DIn = on -- 0.1250 5
asm nop -- 0.2500
asm nop -- *0.3750* - 0.4000 indicates T0H
DIn = off -- 0.1250
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- 0.5000
asm nop -- 0.6250
asm nop -- 0.7500
asm nop -- *0.8750* - 0.8500 indicates T0L, should be a 0
DIn = on -- 0.1250 6
asm nop -- 0.2500
asm nop -- *0.3750* - 0.4000 indicates T0H
DIn = off -- 0.1250
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- 0.5000
asm nop -- 0.6250
asm nop -- 0.7500
asm nop -- *0.8750* - 0.8500 indicates T0L, should be a 0
DIn = on -- 0.1250 7
asm nop -- 0.2500
asm nop -- *0.3750* - 0.4000 indicates T0H
DIn = off -- 0.1250
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- 0.5000
asm nop -- 0.6250
asm nop -- 0.7500
asm nop -- *0.8750* - 0.8500 indicates T0L, should be a 0
DIn = on -- 0.1250 8
asm nop -- 0.2500
asm nop -- *0.3750* - 0.4000 indicates T0H
DIn = off -- 0.1250
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- 0.5000
asm nop -- 0.6250
asm nop -- 0.7500
asm nop -- *0.8750* - 0.8500 indicates T0L, should be a 0
-- Blue 1000 0000
DIn = on -- 0.1250 1
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- 0.5000
asm nop -- 0.6250
asm nop -- *0.7500* - 0.8000 indicates T1H
DIn = off -- 0.1250
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- *0.5000* - 0.4500 indicates T1L; should be a 1
DIn = on -- 0.1250 2
asm nop -- 0.2500
asm nop -- *0.3750* - 0.4000 indicates T0H
DIn = off -- 0.1250
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- 0.5000
asm nop -- 0.6250
asm nop -- 0.7500
asm nop -- *0.8750* - 0.8500 indicates T0L, should be a 0
DIn = on -- 0.1250 3
asm nop -- 0.2500
asm nop -- *0.3750* - 0.4000 indicates T0H
DIn = off -- 0.1250
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- 0.5000
asm nop -- 0.6250
asm nop -- 0.7500
asm nop -- *0.8750* - 0.8500 indicates T0L, should be a 0
DIn = on -- 0.1250 4
asm nop -- 0.2500
asm nop -- *0.3750* - 0.4000 indicates T0H
DIn = off -- 0.1250
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- 0.5000
asm nop -- 0.6250
asm nop -- 0.7500
asm nop -- *0.8750* - 0.8500 indicates T0L, should be a 0
DIn = on -- 0.1250 5
asm nop -- 0.2500
asm nop -- *0.3750* - 0.4000 indicates T0H
DIn = off -- 0.1250
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- 0.5000
asm nop -- 0.6250
asm nop -- 0.7500
asm nop -- *0.8750* - 0.8500 indicates T0L, should be a 0
DIn = on -- 0.1250 6
asm nop -- 0.2500
asm nop -- *0.3750* - 0.4000 indicates T0H
DIn = off -- 0.1250
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- 0.5000
asm nop -- 0.6250
asm nop -- 0.7500
asm nop -- *0.8750* - 0.8500 indicates T0L, should be a 0
DIn = on -- 0.1250 7
asm nop -- 0.2500
asm nop -- *0.3750* - 0.4000 indicates T0H
DIn = off -- 0.1250
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- 0.5000
asm nop -- 0.6250
asm nop -- 0.7500
asm nop -- *0.8750* - 0.8500 indicates T0L, should be a 0
DIn = on -- 0.1250 8
asm nop -- 0.2500
asm nop -- *0.3750* - 0.4000 indicates T0H
DIn = off -- 0.1250
asm nop -- 0.2500
asm nop -- 0.3750
asm nop -- 0.5000
asm nop -- 0.6250
asm nop -- 0.7500
asm nop -- *0.8750* - 0.8500 indicates T0L, should be a 0
end loop
procedure WS2812B_Byte ( byte in pByte
) is
var bit MSB at pByte : 7
-- 1 = 0.750us high, 0.500us low
-- 0 = 0.375us high, 0.875us low
for 8 loop
if (MSB) then
DIn = on
asm nop
asm nop
asm nop
asm nop
asm nop -- 0.7500us (T1H)
DIn = off -- no nop here, can only achieve 2.000us, but need 0.500us
else
DIn = on
asm nop
asm nop -- 0.375us
DIn = off -- no nop here, can only achieve 1.625us, but need 0.875us
end if
pByte = pByte << 1
end loop
end procedure
We use cookies and similar technologies for the following purposes:
Do you accept cookies and these technologies?
We use cookies and similar technologies for the following purposes:
Do you accept cookies and these technologies?