PDA

View Full Version : BS sx + stepper motor + PCF8574



o_wan
07-27-2005, 05:51 PM
hi all,

I've working on hooking up with 2 stepper motors (+ULN2803) + PCF8574, below is the code that I wrote for 1 stepper (P0-P3). I would like to add 1 more stepper to P4-P7 (of the same PCF8574).
I don't quite understand the shifting of bits and how it works in PCF8574, please help for changing the code to drive 2 stepper or show me pointers.

code:
' ------------------------------------------------------------------------------
' I/O Definitions
' ------------------------------------------------------------------------------
'
SDA CON 8 ' I2C serial data line
SCL CON 9 ' I2C serial clock line


' ------------------------------------------------------------------------------
' Constants
' ------------------------------------------------------------------------------

DevType CON %0100 << 4 ' device type
DevAddr CON %000 << 1 ' address = %000 -> %111
Wr8574 CON DevType | DevAddr | 0 ' write to PCF8574
Rd8574 CON DevType | DevAddr | 1 ' read from PCF8574

ACK CON 0 ' acknowledge bit
NAK CON 1 ' no ack bit

MixDDR CON %11110000 ' 1 = input for mixed I/O

Yes CON 0
No CON 1

CrsrXY CON 2 ' DEBUG Position Control


' ------------------------------------------------------------------------------
' Variables
' ------------------------------------------------------------------------------

i2cSDA VAR NIB ' I2C serial data pin
i2cData VAR BYTE ' data to/from I2C device
i2cWork VAR BYTE ' work byte for I2C TX code
i2cAck VAR BIT ' ACK bit from device

counter VAR NIB


i VAR NIB
delay VAR BYTE

delay = 40 'slow the step speed

' ------------------------------------------------------------------------------
' EEPROM Data
' ------------------------------------------------------------------------------


' ------------------------------------------------------------------------------
' Initialization
' ------------------------------------------------------------------------------

Initialize:
PAUSE 250 ' let DEBUG open
DEBUG CLS, "PCF8574 Demo"
i2cSDA = SDA ' define SDA pin
i2cData = %11111111 ' clear outputs
GOSUB Write_PCF8574
IF (i2cAck = ACK) THEN Main ' device is present

DEBUG CLS, "Error: No ACK from PCF8574"
END


' ------------------------------------------------------------------------------
' Program Code
' ------------------------------------------------------------------------------
Main:
FOR i = 1 TO 10
GOSUB Main1
PAUSE delay
GOSUB Main2
PAUSE delay
GOSUB Main3
PAUSE delay
GOSUB Main4
PAUSE delay
NEXT
GOTO Main

Main1:
DEBUG CrsrXY, 10, 2, BIN4 i2cData ' display counter on screen
i2cData = %0101 'I/O pins 0 and 2 high
GOSUB Write_PCF8574 ' display counter on LEDs
RETURN

Main2:
DEBUG CrsrXY, 10, 2, BIN4 i2cData ' display counter on screen
i2cData = %1001 'I/O pins 0 and 2 high
GOSUB Write_PCF8574 ' display counter on LEDs
RETURN

Main3:
DEBUG CrsrXY, 10, 2, BIN4 i2cData ' display counter on screen
i2cData = %1010 'I/O pins 0 and 2 high
GOSUB Write_PCF8574 ' display counter on LEDs
RETURN

Main4:
DEBUG CrsrXY, 10, 2, BIN4 i2cData ' display counter on screen
i2cData = %0110 'I/O pins 0 and 2 high
GOSUB Write_PCF8574 ' display counter on LEDs
RETURN


' ------------------------------------------------------------------------------
' Subroutines
' ------------------------------------------------------------------------------

' Data to be sent is passed in i2cData

Write_PCF8574:
GOSUB I2C_Start ' send Start
i2cWork = Wr8574 ' send address
GOSUB I2C_TX_Byte
i2cWork = i2cData
GOSUB I2C_TX_Byte ' send i2cData to device
GOSUB I2C_TX_Byte ' force to pins
GOSUB I2C_Stop ' send Stop
RETURN


' Data received is returned in i2cData




' ------------------------------------------------------------------------------
' Low Level I2C Subroutines
' ------------------------------------------------------------------------------

' --- Start ---

I2C_Start: ' I2C start bit sequence
INPUT i2cSDA
INPUT SCL
LOW i2cSDA ' SDA -> low while SCL high

Clock_Hold:
IF (INS.LOWBIT(SCL) = 0) THEN Clock_Hold ' device ready?
RETURN


' --- Transmit ---

I2C_TX_Byte:
SHIFTOUT i2cSDA,SCL,MSBFIRST,[i2cWork] ' send byte to device
SHIFTIN i2cSDA,SCL,MSBPRE,[i2cAck\1] ' get acknowledge bit
RETURN



' --- Stop ---

I2C_Stop: ' I2C stop bit sequence
LOW i2cSDA
INPUT SCL
INPUT i2cSDA ' SDA --> high while SCL high
RETURN

Cheers,

Jon Williams
07-27-2005, 09:17 PM
Let me see if I can help without having to go through your code.... Let's say you have two steppers, and the coil states are defined by nib variables: motor1 (P0..P3)·and motor2 (P4..P7).· You can create a single byte var to send to the PCF8574 like this:

· i2cData = motor2 << 4 + motor1

That will align the outputs correctly and allow you to update the coils on one motor without changing the other.



▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
Jon Williams
Applications Engineer, Parallax