X9C103P Digital Pot As Voltage Divider Problem (SOLVED)

Thread Starter

iimagine

Joined Dec 20, 2010
481
This Pot is driving me nuts! I have no Idea why its not working as it should, I followed what the data sheet said: Set CS (Chip Select) LOW, Set UD (Up/Down) direction, Trigger INC LOW then HIGH. then set CS HIGH to write to EEPROM or set CS HIGH before setting INC HIGH to not write to EEPROM.
This DOES work properly! However, only if I write to EEPROM right after by setting CS HIGH again.
Since I dont want to write to EEPROM, I chose to leave CS LOW all the time, for now. It does work, using the osc-scope I can see the voltage varies UP/DOWN but not within the correct range, given an analog voltage of 1.5 and Wiper is set to 1, the analog output voltage is around 1V ?!.
X9C103 connections:
CS, U/D, INC to Arduino digital IO pins
VH (High Terminal) to analog input
VL (Low Terminal) to GND
VW (Wiper) as output

Any advice/help is much appreciated. Thanks in advance.

Datasheet: http://pdf1.alldatasheet.com/datasheet-pdf/view/34250/XICOR/X9C103P.html
Code:
//-----------------------------------------------------------------------
// DPX9C Digital Pot
//-----------------------------------------------------------------------
// Arduino Uno pin 10 to X9Cxxx increment pin (INC) - 1
// Arduino Uno pin 09 to X9Cxxx up/down pin (U/D) - 2
// Arduino Uno pin 08 to X9Cxxx CS pin (CS) - 7
// ---Constants---
const byte DPX9C_INC = B00000100;
const byte DPX9C_UD = B00000010;
const byte DPX9C_CS = B00000001;
const byte DPX9C_POWERUP_TIME = 50;
const byte DPX9C_CS_TIME = 20;
const byte DPX9C_INC_TIME = 1;
// DPX9C Maximun number of steps
const byte DPX9C_STEPS = 100;
const byte DPX9C_LOWER_LIMIT = 1;
const byte DPX9C_UPPER_LIMIT = DPX9C_STEPS - DPX9C_LOWER_LIMIT;
byte volatile dpWiper;

static inline void dpDecrease()
{
  if (dpWiper > DPX9C_LOWER_LIMIT)
  {
    dpWiper--;
    PORTB &= ~DPX9C_UD;
    PORTB &= ~DPX9C_INC;
    delayMicroseconds(DPX9C_INC_TIME);
    PORTB |= DPX9C_INC;
  }
}

static inline void dpIncrease()
{
  if (dpWiper < DPX9C_UPPER_LIMIT)
  {
    dpWiper++;
    PORTB |= DPX9C_UD;
    PORTB &= ~DPX9C_INC;
    delayMicroseconds(DPX9C_INC_TIME);
    PORTB |= DPX9C_INC;
  }
}

void setupDP()
{
  // Wait for DPX9C to complete its powerup sequence
  delay(DPX9C_POWERUP_TIME);
  PORTB &= ~DPX9C_CS;
  PORTB |= DPX9C_INC;
  // Set the digital pot all the way down to zero;
  dpWiper = DPX9C_STEPS << 1;
  while (dpWiper > DPX9C_LOWER_LIMIT)
    dpDecrease();
  while (dpWiper < DPX9C_UPPER_LIMIT)
    dpIncrease();
}
 
Last edited:

JWHassler

Joined Sep 25, 2013
280
This Pot is driving me nuts! I have no Idea why its not working as it should, I followed what the data sheet said: Set CS (Chip Select) LOW, Set UD (Up/Down) direction, Trigger INC LOW then HIGH. then set CS HIGH to write to EEPROM or set CS HIGH before setting INC HIGH to not write to EEPROM.
This DOES work properly! However, only if I write to EEPROM right after by setting CS HIGH again.
Since I dont want to write to EEPROM, I chose to leave CS LOW all the time, for now. It does work, using the osc-scope I can see the voltage varies UP/DOWN but not within the correct range, given an analog voltage of 1.5 and Wiper is set to 1, the analog output voltage is around 1V ?!.
X9C103 connections:
CS, U/D, INC to Arduino digital IO pins
VH (High Terminal) to analog input
VL (Low Terminal) to GND
VW (Wiper) as output

Any advice/help is much appreciated. Thanks in advance.

Datasheet: http://pdf1.alldatasheet.com/datasheet-pdf/view/34250/XICOR/X9C103P.html
Code:
//-----------------------------------------------------------------------
// DPX9C Digital Pot
//-----------------------------------------------------------------------
// Arduino Uno pin 10 to X9Cxxx increment pin (INC) - 1
// Arduino Uno pin 09 to X9Cxxx up/down pin (U/D) - 2
// Arduino Uno pin 08 to X9Cxxx CS pin (CS) - 7
// ---Constants---
const byte DPX9C_INC = B00000100;
const byte DPX9C_UD = B00000010;
const byte DPX9C_CS = B00000001;
const byte DPX9C_POWERUP_TIME = 50;
const byte DPX9C_CS_TIME = 20;
const byte DPX9C_INC_TIME = 1;
// DPX9C Maximun number of steps
const byte DPX9C_STEPS = 100;
const byte DPX9C_LOWER_LIMIT = 1;
const byte DPX9C_UPPER_LIMIT = DPX9C_STEPS - DPX9C_LOWER_LIMIT;
byte volatile dpWiper;

static inline void dpDecrease()
{
  if (dpWiper > DPX9C_LOWER_LIMIT)
  {
    dpWiper--;
    PORTB &= ~DPX9C_UD;
    PORTB &= ~DPX9C_INC;
    delayMicroseconds(DPX9C_INC_TIME);
    PORTB |= DPX9C_INC;
  }
}

static inline void dpIncrease()
{
  if (dpWiper < DPX9C_UPPER_LIMIT)
  {
    dpWiper++;
    PORTB |= DPX9C_UD;
    PORTB &= ~DPX9C_INC;
    delayMicroseconds(DPX9C_INC_TIME);
    PORTB |= DPX9C_INC;
  }
}

void setupDP()
{
  // Wait for DPX9C to complete its powerup sequence
  delay(DPX9C_POWERUP_TIME);
  PORTB &= ~DPX9C_CS;
  PORTB |= DPX9C_INC;
  // Set the digital pot all the way down to zero;
  dpWiper = DPX9C_STEPS << 1;
  while (dpWiper > DPX9C_LOWER_LIMIT)
    dpDecrease();
  while (dpWiper < DPX9C_UPPER_LIMIT)
    dpIncrease();
}
A schematic might help. I can't quite picture where the pot's wiper-pin goes
 

Thread Starter

iimagine

Joined Dec 20, 2010
481
JWHassler's got me into thinking that, somehow, somewhere between the wiper out and my ADC Preamp, something went wrong. So I connected VH to VCC (5V) and VL to GND, taking voltage measurement at VW; no connection to my ADC Preamp, and the Pot is now working properly; with the dpWiper set at 50, the output voltage is now at 2.5V. So now i'm stuck! Staring at my shematic and double check my wiring, wondering why its not working with AC input. Anyone have a thought?
 

Thread Starter

iimagine

Joined Dec 20, 2010
481
Somehow, after reconnecting VH to AC input, VL to GND and VW (Wiper) to Cin of my ADC Preamp, its working!! Must have been a short somewhere that's been resolved by reconnecting everything. Thanks for reading my post
 
Top