DS1307 Real Time Clock - BCD To ASCII Conversion For uLCD-32PTU
Boss9
Posts: 8
I have a 4D Systems uLCD-32PTU display, connected to a Propeller via serial. I'm trying to display the time from an DS1307 Real Time Clock.
I have ran the I2C routines - Archive, DS1307 Demo, and that works great. I can read and write to the DS1307, and it displays on the Parallax Serial Terminal.
This worked right out of the box, only had to edit the SCL, SDA pin numbers.
I have also ran the uLCD32-ptu Demo. It also works great right out of the box.
So I can verify that I can read and write to the RTC, and that I can operate the LCD via serial with the Propeller.
Problem is when I attempt to display the time from the DS1307 on the uLCD32. I can get the Day, and Month to display.
I can not get the Date, Hours, Minutes,Seconds to display.
The DS1307 Demo uses "FullDuplexSerial.spin. This has a PUB.hex that converts the "Date" Bcd number to ASCII. Yep, that's right, its a "HEX" conversion pub that is working on a BCD formatted number from the DS1307.
I don't understand how that works.
Here is small chunk of code from the DS1307 Demo:
FDS.hex(Date,2) ;Calls the FullDuplexSerial .hex pub - see below
And Chunk from FullDuplexSerial:
PUB Hex(value, digits)
value <<= (8 - digits) << 2
repeat digits 'do it for the number of hex digits being transmitted
Tx(lookupz((value <-= 4) & $F : "0".."9", "A".."F"))' Transmit the ASCII value of the hex characters
The uLCD32-ptu Demo does not use the FullDuplexSerial.spin to communicate. It uses the uLCD(SK)-32PTU.spin. This does not have a "HEX" conversion pub.
I have tried some Bitwise conversion stuff, such as :
PRI BCDToNumber(BCD)
' Converts a two-nibble BCD number to a standard binary number
return (((BCD >> 4) * 10) + (BCD & $F))
The Arduino folks use something like this :
seconds = (((seconds & 0b11110000)>>4)*10 + (seconds & 0b00001111)); // convert BCD to decimal
minutes = (((minutes & 0b11110000)>>4)*10 + (minutes & 0b00001111)); // convert BCD to decimal
But I'm not an Arduino guy.
I'm hoping someone else has already done this, and could share with me how to make this work.
And if I could get some help understanding how a "HEX" conversion works on a BCD value, that would be great. I have several project to use this display and Real Time Clock on, so I need to get past this small issue
I can post code if needed, but it's really just straight out of the uLCD32-ptu Demo, and DS1307 Demo from the I2C routines - archives OBEX
I have ran the I2C routines - Archive, DS1307 Demo, and that works great. I can read and write to the DS1307, and it displays on the Parallax Serial Terminal.
This worked right out of the box, only had to edit the SCL, SDA pin numbers.
I have also ran the uLCD32-ptu Demo. It also works great right out of the box.
So I can verify that I can read and write to the RTC, and that I can operate the LCD via serial with the Propeller.
Problem is when I attempt to display the time from the DS1307 on the uLCD32. I can get the Day, and Month to display.
I can not get the Date, Hours, Minutes,Seconds to display.
The DS1307 Demo uses "FullDuplexSerial.spin. This has a PUB.hex that converts the "Date" Bcd number to ASCII. Yep, that's right, its a "HEX" conversion pub that is working on a BCD formatted number from the DS1307.
I don't understand how that works.
Here is small chunk of code from the DS1307 Demo:
FDS.hex(Date,2) ;Calls the FullDuplexSerial .hex pub - see below
And Chunk from FullDuplexSerial:
PUB Hex(value, digits)
value <<= (8 - digits) << 2
repeat digits 'do it for the number of hex digits being transmitted
Tx(lookupz((value <-= 4) & $F : "0".."9", "A".."F"))' Transmit the ASCII value of the hex characters
The uLCD32-ptu Demo does not use the FullDuplexSerial.spin to communicate. It uses the uLCD(SK)-32PTU.spin. This does not have a "HEX" conversion pub.
I have tried some Bitwise conversion stuff, such as :
PRI BCDToNumber(BCD)
' Converts a two-nibble BCD number to a standard binary number
return (((BCD >> 4) * 10) + (BCD & $F))
The Arduino folks use something like this :
seconds = (((seconds & 0b11110000)>>4)*10 + (seconds & 0b00001111)); // convert BCD to decimal
minutes = (((minutes & 0b11110000)>>4)*10 + (minutes & 0b00001111)); // convert BCD to decimal
But I'm not an Arduino guy.
I'm hoping someone else has already done this, and could share with me how to make this work.
And if I could get some help understanding how a "HEX" conversion works on a BCD value, that would be great. I have several project to use this display and Real Time Clock on, so I need to get past this small issue
I can post code if needed, but it's really just straight out of the uLCD32-ptu Demo, and DS1307 Demo from the I2C routines - archives OBEX
Comments
Thanks for the info. That helps a bit. Getting the data out in a serial mode to the 4D display seems to be the issue.
The Demo works great on the Serial Terminal, so I think it's a matter of getting code to work with the serial commands of the 4D display. The uLCD32-ptu object does not have a 'HEX" Pub, and it also doesn't have a "TX" pub
to transmit each byte as does the FullDuplexSerial. The "TX" pub is called in the "HEX"pub.
PUB Tx(txByte)
{{
Places a byte into the transmit buffer for transmission (may wait for room in buffer).
Parameters: txByte = the byte to be transmitted
return: none
example usage: serial.Tx($0D)
expected outcome of example usage call: Transmits the byte $0D serially on the txPin
}}
repeat until (tx_tail <> (tx_head + 1) & $F) 'wait until the buffer has room
tx_buffer[tx_head] := txByte 'place the byte into the buffer
tx_head := (tx_head + 1) & $F 'advance the buffer's pointer
if rxtx_mode & %1000 'if ignoring rx echo
Rx ' receive the echoed byte and discard
I'll keep digging unto the "picaso serial commands" document for the 4D dispaly for now
first to the conversion from BCD to ASCII via HEX.
This is one of the reasons BCD exists at all. BCD stores one decimal digit 0-9 in the first 4 bits of the byte and another decimal digit 0-9 in the second 4 bits.
If viewed as HEX you see the decimal value. Directly.
in real binary you can store 256 different values in a byte. Hex 00 - Hex FF.
in BCD you can store 2 decimal digits in a byte, so 100 different values. Hex 00 - Hex 99. But all Hex values containing A-F in one of the digits are simply not used in BCD.
Back to your main problem.
I do not know which driver you use for the 4D-Systems LCD. But it is basically a serial driver like FullDuplex Serial.
I am absolutely sure that in your LCD driver is a function/procedure/method whatever you want to call it, for transmitting a single character onto the display.
It might not be called TX(txbyte), maybe it is OUT(outbyte) or CHAR(whatever). But it has to be there or you would not be able to output at all.
So copy the HEX pub from full duplex serial into your LCD driver and replace TX(xx) by the name of the existing output function.
If you could archive your project and add the created zip file as attachment, things might be easier to explain.
Enjoy!
Mike
Played with the "HEX" pub and printing strings and characters to the display, until I got it to work.
Did manage to learn more about hex and bcd
Now I can get on with the rest of the Project.
Thanks for helping,
Randy