Bourns encoder gives random values

Hello Im having issues with using a bourns encoder and I2c backpack. I am receiving random values in the serial monitor as if the encoder is bouncing around. Could this be a pin mapping issue?

 #include <ACE128.h>
#include <ACE128map87654321.h>

/*  ACE128 Demonstrator
 *  
 *  This demo provides examples of all the options and functions available in this library.
 *  You should be able to find everything you need from here to use in your own sketch.
 *  This makes is very long, detailed and wordy.
 *  
 *  See the ace128_0x20 and ace128_0x38 examples for short specific tests for the manufactured modules.
 *  
 *  As distributed it can be used to test the functionality of the Absolute Encoder modules 
 *  that I make and distribute online on AVR platforms e.g. Arduino Unos.
 *  
 *  If you wire a button between pin 13 and ground, you can test setting logical zero
 *  
 *  For use on non-AVR chips (e.g. Arduino MKR) and use without PCF8574(A) pin expanders, see below.
 *  
 *  The inline comments do not assume the use of one of my modules, so there are references to
 *  mis-wiring and alternate wiring which are relevent to people building their own circuits or breadboarding.
 *  
 *  The value below is the address of your module. Set this to the correct value.
 *  For purchased modules this is the base address of the module.
 */

//PCF8574 0x20
//#define PCF8574A 0x38
// MCP23008 0x00 (see notes below) 
#define ACE_ADDR 0x38 

/*   
 *  this sketch displays the current position in all five forms on the serial monitor at 9600 baud
 *    pin  = the raw gray-code from the pins. As you rotate this will rise and fall in steps of 1,2,4,8,16,32,64 or 128
 *    raw  = the output from the encoder map table. This should rise from 0 - 127 as you rotate clockwise
 *           if it jumps around and shows 255 a lot - your wiring does not match your encoder map. Check your wiring
 *           and your object declaration. See the make_encodermap example sketch to create encoder maps for
 *           alternate pin arrangements
 *    pos  = this is the raw value converted to the range -64 - +63 relative to the logical zero. Logical zero is
 *           wherever it was when the sketch started, unless the value was saved in EEPROM or reset.
 *    upos = this is the raw value converted to the range 0 - 127 relative to the logical zero
 *    mpos = this is like pos, but goes multiturn -32768 - 32767
 *    
 *    For this sketch we need to select what displays we will use
 */
#define DISPLAY_SERIAL  // display on serial at 9600 baud
//#define DISPLAY_LCD     // display on LCD with PCF8574 backpack at 0x27


#ifdef DISPLAY_LCD
  #include <LiquidCrystal_PCF8574.h>
LiquidCrystal_PCF8574 lcd(0x27);  // 1602 LCD on 0x27
#endif
 /*
 *  Your sketch needs to include the ACE128.h library near the top
 *  For the following non-standard options you need to edit some options in ACE128.h
 *     disabling EEPROM storage code on AVR platforms
 *     enabling I2C EEPROM storage on all platforms - you can also change the default I2C address of this EEPROM
 *     enabling direct-wire to the ACE128 - this disables all the pin-expander chip code
 *     enabling support for MCP23008 pin expanders (this does not disable PCF8574(A) support)
 *  These options will be documented in detail below.
 *  Note that if you are having trouble editing the ACE128.h file in the library folder you can copy it to your sketch folder
 *  and edit it there. If you do this, use the second #include format below
 */
#include <ACE128.h>  // Include the ACE128.h from the library folder
// #include "ACE128.h"  // Include the ACE128.h from the sketch folder

/*  Now we include the encoder map.
 *  This is a table of all the 256 possible pin combinations and how they map to the 128 gray code values. 
 *  Invalid locations are filled with 255. 
 *  The modules I make all use the 87654321 map and this is silkscreened on the circuit board. If you are building your
 *  own circuits or breadboarding you may need another encoder map. Several are available in the library, as well as an
 *  example sketch to generate new ones.
 *  Each map is identified by the sequence of numbers 1 thru 8 in the order that they appear on the P0 - P7 pins of the chip
 */
#include <ACE128map87654321.h> // mapping for pin order 87654321

/*  MCP23008 pin expanders are optionally supported. I built my first modules using these but the code is no longer
 *  included by default and must be enabled by defining ACE128_MCP23008 in ACE128.h 
 *  Both modules can be used on the same project but as the MCP and PCF address ranges overlap we tell them apart by 
 *  calling the contructor with I2C address range 0x00-0x07 which is mapped internally to the actual 0x20-0x27 range
 *  The following little bit of preprocessor code helps for this sketch as we need the mapped address
 *  for bus probing
 */
#ifdef ACE128_MCP23008
  #define ACE_PROBE_ADDR ACE_ADDR | 0x20
#else
  #define ACE_PROBE_ADDR ACE_ADDR
#endif
/*
 *  Now construct an ACE128 object for each unit in your project
 *  There are 4 constructors available. Providing a choice of I2C or direct pin mode and with or without EEPROM state storage
 */
ACE128 myACE(ACE_ADDR, (uint8_t*)encoderMap_87654321); // I2C without using EEPROM
// the EEPROM contructor is not available on SAM based platforms unless ACE128_I2C_EEPROM is defined in ACE128.h
//ACE128 myACE(ACE_ADDR, (uint8_t*)encoderMap_87654321, 0); // I2C using EEPROM address 0

/* 
 *  If wiring directly to the ACE128 sensor, the constructors below are enabled by defining ACE128_ARDUINO_PINS
 *  in ACE128.h - this also disable I2C chip capabilities.
 *  In this case the 8 numbers identify arduino digital pins. So you can shuffle those numbers around instead of 
 *  changing the encoder map. Have fun!
 */
//ACE128 myACE(uint8_t{2,3,4,5,6,7,8,9}, (uint8_t*)encoderMap_87654321); // direct pins without using EEPROM
// the EEPROM contructor is not available on SAM based platforms unless ACE128_I2C_EEPROM is defined in ACE128.h
//ACE128 myACE(uint8_t{2,3,4,5,6,7,8,9}, (uint8_t*)encoderMap_87654321, 0 ); // direct pins using EEPROM address 0

// the following stuff is for this example script
// set-zero button on pin 13
// - button to ground e.g. MakerShield button
const int ZERO = 13;
uint8_t pinPos = 0; // pin values
uint8_t rawPos = 0;
uint8_t upos = 0;
uint8_t oldPos = 255;
int8_t pos;
int16_t mpos;
uint8_t seen = 0;

void setup() {
  Serial.begin(9600);
  myACE.begin();    // this is required for each instance, initializes the pins
}


void loop() {
  pos = myACE.pos();                 // get logical position - signed -64 to +63
  upos = myACE.upos();               // get logical position - unsigned 0 to +127
  mpos = myACE.mpos();               // get multiturn position - signed -32768 to +32767

  if (upos != oldPos) {            // did we move?
    oldPos = upos;                 // remember where we are
    Serial.print(" pos ");
    Serial.print(pos, DEC);
    Serial.print(" upos ");
    Serial.print(upos, DEC);
    Serial.print(" mpos ");
    Serial.println(mpos, DEC);
  }
}

Here is what the serial monitor returns:

/
pos 0 upos 0 mpos -128
pos -1 upos 127 mpos -129
pos 0 upos 0 mpos -128
pos -1 upos 127 mpos -129
pos 0 upos 0 mpos -128
pos 0 upos 127 mpos -129
pos 0 upos 0 mpos -128
pos -1 upos 127 mpos -129
pos 0 upos 0 mpos -128
pos 0 upos 127 mpos -129
pos 0 upos 0 mpos -128
pos 0 upos 43 mpos -85
pos -38 upos 90 mpos -38
pos -38 upos 41 mpos -87
pos 41 upos 56 mpos -72
/

Can you write a simple test sketch to only read inputs from the backpack? That, along with checking connections to the encoder, would verify the hardware.

I dont know how to go about doing that, I have swapped the sda and scl pins with no change though.

SethC:
I dont know how to go about doing that

So this is not your sketch?

You can run an I2C scanner sketch (google it), it will at least detect the backpack.

No, this is an example sketch from the ACE 128 library. I will try the I2c sketch

Ok, the I2c backpack is recognized and shows no errors. I think this may be an issue with the pin mapping but Im not sure what the correct pin mapping would be. If there is a guide to setting this encoder up without using a LCD display that would be very helpful.