On 06/12/2010 15:37, Astan Chee wrote:
Hi,
I've got a lego mindstorm RCX 1.0 (but firmware is 2.0) that uses one of
those old serial IR towers to control the microcontroller. I've had a
look around at python's serial documentation as well as the RCX's
documentation and I'm trying to write something to control the RCX
directly using python. Several examples from of doing this in python
include using lnp (i think) and that doesn't quite run well in windows.
I've had a look at the C++ code and some protocol documentation here:
http://www.generation5.org/content/2001/rob08.asp and converted it to
python. I've attached it at the end of the email. So now I've figured
out how to check for the battery level and it seems to work (I've tested
it on my RCX) but I'm confused with the other documentation (e.g.
http://graphics.stanford.edu/~kekoa/rcx/ ) about how to do this in
python or what this all means. I was wondering if anyone can help me
complete these? or maybe help me do it step-by-step?
Thanks for any help.
Below is the python code I've been working on:
import time
import serial
import struct
import binascii
def tcbin(x, y=8):
"""
     This function returns the padded, two's complement representation
of x, in y-bits.
     It is conventional for y to be 8, 16, 32 or 64, though y can have
any non-zero positive value.
"""
     if x >= 0:
         binstr = bin(x)
         # pad with leading zeros
         while len(binstr) < y + 2:
             binstr = "0b0" + binstr[2:]
         return binstr
     return bin((2**y) + x) # x is negative
def bitcompliment(hex_code):
     return hex(int(tcbin(~(ord(hex_code))),2))

def processOutput(raw_data,output):
     outputStatus = True
     pos = 0
     for i in range(3):
         if raw_data[i] != output[i]:
             outputStatus = False
         pos+=1
     if outputStatus:
         print "output OK"
     else:
         print "problem with output"
     outputCompliment = True
     while outputCompliment:
         if hex(ord(output[pos])) == bitcompliment(output[pos+1]):
             print "output compliment OK"
         else:
             print "problem with output compliment"
         pos+=2
         if hex(ord(output[pos])) == '0x55' and hex(ord(output[pos+1]))
== '0xff' and hex(ord(output[pos+2])) == '0x0':
             pos+=3
             outputCompliment = False
     if hex(ord(output[pos])) == '0xcf' or hex(ord(output[pos])) == '0xc7':
         #battery checker
         pos+=2
         if hex(ord(output[pos])) == bitcompliment(output[pos+1]) and
hex(ord(output[pos+2])) == bitcompliment(output[pos+3]):
             s = ((ord(output[pos+2]) * 256) + ord(output[pos])) / 1000.0
             print "Battery is at " + str(s) + " Volts"
     else:
         for i in range(len(output[pos:]),len(output),2):
             print hex(ord(output[i]))
             if i+1 < len(output):
                 if hex(ord(output[i])) == bitcompliment(output[i+1]):
                     print "message OK. contents: " + hex(ord(output[i]))

# configure the serial connections (the parameters differs on the device
you are connecting to)
ser = serial.Serial(
  port='COM1',
  baudrate=2400,
  parity=serial.PARITY_ODD,
  stopbits=serial.STOPBITS_ONE,
  bytesize=serial.EIGHTBITS
)
raw_data = '\x55\xff\x00\x38\xc7\x38\xc7'
result = ser.write(raw_data)
out = ''
time.sleep(1) #pause for a second
while ser.inWaiting() > 0:
     out+=ser.read(1)
processOutput(raw_data,out)

Here's my version of your code:

import time
import serial
import struct
import binascii

# not needed!
def tcbin(x, y=8):
    """
This function returns the padded, two's complement representation of x, in y-bits. It is conventional for y to be 8, 16, 32 or 64, though y can have any non-zero positive value.
    """
    return "0b" + bin((2 ** y) + x)[-y : ]

def byte_complement(hex_code):
    return (~ord(hex_code)) & 0xff

def process_output(raw_data, output):
    output_status = raw_data[ : 3] == output[ : 3]
    if output_status:
        print "output OK"
    else:
        print "problem with output"
    pos = 3
    output_complement = True
    while output_complement:
        if ord(output[pos]) == byte_complement(output[pos + 1]):
            print "output complement OK"
        else:
            print "problem with output complement"
        pos += 2
if ord(output[pos]) == 0x55 and ord(output[pos + 1]) == 0xff and ord(output[pos + 2]) == 0x00:
            pos += 3
            output_complement = False
    if ord(output[pos]) == 0xcf or ord(output[pos]) == 0xc7:
        # battery checker
        pos += 2
if ord(output[pos]) == byte_complement(output[pos + 1]) and ord(output[pos + 2]) == byte_complement(output[pos + 3]):
            s = ((ord(output[pos + 2]) * 256) + ord(output[pos])) / 1000.0
            print "Battery is at %s Volts" % s
    else:
        for i in range(len(output[pos : ]), len(output), 2):
            print hex(ord(output[i]))
            if i + 1 < len(output):
                if ord(output[i]) == byte_complement(output[i + 1]):
                    print "message OK. contents: %s" % hex(ord(output[i]))

# configure the serial connections (the parameters differs on the device you are connecting to)
ser = serial.Serial(
 port='COM1',
 baudrate=2400,
 parity=serial.PARITY_ODD,
 stopbits=serial.STOPBITS_ONE,
 bytesize=serial.EIGHTBITS
)
raw_data = '\x55\xff\x00\x38\xc7\x38\xc7'
result = ser.write(raw_data)
out = ''
time.sleep(1) # pause for a second
while ser.inWaiting() > 0:
    out += ser.read(1)
process_output(raw_data, out)
--
http://mail.python.org/mailman/listinfo/python-list

Reply via email to