RobTillaart / MCP23S17

Arduino library for SPI based MCP23S17 16 channel port expander
MIT License
27 stars 11 forks source link

Use of Interrupt Pins #18

Closed maklumatpemankanan closed 1 year ago

maklumatpemankanan commented 1 year ago

hello,

how do i configure the Pins that the INT-Pins react on a change of the Gpio-Values ? Is there any Example ?

RobTillaart commented 1 year ago

Thanks for the question, I need to check the code to recall the details of this library.

RobTillaart commented 1 year ago

The library does not have any interrupt (supporting) code.

I am looking in the datasheet and see in table 2.1 that there are 2 INT pins on the chip.

Write to the GPINTENA register to enable interrupts of the pins of PORT A Write to the GPINTENB register to enable interrupts of the pins of PORT B

Paragraph 3.5.5 INTERRUPT CONTROL REGISTER seems to be a must read,

maklumatpemankanan commented 1 year ago

i can do this with the write16-function of your Library?

RobTillaart commented 1 year ago

No,

you must make the readReg() and writeReg() public.

See the mcp23S17.h file.

private:
  //       access to low level registers (just make these two functions public).
  //       USE WITH CARE !!!
  bool     writeReg(uint8_t reg, uint8_t value);
  uint8_t  readReg(uint8_t reg);

Those two functions allow you to write to any register defined in MCP23S17_registers.h Details what to write are described in chapter 3.5 of the datasheet.

maklumatpemankanan commented 1 year ago

thank you !

RobTillaart commented 1 year ago

If you get the interrupt working I am interested in a example code to add to the library examples. At the moment I have no plans to add interrupt configuration functions to the library. However I could make readReg() and writeReg() public by default. That would allow people to access all registers directly.

maklumatpemankanan commented 1 year ago

i write here if i have a working solution. in the moment i try to implement a new function to enable Interrupts for PortA an PortB .

maklumatpemankanan commented 1 year ago

hello Rob,

i have found coincidentally found another Library where the Interupthandling is implenented. So i will not try to do this at your Lib. Maybe you can see on this Library how its work. Here the Link to the Lib : https://github.com/n0mjs710/MCP23S17.

best regards !

RobTillaart commented 1 year ago

OK, Still interested in your code how you do interrupts with that lib.

From the .cpp file

Interrupt features are not implemented in this version byte based (portA, portB) functions are not implemented in this version

maklumatpemankanan commented 1 year ago

with this lib below i can use the Interruptpins INTA and INTB with this examplecode:

#include <SPI.h>              
#include <MCP23S17.h>
/*
 * SPI:
 * MISO 19  blau
 * MOSI 23  orange
 * SCK  18  gelb
*/
#define I2C_INT 17

//Define Expanders

MCP expander0(0, 5);  //Address 0, ChipSelect-Pin 5
MCP expander1(1, 5);  //Address 0, ChipSelect-Pin 5

void setup() {
  Serial.begin(115200);
  //Serial.print("MCP23S17_LIB_VERSION: ");
  //Serial.println(MCP23S17_LIB_VERSION);
  Serial.println("\n* SPI Switches *");
  //Interrupt Pin for Switches
  pinMode(I2C_INT, INPUT_PULLUP);
  //Set Chip as Input
  expander0.begin();
  //enable Interrupt for all Pins
  expander0.byteWrite(0x04, 0xFF);
  expander0.byteWrite(0x05, 0xFF);

  for (int i = 1; i <= 16; i++) {
    expander0.pinMode(i, HIGH);      // Use bit-write mode to set all of the current pin on inputchip to be inputs
    expander0.pullupMode(i, HIGH);   // Use bit-write mode to Turn on the internal pull-down resistor for the current pin
  }

  expander1.begin();
  for (int i = 1; i <= 16; i++) {
    expander1.pinMode(i, LOW);      // Use bit-write mode to set all of the current pin on inputchip to be inputs
    expander1.digitalWrite(i, LOW);
  }

}

void loop() {

  if(digitalRead(I2C_INT) == LOW){
    Serial.print("\nInterrupt detected!\n");
  }

  if(digitalRead(I2C_INT) == LOW){
    Serial.print("Read the Pins : \n");
    //Read all Pins from Expander 0 
    for (int i = 1; i <=16; i++) {
      int value;                      
      value = expander0.digitalRead(i);
      Serial.print("[" + String(i) + ":" + String(value) +"]");
      if( value == 1){
        expander1.digitalWrite(i, LOW);
      }
      if( value == 0){
        expander1.digitalWrite(i, HIGH);
      }

    }
  }

  delay(50); //Little bit debouncing
}

this works fine for me at this moment.

RobTillaart commented 1 year ago

OK, so you are polling the interrupt pin. Creative solution!

maklumatpemankanan commented 1 year ago

Yes, this was my intension. When one or more Gipos change then the Interrupt gives a signal to the ESP32 and a function to do something is starting.

RobTillaart commented 1 year ago

If the issue is solved by this solution, you may close the issue! Thanks for sharing the solution!