Hier werden die Unterschiede zwischen zwei Versionen gezeigt.
Beide Seiten der vorigen Revision Vorhergehende Überarbeitung Nächste Überarbeitung | Vorhergehende Überarbeitung | ||
projekte2014:beerbot:dokumentation:software [2014/07/29 13:43] wuxmax |
projekte2014:beerbot:dokumentation:software [2016/01/21 12:45] (aktuell) |
||
---|---|---|---|
Zeile 1: | Zeile 1: | ||
- | ====== Softwaredokumentation ====== | + | ====== Quellcode ====== |
===== Main Sketch ===== | ===== Main Sketch ===== | ||
Zeile 63: | Zeile 63: | ||
void loop() { | void loop() { | ||
+ | |||
+ | main1(); | ||
+ | | ||
} | } | ||
+ | |||
+ | /** | ||
+ | * test functions for the different components of the robot. | ||
+ | * for debugging and presentation purposes. | ||
+ | */ | ||
void testOpen() { | void testOpen() { | ||
Zeile 95: | Zeile 102: | ||
myGear.turnAngle(90, true, 12); | myGear.turnAngle(90, true, 12); | ||
} | } | ||
+ | |||
+ | /** | ||
+ | * the main function of the robots software. | ||
+ | * defines the different phases of the process | ||
+ | * it is not working pefectly in its current state due to some problems with e.g. the contact sensors. | ||
+ | * it is modified to work as good as possible under the given circumstances. | ||
+ | */ | ||
void main1() { | void main1() { | ||
Zeile 184: | Zeile 198: | ||
} | } | ||
} | } | ||
+ | |||
+ | /** | ||
+ | * helper function to check if the bottle is loaded by the robot. | ||
+ | */ | ||
boolean bottleLoaded() { | boolean bottleLoaded() { | ||
return (capSensor.leftButtonPushed() || capSensor.rightButtonPushed()); | return (capSensor.leftButtonPushed() || capSensor.rightButtonPushed()); | ||
} | } | ||
+ | |||
+ | /** | ||
+ | * helper function to check if the robot touched the bottle. | ||
+ | */ | ||
boolean bottleClose() { | boolean bottleClose() { | ||
return (frontSensor.leftButtonPushed() || frontSensor.rightButtonPushed()); | return (frontSensor.leftButtonPushed() || frontSensor.rightButtonPushed()); | ||
} | } | ||
+ | |||
+ | /** | ||
+ | * an easy algorithm that makes the robot drive forward and scan for cold bottles in steps. | ||
+ | */ | ||
boolean easySearch(float totalDistance, float partDistance) { | boolean easySearch(float totalDistance, float partDistance) { | ||
Zeile 204: | Zeile 230: | ||
} | } | ||
} | } | ||
+ | |||
+ | /** | ||
+ | * a more complex function to scan the room for cold bottles. | ||
+ | * has not been tested. | ||
+ | */ | ||
boolean complexSearch(float totalDistance, float partDistance) { | boolean complexSearch(float totalDistance, float partDistance) { | ||
Zeile 230: | Zeile 261: | ||
return false; | return false; | ||
} | } | ||
+ | |||
+ | /** | ||
+ | * a function to adjust the postion of the robot as it touches the bottle. | ||
+ | */ | ||
void adjustPosition() { | void adjustPosition() { | ||
Zeile 240: | Zeile 275: | ||
myGear.drive(1, 12, true); | myGear.drive(1, 12, true); | ||
} | } | ||
+ | |||
</code> | </code> | ||
Zeile 245: | Zeile 281: | ||
==== BeerBotLib ==== | ==== BeerBotLib ==== | ||
+ | |||
+ | This library defines and implements all classes that are needed to control the different components of the robot, except for the thermal camera. | ||
=== BeerBotLib.h === | === BeerBotLib.h === | ||
Zeile 753: | Zeile 791: | ||
==== ThermalCam ==== | ==== ThermalCam ==== | ||
+ | |||
+ | This library defines and implements only the ThermalCam class. We seperated the thermal camera library, because it is the largest and most complex part of the software. | ||
=== ThermalCam.h === | === ThermalCam.h === | ||
Zeile 772: | Zeile 812: | ||
int sweepSpeed; | int sweepSpeed; | ||
- | int servoSpeed; | ||
- | float tolerance; | ||
double* pixelTemps; | double* pixelTemps; | ||
- | double pixelCompressedTo16[16]; | ||
- | double midPixels; | ||
- | double leftSide; | ||
- | double rightSide; | ||
- | double pixelSum; | ||
- | double coldestPixel; | ||
double temperatureBorder; | double temperatureBorder; | ||
- | double pixelCompressedTo8[8]; | ||
- | int dire; | ||
int servoRange; | int servoRange; | ||
- | float searchTolerance; | ||
boolean foundColdPixel(); | boolean foundColdPixel(); | ||
void getThermalData(); | void getThermalData(); | ||
- | void summarizeVerticalPixels(); | + | |
- | void summarizeMidPixels(); | + | |
- | boolean checkMidPixelsForCold(); | + | |
- | void summarizeSides(); | + | |
- | void moveToColderSide(); | + | |
- | void moveToCold(); | + | |
- | void searchColdestPixel(); | + | |
- | void compressPixelTo8(); | + | |
public: | public: | ||
void setup(int servoPin, int temperatureBorder); | void setup(int servoPin, int temperatureBorder); | ||
boolean searchColdSpot(); | boolean searchColdSpot(); | ||
- | void followColdSpot(); | ||
int getPos(); | int getPos(); | ||
}; | }; | ||
Zeile 818: | Zeile 839: | ||
| | ||
this-> sweepSpeed = 2; | this-> sweepSpeed = 2; | ||
- | this-> servoSpeed = 1; | ||
- | this-> tolerance = 1.5; | ||
- | this-> midPixels = 0.0; | ||
- | this-> leftSide = 0.0; | ||
- | this-> rightSide = 0.0; | ||
- | this-> pixelSum = 0.0; | ||
- | this-> coldestPixel = 0.0; | ||
this-> temperatureBorder = temperatureBorder; | this-> temperatureBorder = temperatureBorder; | ||
- | this-> dire = 0.0; | ||
this-> servoRange = 90; | this-> servoRange = 90; | ||
- | this-> searchTolerance = 1.5; | ||
} | } | ||
+ | |||
+ | /* | ||
+ | Function for getting the thermaldata. | ||
+ | */ | ||
void ThermalCam::getThermalData() { | void ThermalCam::getThermalData() { | ||
- | sensor.readTemperatures(); | + | sensor.readTemperatures(); |
- | pixelTemps = sensor.getPixelTemperatures(); | + | pixelTemps = sensor.getPixelTemperatures(); |
} | } | ||
- | void ThermalCam::summarizeVerticalPixels() { | + | /* |
- | for( int x = 0; x < 16; x++ ) { | + | Function sets thermalcam-servo to 90 degrees. |
- | for( int y = 0; y < 4; y++ ) { | + | Servo does a complete sweep and every degree the thermaldata gets checked for a cold source. |
- | pixelSum += pixelTemps[ y + x * 4 ]; | + | If there is a cold source, "true" is returned back, else "false". |
- | } | + | */ |
- | pixelCompressedTo16[x] = pixelSum / 4.0; | + | |
- | pixelSum = 0.0; | + | |
- | } | + | |
- | } | + | |
- | + | ||
- | void ThermalCam::summarizeMidPixels() { | + | |
- | midPixels = ( pixelCompressedTo16[8] + pixelCompressedTo16[9] ) / 2; | + | |
- | } | + | |
- | + | ||
- | boolean ThermalCam::checkMidPixelsForCold() { | + | |
- | return (midPixels < temperatureBorder); | + | |
- | } | + | |
- | + | ||
- | void ThermalCam::summarizeSides() { | + | |
- | for( int x = 3; x < 8; x++ ) { | + | |
- | rightSide += pixelCompressedTo16[x]; | + | |
- | } | + | |
- | rightSide /= 7; | + | |
- | for( int x = 8; x < 13; x++ ) { | + | |
- | leftSide += pixelCompressedTo16[x]; | + | |
- | } | + | |
- | leftSide /= 7; | + | |
- | } | + | |
- | + | ||
- | void ThermalCam::moveToColderSide() { | + | |
- | if( leftSide < rightSide && ( rightSide - leftSide ) > tolerance ) myServo.moveLeft((int)servoSpeed, 15); | + | |
- | else if( rightSide < leftSide && ( leftSide - rightSide ) > tolerance ) myServo.moveRight((int)servoSpeed, 15); | + | |
- | else; | + | |
- | } | + | |
boolean ThermalCam::searchColdSpot() { | boolean ThermalCam::searchColdSpot() { | ||
- | myServo.setPos(90); | + | myServo.setPos(90); |
- | delay(100); | + | delay(100); |
- | for (int i = 0; i < servoRange; i++) { | + | for (int i = 0; i < servoRange; i++) { |
- | myServo.sweep((int)sweepSpeed, servoRange, 15); | + | myServo.sweep((int)sweepSpeed, servoRange, 15); |
- | getThermalData(); | + | getThermalData(); |
- | for (int i = 28; i < 36; i++) { | + | if (foundColdPixel()) { |
- | Serial.println(pixelTemps[i]); | + | return true; |
- | } | + | |
- | // summarizeVerticalPixels(); | + | |
- | // summarizeMidPixels(); | + | |
- | if (foundColdPixel()) { | + | |
- | return true; | + | |
- | } | + | |
} | } | ||
- | return false; | + | } |
+ | return false; | ||
} | } | ||
- | void ThermalCam::followColdSpot() { | + | /* |
- | getThermalData(); | + | Function, which gives back the current position (angle) of the thermalcam-servo. |
- | //summarizeVerticalPixels(); | + | */ |
- | //compressPixelTo8(); | + | |
- | searchColdestPixel(); | + | |
- | moveToCold(); | + | |
- | } | + | |
int ThermalCam::getPos() { | int ThermalCam::getPos() { | ||
- | return myServo.getPos(); | + | return myServo.getPos(); |
} | } | ||
- | void ThermalCam::moveToCold() { | + | /* |
- | if(dire < 28 && coldestPixel < temperatureBorder && getPos() < 90 + servoRange/2) { | + | Function, which checks the two rows in the middle of the thermalcam-pixelarray for a cold source. |
- | myServo.setPos(getPos() + (int)servoSpeed); | + | */ |
- | delay(10); | + | |
- | } | + | |
- | else if(dire > 27 && coldestPixel < temperatureBorder && getPos() > 90 - servoRange/2) { | + | |
- | myServo.setPos(getPos() - (int)servoSpeed); | + | |
- | delay(10); | + | |
- | } | + | |
- | } | + | |
boolean ThermalCam::foundColdPixel() { | boolean ThermalCam::foundColdPixel() { | ||
- | for( int i = 28; i < 35; i++ ) | + | for( int i = 28; i < 35; i++ ) { |
- | { | + | if( pixelTemps[i] < temperatureBorder ) return true; |
- | if( pixelTemps[i] < temperatureBorder ) | + | |
- | { | + | |
- | return true; | + | |
} | } | ||
- | } | + | return false; |
- | return false; | + | |
} | } | ||
- | void ThermalCam::searchColdestPixel() { | ||
- | coldestPixel = pixelTemps[4]; | ||
- | for( int i = 5; i < 60; i++ ) | ||
- | { | ||
- | if( pixelTemps[i] < coldestPixel && ( coldestPixel - pixelTemps[i] ) > searchTolerance ) | ||
- | { | ||
- | coldestPixel = pixelTemps[i]; | ||
- | dire = i; | ||
- | } | ||
- | } | ||
- | } | ||
- | |||
- | void ThermalCam::compressPixelTo8() { | ||
- | summarizeVerticalPixels(); | ||
- | int j = 0; | ||
- | for( int i = 0; i < 8; i++, j += 2 ) | ||
- | { | ||
- | pixelCompressedTo8[i] = pixelCompressedTo16[j] + pixelCompressedTo16[j + 1]; | ||
- | pixelCompressedTo8[i] /= 2; | ||
- | } | ||
- | } | ||
</code> | </code> | ||
Zeile 962: | Zeile 908: | ||
=== NewPing === | === NewPing === | ||
- | Library for improved usage of an ultrasonic distance sensor. | + | Library for improved usage of an ultrasonic distance sensor with a Teensy. |
https://github.com/PaulStoffregen/NewPing | https://github.com/PaulStoffregen/NewPing |