Updating Readme file, and src files
This commit is contained in:
parent
2ea33655a5
commit
400a727892
79
README.md
79
README.md
@ -56,85 +56,44 @@ At **FABLAB Bahrain**, we're revolutionizing the world of IoT devices with our c
|
|||||||
### Installation
|
### Installation
|
||||||
|
|
||||||
1. Download or clone this repository.
|
1. Download or clone this repository.
|
||||||
2. Copy the `I2CRelay`, `I2CMasterUtils`, and related library folders to your Arduino `libraries` directory.
|
2. Copy the `I2CRelay`, and related library folders to your Arduino `libraries` directory.
|
||||||
3. Restart the Arduino IDE.
|
3. Restart the Arduino IDE.
|
||||||
|
|
||||||
#### Files
|
#### Files
|
||||||
|
|
||||||
The library is composed of several files, each with a specific role:
|
The library is composed of several files, each with a specific role:
|
||||||
|
|
||||||
1. **I2CMasterUtils.h** [3]
|
1. **I2CRelay.h** [5]
|
||||||
- This header file defines the `I2CMasterUtils` class which contains static methods for I2C operations such as scanning for devices and changing slave addresses.
|
|
||||||
|
|
||||||
2. **I2CMasterUtils.cpp** [2]
|
|
||||||
- Contains the implementation of methods defined in `I2CMasterUtils.h`.
|
|
||||||
|
|
||||||
3. **I2CRelay.h** [5]
|
|
||||||
- Defines the `I2CRelay` class, which extends the functionality to control relays over I2C.
|
- Defines the `I2CRelay` class, which extends the functionality to control relays over I2C.
|
||||||
|
|
||||||
4. **I2CRelay.cpp** [4]
|
2. **I2CRelay.cpp** [4]
|
||||||
- Contains the implementation of methods for the `I2CRelay` class.
|
- Contains the implementation of methods for the `I2CRelay` class.
|
||||||
|
|
||||||
---
|
---
|
||||||
|
|
||||||
### Versatility
|
### Versatility
|
||||||
|
|
||||||
The I2CMotor offers exceptional versatility, as it can function as a standalone device and can be adapted to be USB-controlled instead of relying solely on I2C communication. This flexibility allows users to easily integrate the motor into a wide range of projects and control environments. Furthermore, the motor’s firmware can be reprogrammed to support Wi-Fi and Bluetooth connectivity, enabling wireless control and making it ideal for modern applications in robotics, automation, and IoT. This adaptability ensures that the I2CMotor can meet diverse requirements and evolve with your project’s needs.
|
The I2CRelay library offers broad versatility for automation through its configurable I2C addressing, expandable relay control, and cross-platform compatibility. User-friendly commands and customizable hardware pins simplify integration into diverse projects, from IoT and home automation to industrial control. Its efficient, non-blocking operation and persistent configuration via EEPROM ensure a scalable and reliable relay control system.
|
||||||
|
|
||||||
---
|
---
|
||||||
|
|
||||||
### API Overview
|
### API Overview
|
||||||
|
|
||||||
- **scanI2C(Stream &output = Serial)**
|
# I2CRelay Library API Overview
|
||||||
- Scans the I2C bus for connected devices and prints their addresses.
|
|
||||||
|
|
||||||
- **changeSlaveAddress(uint8_t oldAddr, uint8_t newAddr, Stream &output = Serial)**
|
| Method / Constructor | Description | Parameters / Usage Example |
|
||||||
- Sends a command to change the slave address of a device.
|
|---------------------------------------------------|-------------------------------------------------------------------------------------------------------------|------------------------------------------------------|
|
||||||
|
| `I2CRelay(uint8_t address = 0x08, uint8_t sda = 8, uint8_t scl = 3)` | Create an I2CRelay object with optional I2C address and pin selection. | `I2CRelay relay;`<br>`I2CRelay relay(0x10, 21, 22);` |
|
||||||
|
| `void begin()` | Initialize I2C communication with the configured pins. | `relay.begin();` |
|
||||||
|
| `void setRelay(uint8_t relayNum, uint8_t state)` | Turn relay (1–8) ON or OFF. | `relay.setRelay(3, 1); // ON relay 3` |
|
||||||
|
| `void setAllRelays(uint8_t state)` | Turn all relays ON or OFF at once. | `relay.setAllRelays(0); // OFF all relays` |
|
||||||
|
| `void setDeviceName(const String &name)` | Set the name of the I2C relay device (up to 24 chars). | `relay.setDeviceName("MainPanel");` |
|
||||||
|
| `void setI2CAddress(uint8_t newAddr)` | Change the I2C address of the relay slave. | `relay.setI2CAddress(0x12);` |
|
||||||
|
| `String getIdentification()` | Query the slave for its identification string (address, type, name, states). | `String id = relay.getIdentification();` |
|
||||||
|
| `void handleSerialCommand(const String &cmd)` | Parse and execute a serial command string (e.g., `"r 2 1"`, `"all 0"`). | `relay.handleSerialCommand("r 2 1");` |
|
||||||
|
|
||||||
- **parseChangeAddressCommand(const String &input, uint8_t &oldAddr, uint8_t &newAddr)**
|
**Notes:**
|
||||||
- Parses an input string to extract the old and new slave addresses from a "ch" command.
|
- `relayNum` is 1–8 (user-facing), mapped internally to 0–7.
|
||||||
|
- `state` is `1` (ON) or `0` (OFF).
|
||||||
|
- All methods are non-blocking except `setAllRelays`, which adds a small delay between commands.
|
||||||
|
|
||||||
#### Methods
|
|
||||||
|
|
||||||
- **I2CRelay(uint8_t slaveAddress)**
|
|
||||||
- Constructor that initializes the `I2CRelay` object with the given slave address.
|
|
||||||
|
|
||||||
- **begin()**
|
|
||||||
- Initializes the I2C bus for communication.
|
|
||||||
|
|
||||||
- **setRelay(uint8_t relayIndex, bool state)**
|
|
||||||
- Sets the state of a specific relay on the slave device.
|
|
||||||
|
|
||||||
- **scanDevices(uint8_t* foundAddresses, uint8_t maxDevices)**
|
|
||||||
- Scans the I2C bus for connected devices and returns their addresses up to `maxDevices`.
|
|
||||||
|
|
||||||
- **setAddress(uint8_t newAddress)**
|
|
||||||
- Changes the address of the relay slave.
|
|
||||||
|
|
||||||
- **handleI2CCommand()**
|
|
||||||
- Handles incoming I2C commands.
|
|
||||||
|
|
||||||
### Usage Example
|
|
||||||
|
|
||||||
To use this library, you would typically include the necessary files and create instances of `I2CMasterUtils` and `I2CRelay`. Here’s a simple example:
|
|
||||||
|
|
||||||
```cpp
|
|
||||||
#include "I2CMasterUtils.h"
|
|
||||||
#include "I2CRelay.h"
|
|
||||||
|
|
||||||
void setup() {
|
|
||||||
Serial.begin(9600);
|
|
||||||
|
|
||||||
I2CMasterUtils::scanI2C();
|
|
||||||
|
|
||||||
uint8_t newAddress = 0x54;
|
|
||||||
uint8_t oldAddress = CMD_CHANGE_ADDR; // Assuming CMD_CHANGE_ADDR is defined in I2CCommands.h
|
|
||||||
I2CMasterUtils::changeSlaveAddress(oldAddress, newAddress);
|
|
||||||
}
|
|
||||||
|
|
||||||
void loop() {
|
|
||||||
// Example usage of I2CRelay
|
|
||||||
I2CRelay relay(0x54); // Use the newly assigned address
|
|
||||||
relay.begin();
|
|
||||||
relay.setRelay(1, HIGH); // Set relay 1 to ON
|
|
||||||
}
|
|
@ -1,65 +1,23 @@
|
|||||||
#include <Wire.h>
|
|
||||||
#include <I2CRelay.h>
|
#include <I2CRelay.h>
|
||||||
#include <I2CMasterUtils.h>
|
|
||||||
|
|
||||||
I2CRelay relayMaster(0x08); // Default address, can be changed via setAddress()
|
I2CRelay relay;
|
||||||
|
|
||||||
void setup() {
|
void setup() {
|
||||||
Serial.begin(115200);
|
Serial.begin(115200);
|
||||||
delay(1000);
|
relay.begin();
|
||||||
relayMaster.begin();
|
Serial.println("8-Relay I2C Master Ready.");
|
||||||
Serial.println("Enter:");
|
Serial.println("Commands:");
|
||||||
Serial.println(" s - to scan I2C bus");
|
Serial.println(" r <n> <0|1> - Set relay n (1-8) OFF/ON");
|
||||||
Serial.println(" ch <old> <new> - to change slave address");
|
Serial.println(" all <0|1> - Set all relays OFF/ON");
|
||||||
Serial.println(" <relay> <on/off> - to set relay (e.g. 3 on)");
|
Serial.println(" name <newname> - Set device name");
|
||||||
|
Serial.println(" addr <newaddr> - Set I2C address (8-119)");
|
||||||
|
Serial.println(" id - Query identification string");
|
||||||
}
|
}
|
||||||
|
|
||||||
void loop() {
|
void loop() {
|
||||||
if (Serial.available()) {
|
if (Serial.available()) {
|
||||||
String input = Serial.readStringUntil('\n');
|
String cmd = Serial.readStringUntil('\n');
|
||||||
input.trim();
|
cmd.trim();
|
||||||
|
relay.handleSerialCommand(cmd);
|
||||||
if (input == "s") {
|
|
||||||
I2CMasterUtils::scanI2C();
|
|
||||||
} else if (input.startsWith("ch")) {
|
|
||||||
uint8_t oldAddr, newAddr;
|
|
||||||
if (I2CMasterUtils::parseChangeAddressCommand(input, oldAddr, newAddr)) {
|
|
||||||
I2CMasterUtils::changeSlaveAddress(oldAddr, newAddr);
|
|
||||||
relayMaster.setAddress(newAddr); // Update master's address
|
|
||||||
Serial.print("Changed address to 0x");
|
|
||||||
Serial.println(newAddr, HEX);
|
|
||||||
} else {
|
|
||||||
Serial.println("Invalid command format. Use: ch <old_addr> <new_addr>");
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
int spaceIndex = input.indexOf(' ');
|
|
||||||
if (spaceIndex > 0) {
|
|
||||||
String relayStr = input.substring(0, spaceIndex);
|
|
||||||
String stateStr = input.substring(spaceIndex + 1);
|
|
||||||
|
|
||||||
int relayNum = relayStr.toInt();
|
|
||||||
bool state = false;
|
|
||||||
|
|
||||||
stateStr.toLowerCase();
|
|
||||||
if (stateStr == "on") state = true;
|
|
||||||
else if (stateStr == "off") state = false;
|
|
||||||
else {
|
|
||||||
Serial.println("Invalid state! Use 'on' or 'off'.");
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (relayNum >= 1 && relayNum <= 8) {
|
|
||||||
relayMaster.setRelay(relayNum, state);
|
|
||||||
Serial.print("Relay ");
|
|
||||||
Serial.print(relayNum);
|
|
||||||
Serial.print(" turned ");
|
|
||||||
Serial.println(state ? "ON" : "OFF");
|
|
||||||
} else {
|
|
||||||
Serial.println("Invalid relay number! Use 1-8.");
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
Serial.println("Invalid command! Format: <relay_number> <on/off>");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,65 +1,105 @@
|
|||||||
#include <Wire.h>
|
#include <Wire.h>
|
||||||
#include <EEPROM.h>
|
#include <EEPROM.h>
|
||||||
|
|
||||||
// EEPROM settings
|
#define DEFAULT_ADDRESS 0x08
|
||||||
#define ADDR_EEPROM_LOC 0
|
#define MAX_NAME_LENGTH 24
|
||||||
#define EEPROM_SIZE 64
|
|
||||||
|
|
||||||
// Relay pins: GPIO0 to GPIO7
|
// EEPROM Structure
|
||||||
|
struct Config {
|
||||||
|
uint8_t address;
|
||||||
|
char deviceName[MAX_NAME_LENGTH+1];
|
||||||
|
uint8_t relayStates;
|
||||||
|
};
|
||||||
|
|
||||||
|
Config config;
|
||||||
const int relayPins[8] = {0, 1, 2, 3, 4, 5, 6, 7}; // GPIOs 0-7
|
const int relayPins[8] = {0, 1, 2, 3, 4, 5, 6, 7}; // GPIOs 0-7
|
||||||
|
|
||||||
uint8_t i2cAddress;
|
void handleCommand(int numBytes);
|
||||||
|
void saveConfig();
|
||||||
// Unified I2C receive event
|
void loadConfig();
|
||||||
void receiveEvent(int howMany) {
|
void emergencyStop();
|
||||||
if (howMany >= 2) {
|
|
||||||
uint8_t first = Wire.read();
|
|
||||||
uint8_t second = Wire.read();
|
|
||||||
|
|
||||||
// Check for address change command
|
|
||||||
if (first == 0xAA) {
|
|
||||||
// Change I2C address and store in EEPROM
|
|
||||||
uint8_t newAddr = second;
|
|
||||||
EEPROM.write(ADDR_EEPROM_LOC, newAddr);
|
|
||||||
EEPROM.commit();
|
|
||||||
Serial.print("I2C address changed to: 0x");
|
|
||||||
Serial.println(newAddr, HEX);
|
|
||||||
delay(100);
|
|
||||||
ESP.restart();
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Otherwise, treat as relay control
|
|
||||||
int relay = first; // Relay number: 1-8
|
|
||||||
int state = second; // State: 1=ON, 0=OFF
|
|
||||||
if (relay >= 1 && relay <= 8) {
|
|
||||||
digitalWrite(relayPins[relay - 1], state ? LOW : HIGH); // Active LOW relays
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void setup() {
|
void setup() {
|
||||||
Serial.begin(115200);
|
Serial.begin(115200);
|
||||||
EEPROM.begin(EEPROM_SIZE);
|
EEPROM.begin(sizeof(Config));
|
||||||
|
loadConfig();
|
||||||
|
|
||||||
// Read I2C address from EEPROM or use default
|
// Initialize relays
|
||||||
i2cAddress = EEPROM.read(ADDR_EEPROM_LOC);
|
for(int i=0; i<8; i++) {
|
||||||
if (i2cAddress == 0xFF || i2cAddress == 0) i2cAddress = 0x08; // Default address
|
|
||||||
|
|
||||||
Serial.print("Using I2C address: 0x");
|
|
||||||
Serial.println(i2cAddress, HEX);
|
|
||||||
|
|
||||||
// Initialize relay pins
|
|
||||||
for (int i = 0; i < 8; i++) {
|
|
||||||
pinMode(relayPins[i], OUTPUT);
|
pinMode(relayPins[i], OUTPUT);
|
||||||
digitalWrite(relayPins[i], HIGH); // Relays OFF initially (active LOW)
|
digitalWrite(relayPins[i], HIGH); // Active-low logic
|
||||||
}
|
}
|
||||||
|
|
||||||
// Start I2C slave
|
Wire.onReceive(handleCommand);
|
||||||
Wire.begin(i2cAddress);
|
Wire.onRequest([]() {
|
||||||
Wire.onReceive(receiveEvent);
|
String response = String(config.address) + ",8-relay," +
|
||||||
|
config.deviceName + "," +
|
||||||
|
String(config.relayStates, BIN);
|
||||||
|
Wire.print(response);
|
||||||
|
});
|
||||||
|
|
||||||
|
Wire.begin((uint8_t)config.address);
|
||||||
}
|
}
|
||||||
|
|
||||||
void loop() {
|
void loop() { /* Empty */ }
|
||||||
// Nothing needed here for basic operation
|
|
||||||
|
void handleCommand(int numBytes) {
|
||||||
|
uint8_t cmd = Wire.read();
|
||||||
|
|
||||||
|
switch(cmd) {
|
||||||
|
case 0xA0: // Set relay state
|
||||||
|
if(numBytes == 3) {
|
||||||
|
uint8_t relay = Wire.read();
|
||||||
|
uint8_t state = Wire.read();
|
||||||
|
if(relay < 8) {
|
||||||
|
digitalWrite(relayPins[relay], state ? LOW : HIGH);
|
||||||
|
bitWrite(config.relayStates, relay, state);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 0xB0: // Emergency stop
|
||||||
|
emergencyStop();
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 0xC0: // Set address
|
||||||
|
if(numBytes == 2) {
|
||||||
|
config.address = Wire.read();
|
||||||
|
saveConfig();
|
||||||
|
Wire.begin((uint8_t)config.address);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 0xD0: // Set device name
|
||||||
|
if(numBytes > 1) {
|
||||||
|
uint8_t i = 0;
|
||||||
|
while(Wire.available() && i < MAX_NAME_LENGTH) {
|
||||||
|
config.deviceName[i++] = Wire.read();
|
||||||
|
}
|
||||||
|
config.deviceName[i] = '\0';
|
||||||
|
saveConfig();
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void emergencyStop() {
|
||||||
|
for(int i=0; i<8; i++) {
|
||||||
|
digitalWrite(relayPins[i], HIGH);
|
||||||
|
}
|
||||||
|
config.relayStates = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
void loadConfig() {
|
||||||
|
EEPROM.get(0, config);
|
||||||
|
if(config.address < 0x08 || config.address > 0x77) {
|
||||||
|
config.address = DEFAULT_ADDRESS;
|
||||||
|
strcpy(config.deviceName, "8-Relay Module");
|
||||||
|
saveConfig();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void saveConfig() {
|
||||||
|
EEPROM.put(0, config);
|
||||||
|
EEPROM.commit();
|
||||||
}
|
}
|
||||||
|
20
keywords.txt
20
keywords.txt
@ -1,16 +1,8 @@
|
|||||||
#######################################
|
I2CRelay KEYWORD1
|
||||||
# Syntax coloring for Relay8I2C Library
|
|
||||||
#######################################
|
|
||||||
|
|
||||||
# Classes
|
|
||||||
RelayI2CMaster KEYWORD1
|
|
||||||
I2CMasterUtils KEYWORD1
|
|
||||||
|
|
||||||
# Methods
|
|
||||||
begin KEYWORD2
|
begin KEYWORD2
|
||||||
setRelay KEYWORD2
|
setRelay KEYWORD2
|
||||||
scanI2C KEYWORD2
|
setAllRelays KEYWORD2
|
||||||
changeSlaveAddress KEYWORD2
|
setDeviceName KEYWORD2
|
||||||
|
setI2CAddress KEYWORD2
|
||||||
# Constants
|
getIdentification KEYWORD2
|
||||||
CMD_CHANGE_ADDR LITERAL1
|
handleSerialCommand KEYWORD2
|
||||||
|
@ -1,9 +1,9 @@
|
|||||||
name=FABLAB Relay
|
name=I2CRelay
|
||||||
version=1.0.0
|
version=1.0.0
|
||||||
author=Fatima Idrees <fatimaxidrees@gmail.com>
|
author=Fatima Idrees <fatimaxidrees@gmail.com>
|
||||||
maintainer=Fatima Idrees <fatimaxidrees@gmail.com>
|
maintainer=Fatima Idrees <fatimaxidrees@gmail.com>
|
||||||
sentence=Control DC motors via I2C with scanning and configuration utilities.
|
sentence=Simple I2C master library for controlling 8-channel relay modules.
|
||||||
paragraph=Provides easy control of 8-relay modules via I2C communication with dynamic address configuration. Includes master/slave implementation for ESP8266/Arduino platforms.
|
paragraph=I2CRelay allows easy control of up to 8 relays on a remote I2C slave device, with support for device naming, address changes, and identification queries. Designed for ESP32 and Arduino boards with configurable I2C pins.
|
||||||
category=Device Control
|
category=Device Control
|
||||||
url=https://github.com/fablabbh/I2CMasterUtils
|
url=https://git.takeone.bh/fatimaxsen/I2CRelay.git
|
||||||
architectures=*
|
architectures=*
|
||||||
|
@ -1,6 +0,0 @@
|
|||||||
#ifndef I2C_COMMANDS_H
|
|
||||||
#define I2C_COMMANDS_H
|
|
||||||
|
|
||||||
#define CMD_CHANGE_ADDR 0xAA // Use the same value as in your slave
|
|
||||||
|
|
||||||
#endif
|
|
@ -1,36 +0,0 @@
|
|||||||
#include "I2CMasterUtils.h"
|
|
||||||
#include "I2CCommands.h"
|
|
||||||
|
|
||||||
void I2CMasterUtils::scanI2C(Stream &output) {
|
|
||||||
output.println("Scanning for I2C devices...");
|
|
||||||
for (uint8_t addr = 1; addr < 127; addr++) {
|
|
||||||
Wire.beginTransmission(addr);
|
|
||||||
if (Wire.endTransmission() == 0) {
|
|
||||||
output.print("Found device at 0x");
|
|
||||||
output.println(addr, HEX);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void I2CMasterUtils::changeSlaveAddress(uint8_t oldAddr, uint8_t newAddr, Stream &output) {
|
|
||||||
Wire.beginTransmission(oldAddr);
|
|
||||||
Wire.write(CMD_CHANGE_ADDR); // Use the command code from I2CCommands.h
|
|
||||||
Wire.write(newAddr);
|
|
||||||
Wire.endTransmission();
|
|
||||||
output.print("Sent address change command to 0x");
|
|
||||||
output.print(oldAddr, HEX);
|
|
||||||
output.print(" -> 0x");
|
|
||||||
output.println(newAddr, HEX);
|
|
||||||
}
|
|
||||||
|
|
||||||
bool I2CMasterUtils::parseChangeAddressCommand(const String &input, uint8_t &oldAddr, uint8_t &newAddr) {
|
|
||||||
if (!input.startsWith("ch")) return false;
|
|
||||||
int o, n;
|
|
||||||
int matched = sscanf(input.c_str(), "ch %x %x", &o, &n);
|
|
||||||
if (matched == 2) {
|
|
||||||
oldAddr = (uint8_t)o;
|
|
||||||
newAddr = (uint8_t)n;
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
return false;
|
|
||||||
}
|
|
@ -1,14 +0,0 @@
|
|||||||
#ifndef I2CMASTERUTILS_H
|
|
||||||
#define I2CMASTERUTILS_H
|
|
||||||
|
|
||||||
#include <Arduino.h>
|
|
||||||
#include <Wire.h>
|
|
||||||
|
|
||||||
class I2CMasterUtils {
|
|
||||||
public:
|
|
||||||
static void scanI2C(Stream &output = Serial);
|
|
||||||
static void changeSlaveAddress(uint8_t oldAddr, uint8_t newAddr, Stream &output = Serial);
|
|
||||||
static bool parseChangeAddressCommand(const String &input, uint8_t &oldAddr, uint8_t &newAddr);
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif
|
|
115
src/I2CRelay.cpp
115
src/I2CRelay.cpp
@ -1,35 +1,102 @@
|
|||||||
#include <Wire.h>
|
|
||||||
#include <Arduino.h>
|
|
||||||
#include "I2CRelay.h"
|
#include "I2CRelay.h"
|
||||||
#include "I2CMasterUtils.h"
|
|
||||||
#include "I2CCommands.h"
|
|
||||||
|
|
||||||
I2CRelay::I2CRelay(uint8_t slaveAddress) : _slaveAddress(slaveAddress) {}
|
I2CRelay::I2CRelay(uint8_t address, uint8_t sda, uint8_t scl)
|
||||||
|
: _address(address), _sda(sda), _scl(scl) {}
|
||||||
void I2CRelay::setAddress(uint8_t newAddress) {
|
|
||||||
_slaveAddress = newAddress;
|
|
||||||
}
|
|
||||||
|
|
||||||
void I2CRelay::begin() {
|
void I2CRelay::begin() {
|
||||||
Wire.begin();
|
Wire.begin(_sda, _scl);
|
||||||
}
|
}
|
||||||
|
|
||||||
void I2CRelay::setRelay(uint8_t relayIndex, bool state) {
|
void I2CRelay::setRelay(uint8_t relayNum, uint8_t state) {
|
||||||
Wire.beginTransmission(_slaveAddress);
|
if (relayNum < 1 || relayNum > 8) return;
|
||||||
Wire.write(relayIndex);
|
Wire.beginTransmission(_address);
|
||||||
Wire.write(state ? 1 : 0);
|
Wire.write(0xA0);
|
||||||
|
Wire.write(relayNum - 1); // Map 1-8 to 0-7
|
||||||
|
Wire.write(state);
|
||||||
Wire.endTransmission();
|
Wire.endTransmission();
|
||||||
}
|
}
|
||||||
|
|
||||||
uint8_t I2CRelay::scanDevices(uint8_t* foundAddresses, uint8_t maxDevices) {
|
void I2CRelay::setAllRelays(uint8_t state) {
|
||||||
uint8_t count = 0;
|
for (uint8_t i = 1; i <= 8; i++) {
|
||||||
for(uint8_t addr = 1; addr < 127; addr++) {
|
setRelay(i, state);
|
||||||
Wire.beginTransmission(addr);
|
delay(10);
|
||||||
if(Wire.endTransmission() == 0) {
|
}
|
||||||
if(count < maxDevices) {
|
}
|
||||||
foundAddresses[count++] = addr;
|
|
||||||
|
void I2CRelay::setDeviceName(const String &name) {
|
||||||
|
Wire.beginTransmission(_address);
|
||||||
|
Wire.write(0xD0);
|
||||||
|
for (uint8_t i = 0; i < name.length() && i < 24; i++) {
|
||||||
|
Wire.write(name[i]);
|
||||||
|
}
|
||||||
|
Wire.endTransmission();
|
||||||
|
}
|
||||||
|
|
||||||
|
void I2CRelay::setI2CAddress(uint8_t newAddr) {
|
||||||
|
if (newAddr < 8 || newAddr > 119) return;
|
||||||
|
Wire.beginTransmission(_address);
|
||||||
|
Wire.write(0xC0);
|
||||||
|
Wire.write(newAddr);
|
||||||
|
Wire.endTransmission();
|
||||||
|
}
|
||||||
|
|
||||||
|
String I2CRelay::getIdentification() {
|
||||||
|
Wire.requestFrom(_address, (uint8_t)40);
|
||||||
|
String id = "";
|
||||||
|
while (Wire.available()) {
|
||||||
|
char c = Wire.read();
|
||||||
|
id += c;
|
||||||
|
}
|
||||||
|
return id;
|
||||||
|
}
|
||||||
|
|
||||||
|
void I2CRelay::handleSerialCommand(const String &cmd) {
|
||||||
|
if (cmd.startsWith("r ")) {
|
||||||
|
int space1 = cmd.indexOf(' ');
|
||||||
|
int space2 = cmd.indexOf(' ', space1 + 1);
|
||||||
|
if (space1 > 0 && space2 > space1) {
|
||||||
|
int relay = cmd.substring(space1 + 1, space2).toInt();
|
||||||
|
int state = cmd.substring(space2 + 1).toInt();
|
||||||
|
if (relay >= 1 && relay <= 8 && (state == 0 || state == 1)) {
|
||||||
|
setRelay(relay, state);
|
||||||
|
Serial.print("Relay ");
|
||||||
|
Serial.print(relay);
|
||||||
|
Serial.print(" set to ");
|
||||||
|
Serial.println(state ? "ON" : "OFF");
|
||||||
|
} else {
|
||||||
|
Serial.println("Invalid relay number or state. Use 1-8 and 0/1.");
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
Serial.println("Usage: r <relayNum 1-8> <0|1>");
|
||||||
|
}
|
||||||
|
} else if (cmd.startsWith("all ")) {
|
||||||
|
int state = cmd.substring(4).toInt();
|
||||||
|
if (state == 0 || state == 1) {
|
||||||
|
setAllRelays(state);
|
||||||
|
Serial.print("All relays set to ");
|
||||||
|
Serial.println(state ? "ON" : "OFF");
|
||||||
|
} else {
|
||||||
|
Serial.println("Invalid state for all.");
|
||||||
|
}
|
||||||
|
} else if (cmd.startsWith("name ")) {
|
||||||
|
String name = cmd.substring(5);
|
||||||
|
setDeviceName(name);
|
||||||
|
Serial.print("Device name set to: ");
|
||||||
|
Serial.println(name);
|
||||||
|
} else if (cmd.startsWith("addr ")) {
|
||||||
|
int newAddr = cmd.substring(5).toInt();
|
||||||
|
if (newAddr >= 8 && newAddr <= 119) {
|
||||||
|
setI2CAddress(newAddr);
|
||||||
|
Serial.print("I2C address set to: ");
|
||||||
|
Serial.println(newAddr, HEX);
|
||||||
|
} else {
|
||||||
|
Serial.println("Invalid address.");
|
||||||
|
}
|
||||||
|
} else if (cmd == "id") {
|
||||||
|
String id = getIdentification();
|
||||||
|
Serial.print("ID: ");
|
||||||
|
Serial.println(id);
|
||||||
|
} else {
|
||||||
|
Serial.println("Unknown command.");
|
||||||
}
|
}
|
||||||
}
|
|
||||||
}
|
|
||||||
return count;
|
|
||||||
}
|
}
|
||||||
|
@ -1,20 +1,27 @@
|
|||||||
#ifndef I2CRelay_H
|
#ifndef I2CRELAY_H
|
||||||
#define I2CRelay_H
|
#define I2CRELAY_H
|
||||||
|
|
||||||
#include <Arduino.h>
|
#include <Arduino.h>
|
||||||
#include <Wire.h>
|
#include <Wire.h>
|
||||||
|
|
||||||
class I2CRelay {
|
class I2CRelay {
|
||||||
public:
|
public:
|
||||||
I2CRelay(uint8_t slaveAddress);
|
I2CRelay(uint8_t address = 0x08, uint8_t sda = 8, uint8_t scl = 3);
|
||||||
|
|
||||||
void begin();
|
void begin();
|
||||||
void setRelay(uint8_t relayIndex, bool state);
|
void setRelay(uint8_t relayNum, uint8_t state);
|
||||||
uint8_t scanDevices(uint8_t* foundAddresses, uint8_t maxDevices);
|
void setAllRelays(uint8_t state);
|
||||||
void setAddress(uint8_t newAddress);
|
void setDeviceName(const String &name);
|
||||||
void handleI2CCommand();
|
void setI2CAddress(uint8_t newAddr);
|
||||||
|
String getIdentification();
|
||||||
|
|
||||||
|
// Helper for command parsing (optional)
|
||||||
|
void handleSerialCommand(const String &cmd);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
uint8_t _slaveAddress;
|
uint8_t _address;
|
||||||
|
uint8_t _sda;
|
||||||
|
uint8_t _scl;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
Loading…
x
Reference in New Issue
Block a user