PDA

View Full Version : [Question(s)] Devantech CMPS03 Compass and USB-I2C



Connor
01-02-2009, 01:46 PM
Okay, working on my compass today.. I had to get a USB-I2C converter.. It came in today.. so I'm playing.. I've looked all over, and can't find any python code to work with these devices.. does anyone have any code? or a easy way to get this thing up and running? I've never done anything with I2C before.

Thanks, Connor

Adrenalynn
01-02-2009, 01:49 PM
It might help to tell us WHICH I2C converter... ;)

jes1510
01-02-2009, 02:14 PM
Show us which one so I can see the datasheet and I should be able to give you some code snippets.

Connor
01-02-2009, 03:35 PM
It might help to tell us WHICH I2C converter... ;)

The one from Devantech of course! :) I figuted, Devantech Compass, Hmm.. Why not the Devantech USB-I2C converter. :)

Thanks, Connor

jes1510
01-02-2009, 04:13 PM
Do you have pyserial installed and working?

Connor
01-02-2009, 04:15 PM
Do you have pyserial installed and working?

Sure do, that's how I communicate with the Roomba, and the X10 Firecracker.

jes1510
01-02-2009, 04:40 PM
First here is the documentation for pyserial
http://pyserial.wiki.sourceforge.net/pySerial

It looks like the BB code is going to butcher the white space so you'll need to clean it up to test. Give this a test. The documentation says to write the address with the R/W bite low, then the register, then the address with the R/W bit high. It should return 2 bytes with the bearing. FWIW I have never used pyserial for Hex data so this may not work at all.



import serial
import time

# replace the 8 with COM number - 1 (pyserial ports start at 0(
ser = serial.Serial(8, 19200, timeout = 1)

address = hex(192)

def readCompass :
ser.write(address) # write the address
ser.write(hex(2)) # I think you have to write both registers
ser.write(hex(3))
ser.write(hex(193)) # Tell it your done
highByte = ser.read() # high byte is returned first
lowByte = ser.read() # low byte next
highByteShifted = highByte << 8 # shift low byte 8 bits left
bearing = highByteShifted && lowByte # & them together to get complete word
return bearing

while 1 :
heading = readCompass()
print heading
time.sleep(.5)


Edit: I assume you know that the above example will run forever until broken with ctrl^c
Edit of the edit: I added a 1/2 second delay so you aren't slamming the compass. You also may have to add the
stopbits=STOPBITS_TWO attribute to the serial instance. ie:
ser = serial.Serial(8, 19200, timeout = 1, stopbits=STOPBITS_TWO
)

Connor
01-02-2009, 05:40 PM
Tried the code, opens the comport just fine.. but, I'm not seeing it pulse the USB-I2C unit.. (I found a perl program that would pulse it.. but, it was setup for the sonar, not the compass, so no meaningful data).

The code looks good, I commented out the following lines...

highByteShifted = highByte << 8 # shift low byte 8 bits left
bearing = highByteShifted && lowByte # & them together to get complete word return bearing

and then just printed out highBye and lowByte.. but they're empty..

ser.write(hex(193) needs a extra ) on the end.

Hmm.. Now what..

jes1510
01-02-2009, 05:54 PM
Is the code spitting out any errors?

Put your scope on the I2C lines and make sure it isn't sending anything. Also make sure that you are writing to the correct port. A new serial port should appear when you connect the USB to I2C device. Does the ting have any LED's to show data?

Connor
01-02-2009, 11:07 PM
Finalized code..



import serial
import time
from struct import *

# replace the 8 with COM number - 1 (pyserial ports start at 0(
ser = serial.Serial(4, 19200, timeout = 1 , bytesize=8, parity='N', stopbits=2,xonxoff=0, rtscts=0)

def readCompass():
out = pack('4B',0x55,0xC1,0x02,0x02)
ser.write(out)
out = ser.read(2) # high byte is returned first
heading = (ord( out[0]) * 256 + ord(out[1])) * .1
return heading

while 1:
heading = readCompass()
print heading
time.sleep(.10)

Adrenalynn
01-03-2009, 12:14 AM
That compass will wrap around, right? What happens when you rotate 370deg?

lnxfergy
01-03-2009, 12:27 AM
That compass will wrap around, right? What happens when you rotate 370deg?

You get 10 degrees....

Am I missing something in your question? - The compass only returns 0.0-359.9 degrees

-Fergs