Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- // --------------------------------------
- // Example use of the DS1882 Dual Channel Digital Potentiometer
- //
- // 2021 ++trent m. wyatt
- //
- #include <Arduino.h>
- #include <Printf.h>
- #include <Wire.h>
- #define DIGIPOT_ADDR 0x28
- // Command byte upper 2 bits determines command:
- // Config Register
- // Selection Settings
- // 0b00 xxxxxx
- // Invalid 0b11xxxxxx
- #define WRITE_POT0 0b00000000
- #define WRITE_POT1 0b01000000
- #define WRITE_CFG 0b10000000
- // Config Register, lower 3 bits:
- // Volatile/Nonvolatile Potentiometer Register Control Bit: A control bit that sets the
- // potentiometer registers to be either volatile or nonvolatile memory.
- // 0 = Potentiometer registers are set to nonvolatile memory storage.
- // 1 = Potentiometer registers are set to volatile memory storage. On power-up, the potentiometer wipers are in the mute position (default).
- #define NONVOLATILE 0b00000100
- // Zero-Crossing Detection Enable Bit: A bit used to enable and disable the zero-crossing functionality.
- // 0 = Zero-crossing detection is disabled.
- // 1 = Zero-crossing detection is enabled (default).
- #define ZEROCROSSING 0b00000010
- // Potentiometer Position Configuration: A control bit used to select the number of positions both potentiometers have.
- // 0 = Potentiometers have 63 positions and mute.
- // 1 = Potentiometers have 33 positions and mute (default).
- #define POTCONFIG 0b00000001
- uint8_t cfg_value = NONVOLATILE | ZEROCROSSING | POTCONFIG;
- int8_t pot0_value = 0;
- int8_t pot1_value = 0;
- uint8_t which_pot = 0;
- enum Modes { InvalidMode = -1, MenuMode, ScanMode, Tremelo };
- Modes mode = InvalidMode;
- void update_values() {
- write_config(cfg_value);
- write_pot0(pot0_value);
- write_pot1(pot1_value);
- //display_status();
- }
- void setup() {
- mode = MenuMode;
- // mode = ScanMode;
- // mode = Tremelo;
- digitalWrite(5, HIGH);
- pinMode(5, OUTPUT);
- digitalWrite(LED_BUILTIN, LOW);
- pinMode(LED_BUILTIN, OUTPUT);
- Wire.begin();
- //Serial.begin(230400);
- Serial.begin(2000000);
- delayMicroseconds(10);
- while (!Serial); // Leonardo: wait for Serial Monitor
- printf("\n");
- if (ScanMode == mode) {
- printf("\nI2C Scanner\n");
- }
- display_status();
- }
- void display_status() {
- printf("Selected potentiometer: ");
- if (2 == which_pot) {
- printf("Both\n");
- }
- else {
- printf("%d\n", which_pot);
- }
- printf("(V) Non-volatile is set to %s\n", (cfg_value & NONVOLATILE) == 0 ? "false" : "true");
- printf("(Z) Zero-crossing is set to %s\n", (cfg_value & ZEROCROSSING) == 0 ? "false" : "true");
- printf("(C) Pot-config is set to %s\n", (cfg_value & POTCONFIG) == 0 ? "Option 0" : "Option 1");
- printf("(0) Pot 0 value = %d\n", pot0_value);
- printf("(1) Pot 1 value = %d\n", pot1_value);
- printf("\n");
- }
- int factor0 = 1;
- int factor1 = 1;
- void loop() {
- static unsigned long timer = millis() + 1000UL;
- if (millis() >= timer) {
- timer = millis() + 1000UL;
- digitalWrite(LED_BUILTIN, !
- digitalRead(LED_BUILTIN));
- }
- unsigned long dur = 100000000UL;
- switch (mode) {
- case Tremelo:
- pot0_value += factor0;
- if (pot0_value < 10 || pot0_value >= 20)
- factor0 *= -1;
- pot1_value += factor1;
- if (pot1_value < 10 || pot1_value >= 20)
- factor1 *= -1;
- update_values();
- delayMicroseconds(dur);
- break;
- case MenuMode:
- menuloop();
- break;
- case ScanMode:
- scanloop();
- break;
- default:
- printf("Invalid mode: %d.\nStopping.\n", mode);
- while (true) { ; }
- break;
- }
- }
- void menuloop() {
- if (Serial.available() > 0) {
- while (Serial.available() > 0) {
- uint8_t b = Serial.read();
- b = toupper(b);
- if (isdigit(b) || isalpha(b)) {
- switch (b) {
- case '0':
- printf("Switching to potentiometer 0\n");
- which_pot = 0;
- break;
- case '1':
- printf("Switching to potentiometer 1\n");
- which_pot = 1;
- break;
- case '2':
- printf("Switching to both potentiometers\n");
- which_pot = 2;
- break;
- case 'V':
- cfg_value ^= NONVOLATILE;
- printf("Switching non-volatile to %s\n", (cfg_value & NONVOLATILE) == 0 ? "false" : "true");
- break;
- case 'Z':
- cfg_value ^= ZEROCROSSING;
- printf("Switching zero-crossing to %s\n", (cfg_value & ZEROCROSSING) == 0 ? "false" : "true");
- break;
- case 'C':
- cfg_value ^= POTCONFIG;
- printf("Switching pot-config to %s\n", (cfg_value & POTCONFIG) == 0 ? "Option 0" : "Option 1");
- break;
- case 'U':
- if (0 == which_pot || 2 == which_pot) {
- pot0_value++;
- printf("Up. Pot 0 value = %d\n", pot0_value);
- }
- if (1 == which_pot || 2 == which_pot) {
- pot1_value++;
- printf("Up. Pot 1 value = %d\n", pot1_value);
- }
- update_values();
- break;
- case 'D':
- if (0 == which_pot || 2 == which_pot) {
- pot0_value--;
- if (pot0_value < 0) pot0_value = 0;
- printf("Down. Pot 0 value = %d\n", pot0_value);
- }
- if (1 == which_pot || 2 == which_pot) {
- pot1_value--;
- if (pot1_value < 0) pot1_value = 0;
- printf("Down. Pot 1 value = %d\n", pot1_value);
- }
- update_values();
- break;
- default:
- break;
- }
- }
- }
- display_status();
- }
- }
- uint8_t write_pot0(uint8_t b) {
- return sendSingle(WRITE_POT0 | (b & 0x3F));
- }
- uint8_t write_pot1(uint8_t b) {
- return sendSingle(WRITE_POT1 | (b & 0x3F));
- }
- uint8_t write_config(uint8_t b) {
- return sendSingle(WRITE_CFG | (b & 0x3F));
- }
- uint8_t sendSingle(uint8_t b1) {
- digitalWrite(5, LOW);
- delay(1);
- Wire.beginTransmission(DIGIPOT_ADDR);
- Wire.write(b1);
- uint8_t error = Wire.endTransmission();
- delay(1);
- digitalWrite(5, HIGH);
- return error;
- }
- void scanloop() {
- static int Pass = 1;
- int nDevices = 0;
- printf("Scanning pass #%d...\n", Pass++);
- digitalWrite(LED_BUILTIN, HIGH);
- for (byte address = 1; address < 127; ++address) {
- // The i2c_scanner uses the return value of
- // the Wire.endTransmission to see if
- // a device did acknowledge to the address.
- digitalWrite(5, LOW);
- delay(1);
- Wire.beginTransmission(address);
- byte error = Wire.endTransmission();
- delay(1);
- digitalWrite(5, HIGH);
- if (0 == error ) {
- printf("I2C device found at address 0x%02X !\n", address);
- ++nDevices;
- } else if (error == 4) {
- printf("Unknown error at address 0x%02X\n", address);
- }
- }
- digitalWrite(LED_BUILTIN, LOW);
- if (nDevices == 0) {
- printf("No I2C devices found\n\n");
- } else {
- printf("%d devices found. Done\n\n", nDevices);
- }
- delay(5000); // Wait 5 seconds for next scan
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement