Thank you very much for your reply.
The reason for my question is that as far as I can see the option is already in the mcp23017.h library.
I just can't figure out how to use that command.
Unfortunately, I can't really find a demo or documentation where it says how to use the command.
When I look in the mcp23017.h library, it is these lines that make me think that I should be able to set one bit at a time.
' ==============================================================================
' Programma un solo bit della porta A
' Program only one bit of port A
' ------------------------------------------------------------------------------
Sub OUT_GPA_BIT(In DeviceAddress, In BIT_A, In State_Bit)
DataGpAByte = IN_GPA_BYTE (DeviceAddress)
DataGpAByte.BIT_A = State_Bit
OUT_GPA_BYTE (DeviceAddress, DataGpAByte)
End Sub
Kind regards
Gert
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
I have no idea who created that library and I don't have access to it on this PC but, from that code I would try:
if you wanted to set bit 7 to High for example:
OUT_GPA_BIT(mcp23017Address, 7, HIGH)
Last edit: Chris Roper 2024-12-20
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
@Gert:
Hi, I'm out of Rome these days for the holidays.
I return to Rome on January 7th, so as soon as I can I'll check the source of the lines you pointed out to me.
I check, test and possibly release a new corrected version.
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
an old example
;328p nano controlling two 28BYJ-48 Stepper Motors using interrupt
chip mega328p,16
include <mcp23017.h></mcp23017.h>
option Explicit
#define I2C_MODE Master
#define I2C_DATA PORTC.4
#define I2C_CLOCK PORTC.5
#define I2C_DISABLE_INTERRUPTS ON
'Optionally, you can reduce the I2C timings.
#define I2C_BIT_DELAY 0 us
#define I2C_CLOCK_DELAY 1 us
#define I2C_END_DELAY 0 us
define MCP23017_addr 0x4e
;#define MCP23017_IODIRA 0; make porta output
MCP23017_sendbyte (MCP23017_addr,MCP23017_IODIRA,0) ;set port a to out
;MCP23017_sendbyte(MCP23017_addr,MCP23017_GPIOA,0)
dim lmotdir,lmotor,rmotdir,rmotor,lmotval,rmotval as byte
lmotdir=255:lmotor=1:rmotdir=255:rmotor=1
;interrupt drives motor 100 Hz
; On Interrupt Timer0Match1 Call motors
Dim OCR0 AS byte alias OCR0A
Dim TCCR0 AS byte alias TCCR0B
WGM01 = 1 'Timer in CTC mode - required
OCR0 = 19
TCCR0 = 0x28
TCCR0 = TCCR0 or 0x05
;-------------------------
;
do
lmotdir=255:rmotdir=255
wait 2 s
lmotdir=1:rmotdir=1
wait 2 s
lmotdir=255:rmotdir=1
wait 2 s
lmotdir=1:rmotdir=255
wait 2 s
loop
;----- end
Sub motors
;left stepper motor
if lmotdir>0 then
if lmotdir=1 Then
lmotor++
if lmotor=9 then lmotor=1
else
lmotor---
if lmotor=0 then lmotor=8
end if
; ReadTable lmot,lmotor,lmotval
select case lmotor
case 1
lmotval=128
case 2
lmotval=192
case 3
lmotval=64
case 4
lmotval=96
case 5
lmotval=32
case 6
lmotval=48
case 7
lmotval=16
case 8
lmotval=144
End Select
Else
lmotval=0
end if
;right stepper motor
if rmotdir>0 then
if rmotdir=1 Then
rmotor++
if rmotor=9 then rmotor=1
else
rmotor---
if rmotor=0 then rmotor=8
end if
; ReadTable rmot,rmotor,rmotval
select case rmotor
case 1
rmotval=1
case 2
rmotval=3
case 3
rmotval=2
case 4
rmotval=6
case 5
rmotval=4
case 6
rmotval=12
case 7
rmotval=8
case 8
rmotval=9
End Select
else
rmotval=0
end if
MCP23017_sendbyte (MCP23017_addr,MCP23017_GPIOA,lmotval+rmotval) ;sets porta to lmotval+rmotval
End Sub
;
table lmot
128,192,64,96,32,48,16,144
end table
;
table rmot
1,3,2,6,4,12,8,9
end table
Hi,
Just started playing with mcp23017 and everything works fine and easy.
It works well to send a byte that sets the entire port.
But I simply can't figure out how to set a single bit at a time, e.g. bit 7 on port A
Can someone give me a clue?
Kind regards
Gert
Read the Port OR it with a Mask containing the bits you wish to set and Write the result back to the Port.
Hi Chris,
Thank you very much for your reply.
The reason for my question is that as far as I can see the option is already in the mcp23017.h library.
I just can't figure out how to use that command.
Unfortunately, I can't really find a demo or documentation where it says how to use the command.
When I look in the mcp23017.h library, it is these lines that make me think that I should be able to set one bit at a time.
' ==============================================================================
' Programma un solo bit della porta A
' Program only one bit of port A
' ------------------------------------------------------------------------------
Sub OUT_GPA_BIT(In DeviceAddress, In BIT_A, In State_Bit)
DataGpAByte = IN_GPA_BYTE (DeviceAddress)
DataGpAByte.BIT_A = State_Bit
OUT_GPA_BYTE (DeviceAddress, DataGpAByte)
End Sub
Kind regards
Gert
Hi Gert,
I have no idea who created that library and I don't have access to it on this PC but, from that code I would try:
if you wanted to set bit 7 to High for example:
OUT_GPA_BIT(mcp23017Address, 7, HIGH)
Last edit: Chris Roper 2024-12-20
Hi Chris,
I have tried with your suggestion. And everything else that occurred to me. But without success.
Ping the library writer. JackJames I believe.
Thanks for your suggestion Anobium.
Can you help me with a solution to my problem @jackjames
@Gert:
Sub OUT_GPA_BIT(In DeviceAddress, In BIT_A, In State_Bit)
@jackjames :
I'm still struggling to get it to work.
Tried different things and after switching to hardware i2c I get two errors when I compile my program.
The first one in line 213: HI2reCStart
So I changed this to: HI2CStart is that right or should it be HI2CRestart?
The second in line 419: STATE_BIT is not a bit or valid constant. Constant values should be 0 or 1
I inserted a line with: DIM STATE_BIT as Bit
After these changes it compiles without errors. But still can't get the command to work.
Last edit: Gert Klemmensen 2025-01-02
@Gert:
Hi, I'm out of Rome these days for the holidays.
I return to Rome on January 7th, so as soon as I can I'll check the source of the lines you pointed out to me.
I check, test and possibly release a new corrected version.
@jackjames
It is really appreciated. Many thanks!
an old example
;328p nano controlling two 28BYJ-48 Stepper Motors using interrupt
chip mega328p,16
include <mcp23017.h></mcp23017.h>
option Explicit
#define I2C_MODE Master
#define I2C_DATA PORTC.4
#define I2C_CLOCK PORTC.5
#define I2C_DISABLE_INTERRUPTS ON
'Optionally, you can reduce the I2C timings.
#define I2C_BIT_DELAY 0 us
#define I2C_CLOCK_DELAY 1 us
#define I2C_END_DELAY 0 us
define MCP23017_addr 0x4e
;#define MCP23017_IODIRA 0; make porta output
MCP23017_sendbyte (MCP23017_addr,MCP23017_IODIRA,0) ;set port a to out
;MCP23017_sendbyte(MCP23017_addr,MCP23017_GPIOA,0)
dim lmotdir,lmotor,rmotdir,rmotor,lmotval,rmotval as byte
lmotdir=255:lmotor=1:rmotdir=255:rmotor=1
;interrupt drives motor 100 Hz
; On Interrupt Timer0Match1 Call motors
;-------------------------
;
do
lmotdir=255:rmotdir=255
wait 2 s
lmotdir=1:rmotdir=1
wait 2 s
lmotdir=255:rmotdir=1
wait 2 s
lmotdir=1:rmotdir=255
wait 2 s
loop
;----- end
Sub motors
;left stepper motor
if lmotdir>0 then
if lmotdir=1 Then
lmotor++
if lmotor=9 then lmotor=1
else
lmotor---
if lmotor=0 then lmotor=8
end if
; ReadTable lmot,lmotor,lmotval
select case lmotor
case 1
lmotval=128
case 2
lmotval=192
case 3
lmotval=64
case 4
lmotval=96
case 5
lmotval=32
case 6
lmotval=48
case 7
lmotval=16
case 8
lmotval=144
End Select
Else
lmotval=0
end if
;right stepper motor
if rmotdir>0 then
if rmotdir=1 Then
rmotor++
if rmotor=9 then rmotor=1
else
rmotor---
if rmotor=0 then rmotor=8
end if
; ReadTable rmot,rmotor,rmotval
select case rmotor
case 1
rmotval=1
case 2
rmotval=3
case 3
rmotval=2
case 4
rmotval=6
case 5
rmotval=4
case 6
rmotval=12
case 7
rmotval=8
case 8
rmotval=9
End Select
else
rmotval=0
end if
MCP23017_sendbyte (MCP23017_addr,MCP23017_GPIOA,lmotval+rmotval) ;sets porta to lmotval+rmotval
End Sub
;
table lmot
128,192,64,96,32,48,16,144
end table
;
table rmot
1,3,2,6,4,12,8,9
end table
Last edit: stan cartwright 2025-01-05
Hi @Stan,
Thank you very much for your example.
I have no problem sending a BYTE to either PORTA or B.
It's when I just want to set a single BIT on, for example PORTA.
durr. can't you mask the bit in a byte. dunno , long time since using gcb :)
I modified the two routines.
Now it works.
He had no problems with the old compilers.
I ask evan to replace the old library with this updated one.
@jackjames
Just tested it.
Thank you very much!!
Updated library:
Here is the merged file from the Build system.
Dates and other non functional changes were in the pipeline.