Two LDRs give varying values under the same light

Hi,
I'm creating a light searching robot so I have two LDRs to work out which side of the robot the light is on. If the light is stronger on the right, the robot turns right, turning left if the light is stronger there.

The problem I'm having is that even if I hold the LDRs right next to each other and put them under the same amount of light, I get different values. They're wired exactly the same, each with a 1k ohm resistor.

Is there any way that I can level the two values so they increase/decrease at the same rate? Preferably through code.

I've attached a screen clipping of the two values compared under the same light. The "left" column is the values of the left LDR. The "right" column, the values from the right LDR. The "//" column is the left divided by the right and the "--" column is the right subtracted from the left.

This is also the code that I'm using to read the LDR values. It's just a simple analogRead program.

const int ldrLeft_Pin = A1;     // Pin designations
const int ldrRight_Pin = A7;

void setup() {
  Serial.begin(9600);
  pinMode(ldrLeft_Pin, INPUT);    // Set LDR pins as INPUT
  pinMode(ldrRight_Pin, INPUT);
}

void loop() {
  int ldr_Value_L = analogRead(ldrLeft_Pin);          //Read the LDR values
  int ldr_Value_R = analogRead(ldrRight_Pin);
  
  //ldr_Value_L = map(ldr_Value_L, 0, 1016, 0, 255);  // Maps the values to later write to LEDs
  //ldr_Value_R = map(ldr_Value_R, 0, 1016, 0, 255);
  int light_Value = (ldr_Value_L + ldr_Value_R)/2;    // In theory this is the "front" light value
  
  Serial.print("Left LDR: ");           // Print all the values
  Serial.println(ldr_Value_L);
  Serial.print("Right LDR: ");
  Serial.println(ldr_Value_R);
  Serial.print("Front LDR Value: ");
  Serial.println(light_Value);
  Serial.println("");
  delay(1000);
}

Screenshot (7).png

What you are seeing is not all that unusual depending on the LDR and actual series resistance. Just as an example of what I am getting at here is a data sheet for a specific group os LDRs.

A single unit cost about $6.53 USD

I would expect something like that to repeat unit to unit more than 10 for $5.00 on Amazon Prime. You normally choose a LDR for its intended application. Do you have a data sheet link to what you have?

Ron

Thanks for the reply.

Unfortunately this is a university project so I'm working with the two LDRs I was given. They gave us a component list so I managed to track down the datasheet for the LDRs they've given me:

I'm afraid I don't have a lot of experience with Arduino or electronic sensors like LDRs so I'm sort of learning on the spot here. I have a lot of experience with programming but this is my first robotics project. Because of that I'll be honest I'm not sure what I'm looking at on a lot of that datasheet.

Thanks for your help!

mbennett0219:
Is there any way that I can level the two values so they increase/decrease at the same rate? Preferably through code.

You could graph the factors in your third column and get your favorite spreadsheet or other tool to figure out a formula to adjust the right column before you use them for comparing.

So I found a rough solution. And by rough I mean the most botched, thrown-together solution ever.

By mapping one of the LDR values between 2400 and 1000 then dividing by 1000 I'm able to roughly get the // value that corresponds with the LDR value. Then I divide the left LDR value by that proportional float number I just calculated to make it roughly level with the right LDR when they're under the same light.

Finally I map the two LDR values to a range that LEDs can handle (0-255). However I noticed that over a value of 30 the LDRs are still out of sync by a constant of around 20, so if the right value is above 30 I add 20 to the left value.

It's very messy, but it works.

const int ldrLeft_Pin = A1;     // Pin designations
const int ldrRight_Pin = A7;

void setup() {
  Serial.begin(9600);
  pinMode(ldrLeft_Pin, INPUT);    // Set LDR pins as INPUT
  pinMode(ldrRight_Pin, INPUT);
}

void loop() {
  int ldr_Value_L = analogRead(ldrLeft_Pin);          //Read the LDR values
  int ldr_Value_R = analogRead(ldrRight_Pin);

  float divider = float(map(ldr_Value_R, 0, 1023, 2400, 1000))/1000;
  ldr_Value_L = ldr_Value_L/divider;
  
  ldr_Value_R = map(ldr_Value_R, 0, 1023, 0, 255);      // Maps the values to later write to LEDs
  if (ldr_Value_R < 30){
    ldr_Value_L = map(ldr_Value_L, 0, 1023, 0, 255);
  }
  else{
   ldr_Value_L = map(ldr_Value_L, 0, 1023, 0, 255) + 20;
  }
  
  int light_Value = (ldr_Value_L + ldr_Value_R)/2;    // In theory this is the "front" light value

  Serial.print("Divider: ");
  Serial.println(divider);
  Serial.print("Left LDR: ");           // Print all the values
  Serial.println(ldr_Value_L);
  Serial.print("Right LDR: ");
  Serial.println(ldr_Value_R);
  Serial.print("Front LDR Value: ");
  Serial.println(light_Value);
  Serial.println("");
  delay(1000);
}

OK, I can see your problem since the parts were handed to you. As I mentioned the fact that the two LDRs do not agree is no surprise. You may have another problem in that each LDR is a non-linear device. Something maybe worth a try with mapping is multi-mapping each LDR.

https://playground.arduino.cc/Main/MultiMap/

That may help get things in agreement.

Ron

It is entirely possible to calibrate the two LDRs so that they agree. You should start by collecting some raw data points (analog readings) at different light levels, using the same level for each sensor.

In the followup, as suggested above, correct one sensor's output (or both). It is an interesting problem and there are at least two ways to go about it:

  1. fit a curve to one set of points using the other set of points as a reference

  2. individually calibrate each sensor, following this general calibration tutorial: Why Calibrate? | Calibrating Sensors | Adafruit Learning System

Let us know if you want to pursue either option and we can help.