Skip to content
Dimitris Platis edited this page Jan 20, 2016 · 26 revisions

Contents


How does the cruise control work?

In cruise control mode, the vehicle attempts to move at a stable speed, regardless of various external disturbances. External disturbances could include the floor's friction, the weight of the car, the voltage battery drops etc. It is essential, if the user wants to make sure that the car will move at a specific speed, regardless of those factors. The algorithm utilized in order to achieve that is called PID controller. Nevertheless, the fact that the car attempts to maintain its speed, does not necessarily mean that it actually accomplishes that and particularly in an efficient manner.

For maximum performance, a user should optimize their PID controller, using the Kp, Ki and Kd variables as arguments in the enableCruiseControl method, as well as the frequency that the controller will be accessed.

How can I optimize the PID controller algorithm of the cruise control?

To put it very simply, you optimize or tune a PID controller by changing the Kp, Ki and Kd values and observing its behavior/output. If the oscillations in the output in its effort to reach the desired outcome are nominal and if the controller reaches the desired state fast enough, then you have a well tuned PID controller.

There are many ways to do that, but for reference you can have a look at the Ziegler-Nichols method. Alternatively, you can have look at some more empirical and practical approaches here: What are good strategies for tuning PID loops?

How do I calibrate the gyroscope?

The gyroscope, even at its idle state (when it is being still), produces an output, which usually varies between a range. This noise can affect the stability of our readings, if not taken into consideration during the calculations from which we derive the angular displacement. Therefore, we need to define an offset (as well as a threshold) in order to filter out this invalid measurements. As you should not expect the offset value to be valid for your own gyroscope, you should run the sketch found under Examples → sensors → gyroscope → gyroscopeCallibration, while having the vehicle still and the serial monitor open. If ran successfully, you will get a value that represents the offset for your specific gyroscope and you can use it from that point and onward in the gyroscope's constructor.

How do I calibrate the speed encoders?

The speed encoders measure how much a wheel or motor has rotated, by counting pulses generated by the infrared beam being blocked and released, due to the movement of the encoder disk. Read more on how they work.

In order to derive the traveled distance from these pulses, we need to know how many pulses we get per meter or centimeters. We can use that number as a factor in order to calculate the distance covered by the vehicle. For example, if we know that we get 50 pulses per meter, then we need to multiply the amount of pulses that we get by 2 (alternatively, divide that number by 0.5), in order to estimate the distance we have traveled, in centimeters.

As this number depends on the encoder disk, as well as the sensitivity of the odometer sensor itself, you should not rely on the default value, provided with the library. Instead, you should discover that number for your own setup. You can do this by uploading the sketch found in Examples → sensors → Odometer → findPulsesPerMeter. Next, take a measure of 1 meter and place it on the floor. Having the serial port open, either by having the car connected to your computer with a preferably long USB cable or using Bluetooth, roll the car along the measure and stop it after its wheels have traveled (approximately) one meter. Do not forget to make sure the wheels are spinning and not sliding on the floor. You might need to apply some light pressure downwards, in order to manage that. The number that is printed on your serial monitor, is the one you are looking for that represents how many pulses we get per meter from the speed encoders. To be safe, do this a couple of times, so to be certain that the number you have found is the correct one.

Finally, you should provide that number as an argument in the Odometer constructor, so you can get accurate distances in centimeters and speed in meters per second, while using the appropriate functions.

How do I use an existing class with a less complicated name?

If you want to create an alias for a class (e.g. instead of GP2Y0A02, just IR) you should use the typedef function. Below, you can find an example that illustrates the creation of an alias for the GP2Y0A02 class.

#include <Wire.h>
#include <Smartcar.h>
#include <Servo.h>

typedef GP2Y0A02 IR; //give a more simple name to the GP2Y0A02 class

IR infrared;

void setup() {
  Serial.begin(9600);
  infrared.attach(A0);
}

void loop() {
  Serial.println(infrared.getDistance());
  delay(500);
}

How can I add a new sensor in the library?

If you want support for a new sensor to be added in the library, then you can open an Issue and we can discuss about it. Alternatively, if you have developed something already, you can create a pull request. Keep in mind however, that the library should maintain its architectural structure. So, if it is a distance sensor, it should at least extend the DistanceSensor class and if it is a motor, the Motor and ThrottleMotor or SteeringMotor classes.

Where can I buy an already assembled car or Smartcar shield?

Short answer: You cannot.

Or to be precise, I am not aware of any shop that sells the Smartcar kits already assembled. The Smartcar shield is not being sold by me, in any form, assembled or not. If you live nearby and want one assembled or have a specific reason not to be able to print and assemble one yourself, send me a message and we can discuss about what can be done.

Why does the <X> sensor not work?

To be honest, no idea! It could be due to a great number of reasons. Follow the troubleshooting guide below, before asking for help:

  • Is the sensor getting powered? Check whether the voltage and ground pins connected correctly.
  • Is the component sufficiently powered? Is the voltage correct? If so, does the sensor get enough current? If your batteries are depleted or have a power hungry component, the current (especially when supplied from the Arduino power pins) might not be enough.
  • Are the signal pins correctly connected? Check also whether they correspond with what you have declared in your code.
  • Is it a code related issue? Create a new sketch and add ONLY the code necessary for this sensor.
  • Does the Arduino itself have a problem? Upload a very simple sketch to the Arduino (e.g. blinking a LED or printing a string through the Serial port) and verify whether something as basic as this works.

And then, ask for help. :)

Can I use this library even if I do not have the shield, but just a car with a servo motor and an ESC?

Yes! Just use the appropriate arguments in the constructor, i.e. Car car(useServo(5), useESC(6)) if your servo is connected to pin 5 and your ESC to pin 6. Of course some functions that are related to specific hardware components (e.g. the gyroscope) will not work.

Clone this wiki locally