There are various complexities for optical encoders,
I will be focusing on the more basic types.
For those of you who like a video see Video 1, this video covers some of the theory behind how an optical encoder works.However it does not cover of the application to the ROV project.
Video 1: Basics and how it works.
Here is a DC motor connected to an optical encoder. A DC motor isn't very accurate however it has the support and is inexpensive.
An optical encoder improvises for the lack of accuracy. There are three basic parts to an optical encoder see figure 1.
- In the black rectangle on the left there is a laser or an LED to shine a beam of light.
- Also in the black box there is a gap under the LED or laser, and across that gap there is a photo resistor (light receiver).
- There is a rotary disk which fits in the gap between the laser or LED and photo resistor. The disc is transparent, there are hundreds or thousands of black lines to interrupt the light beam which is printed on this disc. I used a marker to enlarge these interrupt lines for visual effects see figure 2.
Figure 1: Optical encoder on DC motor
Figure 2: Optical encoder with enlarged interrupts
Not all optical encoders are the same see Figure 3. This is the optical encoder from my ROV. There are 50 black lines on this rotary encoder. since the encoder has low resolution you can see the lines in this figure. the light emitter and receiver's on the left.
| Figure 3: Optical encoder from ROP project |
In the optics the photo resistor can only see it's on and off state or and logic design a 1 or a 0.
If we wanted our motor to do a full rotation and there are 50 black lines, then we can rotate our motor until the logic of the photoresistor has seen a 1 50 separate times.
For those of you who are observant will notice that this is not the standard DC motor it is a servo, I unfortunately bought a cheap servo without an accurate built-in encoder.
But wait there are more little tricks to encoders, there is a way to get twice the resolution. Yes, that means 100 steps from 50 black lines. we have been saying that that light received is a 1 and that light interrupted is a 0 see Table 1.
To double our resolution we used the rising and falling edge of each black line. One example, the transition from not receiving light to receiving light has a value of one, however both light received an light interrupted as a value of zero see Table 2.
| State of Florida resistor |
Light receives
|
Light interrupted
|
Logic value
|
1
|
0
|
If you find the case in Table 2 difficult to understand consider watching Video 1 at time 2:20 (Here).
Table 2: logic value second case
Photo resistor
|
Light received
|
Light received transition to light interrupted
|
Light interrupted
|
Light interrupted transition to light received
|
Logic value
|
0
|
1
|
0
|
1
|
To see a demo for arduino code click (here)
On line ~25 you will see
attachInterrupt(digitalPinToInterrupt(servoEncoder), AirServoEncoder, CHANGE);
The attach interrupt has works different on different arduinos. You can fine fore detail on arduino's site (here).
Attach interrupt allows the program to monitor a pin while doing other tasks. The controller could spend all of its time monitoring one pin awaiting a signal that will be so fast that just about any other way the signal would be missed. But there is one other thing we can do, that is an attachInterrupt.
When an event happens while running a different part of the program, this interrupt will make a note of the missed event to run a designated function when it can make time.
In my case going back to
attachInterrupt(digitalPinToInterrupt(servoEncoder), AirServoEncoder, CHANGE);
this says when there is a "CHANGE" to "digitalPinToInterrupt(servoEncoder)" pin nomater where the program is running go to "AirServoEncoder" program.
The referenced program has to be as simple as possible without any delays or any thing that can act like one. My referenced program is "AirServoEncoder" and the only line of code in it is on line ~52 "encoderCount++;" then my loop will reference the int encoderCount for posichaning. The int encoderCount is a count of how many stamps have been seen.
Here is a side view of the servo, encoder, adapter, and air regulator for my remote-controlled submarine's air system see Figure 4. The cylinder on the top of the picture is the bottom of my air regulator, right under that is my 3-D printed (soon to be cast aluminum) adapter to fit to the top of the servo. It's difficult to see in this picture of the encoder is placed between the servo and of the adapter.
Figure 4