ADNS 1620 optical mouse sensor 18x18 pixel camera

Hello,

I have found an ADNS1620 Sensor, but problems to understand the datasheet as non native english speaker. Further the communication with the 1620 chip seems very complex for me.

ADNS 1620 DATASHEET

I tried to modify the code from HERE but dont understand most of what the code does.

#define SCLK 2
#define SDIO 3
// #define PD 4

#define REG_CONFIG_BITS 0x40
#define REG_PRODUCT_ID 0x41 //Asleep-Wake
#define REG_DELTA_Y 0x42
#define REG_DELTA_X 0x43
#define REG_SQUAL 0x44
#define REG_MAXIMUM_PIXEL 0x45
#define REG_MINIMUM_PIXEL 0x46
#define PIXEL_SUM 0x47
#define PIXEL_DATA 0x48
#define REG_SHUTTER_UPPER 0x49
#define REG_SHUTTER_LOWER 0x4A
#define REG_FRAME_PERIOD 0x4B
// #define REG_REVISION_ID 0x01
// #define REG_MOTION 0x02
// #define REG_DATA_OUT_LOWER 0x0C
// #define REG_DATA_OUT_UPPER 0x0D
// #define REG_FRAME_PERIOD_LOWER 0x10
// #define REG_FRAME_PERIOD_UPPER 0x11

int dumpWidth = 324; // Number of pixels to read for each frame.
byte frame[324];

void setup() {
  Serial.begin(115200);

  reset();
  byte productId = readRegister(REG_PRODUCT_ID);
  Serial.print("ProductId ");
  Serial.println(productId, HEX);

  byte config = readRegister(REG_CONFIG_BITS);
  config |= B00100001; // Don't sleep (LED always powered on).
  writeRegister(REG_CONFIG_BITS, config);

}

void loop() {
  // Allows to set the dump window by sending the number of lines to read via the serial port.
  if(Serial.available() > 0) {
    dumpWidth = 18 * Serial.read();
    dumpWidth = constrain(dumpWidth, 0, 324);
  }

//  readRegister(REG_MOTION); // Freezes DX and DY until they are read or MOTION is read again.
  char dx = readRegister(REG_DELTA_X);
  char dy = readRegister(REG_DELTA_Y);
  Serial.print("DELTA:");
  Serial.print(dx, DEC);
  Serial.print(" ");
  Serial.println(dy, DEC);

  if( dumpWidth > 0 )
    dumpFrame();
}

void dumpFrame() {
  byte config = readRegister(REG_CONFIG_BITS);
  config |= B00000001; // PixDump
  writeRegister(REG_CONFIG_BITS, config);

  int count = 0;
  do {
//    byte data = readRegister(REG_DATA_OUT_LOWER);
//    if( (data & 0x80) == 0 ) { // Data is valid
      frame[count++]; // = data;
    }
//  } 

  while (count != dumpWidth);

  config = readRegister(REG_CONFIG_BITS);
  config &= B11110111;
  writeRegister(REG_CONFIG_BITS, config);


  Serial.print("FRAME:");
  for(int i = 0; i < dumpWidth; i++) {
    byte pix = frame[i];
    if( pix < 0x10 )
      Serial.print("0");
    Serial.print(pix, HEX);
  }
  Serial.println();
}

void reset() {
  pinMode(SCLK, OUTPUT);
  pinMode(SDIO, INPUT);
//  pinMode(PD, OUTPUT);
  digitalWrite(SCLK, LOW);
//  digitalWrite(PD, HIGH);
  delayMicroseconds(1);
//  digitalWrite(PD, LOW);
}

byte readRegister(byte address) {
  pinMode (SDIO, OUTPUT);

  for (byte i=128; i >0 ; i >>= 1) {
    digitalWrite (SCLK, LOW);
    digitalWrite (SDIO, (address & i) != 0 ? HIGH : LOW);
    digitalWrite (SCLK, HIGH);
  }

  pinMode (SDIO, INPUT);

  delayMicroseconds(100); // tHOLD = 100us min.

  byte res = 0;
  for (byte i=128; i >0 ; i >>= 1) {
    digitalWrite (SCLK, LOW);
    digitalWrite (SCLK, HIGH);
    if( digitalRead (SDIO) == HIGH )
      res |= i;
  }

  return res;
}

void writeRegister(byte address, byte data) {
  address |= 0x80; // MSB indicates write mode.
  pinMode (SDIO, OUTPUT);

  for (byte i = 128; i > 0 ; i >>= 1) {
    digitalWrite (SCLK, LOW);
    digitalWrite (SDIO, (address & i) != 0 ? HIGH : LOW);
    digitalWrite (SCLK, HIGH);
  }

  for (byte i = 128; i > 0 ; i >>= 1) {
    digitalWrite (SCLK, LOW);
    digitalWrite (SDIO, (data & i) != 0 ? HIGH : LOW);
    digitalWrite (SCLK, HIGH);
  }

  delayMicroseconds(100); // tSWW, tSWR = 100us min.
}

I guess timings and order do not match, can anyone please help me with that?

It works!!

The code from Optical mouse hacking, part 1 | Conor Peterson helped me a lot.

Thanks,

Kolbi