I know this is an old thread, I am trying to decode a PT2262 encoder using a PIC could do with someone looking at my code to see where I am going wrong. The code is modified from Bruce's Holtec decoding routine.
I can read the buttons pressed using the code below, but it only works if I hold the Tx a few inches from the Rx. I think there is a timing problem.
I have measured the waveforms at the output of the encoder and they are;
120uS for a logic 0 and 400uS for a logic 1 with a duty cycle of 500uS. Each pulse train is spaced at 4mS, each button press is repeated 4 times. See the data sheet posted in dhoustons link above.
I am using the bit24 (sync) as the reference bit as its the only constant in the pulse train.
Thanks Nick
Code:
@ __config _INTRC_OSC_NOCLKOUT & _WDT_ON & _PWRTE_OFF & _MCLRE_OFF & _BOD_OFF & _CP_ON & _CPD_ON
OSCCON = %01110000 ' Internal 8MHz osc
ANSEL = %00000000
CMCON0 = 7
Define OSC 8 ' Define oscilator speed
DEFINE DEBUG_REG GPIO
DEFINE DEBUG_BIT 0 'GPIO.0
DEFINE DEBUG_MODE 0 'Inverted
DEFINE DEBUG_BAUD 9600 'Baud rate to LCD
define DEBUG_PACING 1000
DEFINE PULSIN_MAX 3000 ' Set MAX wait period
INCLUDE "modedefs.bas"
GPIO=0 ' All outputs = 0 on boot
GPIO=%00100000 ' GPIO.5 = in, rest outputs.
PBIT VAR BYTE[24]' Pulse-in results of high-going address/data/ synch
NUMS VAR WORD ' Pulsin result of low-going synch period
ADDRESS VAR Byte ' Holds decoded 8-bit address
ADDRESS2 VAR Byte ' 2nd address storage for verification pass
ADDRESS3 VAR BYTE ' 3rd address storage for verification pass
DBYTE VAR BYTE ' Holds decoded 8-bit data byte
DBYTE2 VAR BYTE ' 2nd data byte storage for verification pass
DBYTE3 VAR BYTE ' 3rd data byte storage for verification pass
X VAR BYTE ' GP loop counter/array index pointer
Y VAR BYTE ' Address & Data bit index pointer
Z var byte ' Used to display button press
LOOPS VAR BYTE ' Loop counter for address & data match
P_MAX VAR BYTE ' Wide pulse (indicates GND)
P_MIN VAR BYTE ' Narrow pulse (indicates Vcc)
DIN VAR GPIO.5 ' Data input pin from RF receiver
LED VAR GPIO.2 ' Visual cue
High LED
pause 2000
Debug $FE,1,"Power UP" 'Output received data to the world
pause 500
Debug $FE,1,"Waiting for" 'Output received data to the world
Debug $FE,$C0,"Button press"
Begin: ' Clear vars on power up & start over.
ADDRESS=0 : ADDRESS2=0 : ADDRESS3=0 : DBYTE=0 : DBYTE2=0 : DBYTE3=0 : LOOPS=0
GET_P:
'PULSIN DIN,0,NUMS ' Get low going synch period pulse.
'IF NUMS = 0 THEN ' If NUMS=0, no synch pulse within defined period.
' Loops=0 ' Clear "1st pass" address & data loop counter.
' GOTO GET_P ' Keep looking.
' ENDIF
' Normally the synch pulse is between 11-16mS, so we'll reject any synch pulse < 10mS
' to allow for variations in timing & transmitter voltages.
'IF NUMS < 1000 THEN GET_P ' 1000 X 10uS = 10mS (PULSIN = 10uS resolution at 4MHz)
FOR X = 0 TO 24 ' 25 bits in total for pt2262
PULSIN DIN,1,NUMS '
IF NUMS < 20 THEN GET_P 'USED TO REJECT NOISE
PBIT[X] = NCD NUMS ' 25 bits total. 1 synch, 16 address, 8 data
NEXT X ' Note that the PT2262 uses two pulses form each bit.
' Now load P_MAX & P_MIN for sort loops below to sort out
' address/data bit logic states.
P_MAX = PBIT[0] ' Not used yet
P_MIN = PBIT[24] ' "narrow" synch bit
' Decode 8-bit address
ADDRESS = $FF ' Start with all 1's & find each zero bit
Y=0 ' Zero address bit index pointer
' PBIT[0] + PBIT[1]=1st address bit. PBIT[14] + PBIT[15]=last
FOR X = 0 to 15 STEP 2 ' Increment x 2 each pass
IF (PBIT[X] = P_MIN) AND (PBIT[X+1] = P_MIN) THEN
ADDRESS.0[Y]=0
ENDIF
Y=Y+1 ' Increment address bit index pointer
NEXT X
' Decode 8-bit data byte (decode button press)
DBYTE = $FF ' Start with all 1's & find each zero bit
Y=0 ' Zero data bit index pointer
' PBIT[16] + PBIT[17]=1st data bit. PBIT[22] + PBIT[23]=last
FOR X = 16 TO 23 STEP 2 ' Increment x 2 each pass
IF PBIT[X] AND PBIT[X+1] = P_MIN THEN DBYTE.0[Y]=0
Y=Y+1 ' Increment data bit index pointer
NEXT X
' On 1st pass, load 1st address & data into verify registers,
' then return for 2nd pass at pulsin. We'll make address &
' data match twice before moving on.
Loops = Loops + 1 ' Increment loop counter
'if LOOPS = 1 THEN GET_P
IF Loops = 1 THEN ' 2nd pass through?
Address2 = Address ' Yes. Load 1st address into match register
DBYTE2 = DBYTE ' Load 1st data into match register
GOTO GET_P ' Get 2nd readings for comparison with 1st two
ENDIF
' 2nd pass, so verify address & data bytes.
' If they match, show button press
CONTINUE:
IF (DBYTE = DBYTE2) AND (ADDRESS = ADDRESS2) THEN ' Show only if both data bytes equal
if DBYTE2 = %11110001 THEN Z = "B"
if DBYTE2 = %11111000 THEN Z = "A"
if DBYTE2 = %11110010 THEN Z = "D"
if DBYTE2 = %11110100 THEN Z = "C"
Debug $FE,1,"Add=",$14,#address2 'Output received data to the world
Debug $FE,$C0,"Button=",$14,z
ENDIF
GOTO Begin ' Start over.
END
Bookmarks