Program for the water play project for the course Software Testing Practical 2016 given at the VU University

Dependencies:   mbed DRV88255 TextLCD Ping mbed-rtos

Committer:
sbouber1
Date:
Sun Jun 19 22:39:16 2016 +0000
Revision:
58:b5f0c0f305ff
Parent:
57:8dc3192ff150
Child:
62:52cceb263591
update

Who changed what in which revision?

UserRevisionLine numberNew contents of line
sbouber1 28:f4a4ee58d57e 1 #include "PIDController.h"
sbouber1 35:c9261391a995 2 #include "testing.h"
sbouber1 46:7e4c1f2ab76c 3 #include "LCDController.h"
sbouber1 35:c9261391a995 4
sbouber1 57:8dc3192ff150 5 static DigitalOut heater(p18);
sbouber1 28:f4a4ee58d57e 6
sbouber1 57:8dc3192ff150 7 static DRV8825 mtr_fresh(p21, p27, p28, p29, p22, p23);
sbouber1 57:8dc3192ff150 8 static DRV8825 mtr_salt(p24, p27, p28, p29, p25, p26);
joran 44:7c932cc5991b 9
joran 44:7c932cc5991b 10
sbouber1 28:f4a4ee58d57e 11 // This is called in the main loop on every iteration
sbouber1 28:f4a4ee58d57e 12 void PIDController::update() {
sbouber1 35:c9261391a995 13
sbouber1 57:8dc3192ff150 14 #ifndef TEST_MODE
sbouber1 38:930469a33001 15 if(this->num_iters < STARTUP_ITERATIONS) {
sbouber1 38:930469a33001 16 printf("PIDController: not running, startup phase");
sbouber1 38:930469a33001 17 return;
sbouber1 38:930469a33001 18 }
sbouber1 38:930469a33001 19 #endif
sbouber1 38:930469a33001 20
sbouber1 35:c9261391a995 21 // Control the heater
sbouber1 35:c9261391a995 22 // This could be done in the pumping function as well, if needed
sbouber1 57:8dc3192ff150 23 if (this->isHeating() && this->temp->getValue() >= 33.0f) {
sbouber1 57:8dc3192ff150 24 this->setHeating(false);
sbouber1 58:b5f0c0f305ff 25 } else if (!this->isHeating() && this->temp->getValue() < 32.0f) {
sbouber1 57:8dc3192ff150 26 this->setHeating(true);
joran 49:ca6fb19fc280 27 }
sbouber1 35:c9261391a995 28
sbouber1 28:f4a4ee58d57e 29 float s = this->salt->getValue();
sbouber1 57:8dc3192ff150 30 float s_in_grams = this->getSaltInGrams();
sbouber1 30:cf12566013a5 31
sbouber1 32:1e4919a44196 32 if(s <= 6.0) {
sbouber1 30:cf12566013a5 33
sbouber1 57:8dc3192ff150 34 float ml = this->getMlSaltyWater(s_in_grams, this->proximity->getValue());
sbouber1 35:c9261391a995 35 int ml_int = static_cast<int>(ml);
sbouber1 30:cf12566013a5 36
sbouber1 35:c9261391a995 37 printf("PIDCONTROLLER: need to pump %d (%.3f) ml of salty water\r\n", ml_int, ml);
sbouber1 30:cf12566013a5 38
sbouber1 35:c9261391a995 39 //this->pump_salt_water(ml_int);
sbouber1 30:cf12566013a5 40
sbouber1 32:1e4919a44196 41 } else if(s >= 9.0) {
sbouber1 32:1e4919a44196 42
sbouber1 32:1e4919a44196 43 float ml = this->getMlFreshWater(s, this->proximity->getValue());
sbouber1 35:c9261391a995 44 int ml_int = static_cast<int>(ml);
sbouber1 32:1e4919a44196 45
sbouber1 35:c9261391a995 46 printf("PIDCONTROLLER: need to pump %d (%.3f) ml of fresh water\r\n", ml_int, ml);
sbouber1 35:c9261391a995 47
sbouber1 35:c9261391a995 48 //this->pump_fresh_water(ml_int);
sbouber1 32:1e4919a44196 49
sbouber1 30:cf12566013a5 50 }
sbouber1 28:f4a4ee58d57e 51 }
sbouber1 28:f4a4ee58d57e 52
sbouber1 57:8dc3192ff150 53 std::string PIDController::getName() {
sbouber1 30:cf12566013a5 54 return "PIDController";
sbouber1 28:f4a4ee58d57e 55 }
sbouber1 28:f4a4ee58d57e 56
joran 29:2b256a7ce0ae 57 //get the salt in the body in grams
sbouber1 57:8dc3192ff150 58 float PIDController::getSaltInGrams() {
sbouber1 57:8dc3192ff150 59 float current_ppt = this->salt->getValue(); //in ppt
sbouber1 57:8dc3192ff150 60 float current_vol = this->proximity->getValue(); //in ml
joran 29:2b256a7ce0ae 61
sbouber1 57:8dc3192ff150 62 return current_ppt * (current_vol / 1000);
joran 29:2b256a7ce0ae 63 }
joran 29:2b256a7ce0ae 64
joran 29:2b256a7ce0ae 65
sbouber1 57:8dc3192ff150 66 void PIDController::pumpSaltWater(int ml) {
sbouber1 57:8dc3192ff150 67 this->pumpWater(&mtr_salt, ml);
sbouber1 32:1e4919a44196 68 }
sbouber1 32:1e4919a44196 69
sbouber1 32:1e4919a44196 70
sbouber1 57:8dc3192ff150 71 void PIDController::pumpFreshWater(int ml) {
sbouber1 57:8dc3192ff150 72 this->pumpWater(&mtr_fresh, ml);
sbouber1 32:1e4919a44196 73 }
sbouber1 32:1e4919a44196 74
sbouber1 57:8dc3192ff150 75
sbouber1 57:8dc3192ff150 76 void PIDController::pumpWater(DRV8825 *mtr, int ml) {
joran 44:7c932cc5991b 77 LCDController::showPumping();
sbouber1 57:8dc3192ff150 78
joran 40:1668630544c7 79 this->pumping = true;
sbouber1 57:8dc3192ff150 80
sbouber1 32:1e4919a44196 81 int j = 5010 * (ml - 1);
sbouber1 32:1e4919a44196 82
sbouber1 32:1e4919a44196 83 for (int i = 500; i < MAX_SPEED; i += 5) {
sbouber1 46:7e4c1f2ab76c 84 mtr->settings(1 / MICROSTEPS_PER_STEP, RIGHT, i);
sbouber1 46:7e4c1f2ab76c 85 }
sbouber1 46:7e4c1f2ab76c 86
sbouber1 46:7e4c1f2ab76c 87 for (int i = 0; i < 2010 + j; i += 1) {
sbouber1 46:7e4c1f2ab76c 88 mtr->settings(1 / MICROSTEPS_PER_STEP, RIGHT, 8000);
sbouber1 46:7e4c1f2ab76c 89 }
sbouber1 46:7e4c1f2ab76c 90
sbouber1 46:7e4c1f2ab76c 91 for (int i = 8000; i > 500; i -= 5) {
sbouber1 46:7e4c1f2ab76c 92 mtr->settings(1 / MICROSTEPS_PER_STEP, RIGHT, i);
sbouber1 46:7e4c1f2ab76c 93 }
sbouber1 46:7e4c1f2ab76c 94
sbouber1 46:7e4c1f2ab76c 95 wait(5);
sbouber1 46:7e4c1f2ab76c 96
sbouber1 46:7e4c1f2ab76c 97 for (int i = 500; i < MAX_SPEED; i += 5) {
sbouber1 32:1e4919a44196 98 mtr->settings(1 / MICROSTEPS_PER_STEP, LEFT, i);
sbouber1 32:1e4919a44196 99 }
sbouber1 32:1e4919a44196 100
sbouber1 32:1e4919a44196 101 for (int i = 0; i < 2010 + j; i += 1) {
sbouber1 32:1e4919a44196 102 mtr->settings(1 / MICROSTEPS_PER_STEP, LEFT, 8000);
sbouber1 32:1e4919a44196 103 }
sbouber1 32:1e4919a44196 104
sbouber1 32:1e4919a44196 105 for (int i = 8000; i > 500; i -= 5) {
sbouber1 32:1e4919a44196 106 mtr->settings(1 / MICROSTEPS_PER_STEP, LEFT, i);
sbouber1 32:1e4919a44196 107 }
sbouber1 32:1e4919a44196 108
sbouber1 46:7e4c1f2ab76c 109 wait(5);
joran 40:1668630544c7 110 this->pumping = false;
sbouber1 32:1e4919a44196 111 }
sbouber1 32:1e4919a44196 112
sbouber1 32:1e4919a44196 113
sbouber1 57:8dc3192ff150 114 float PIDController::getMlSaltyWater(float grams_in_body, float volume_in_body) {
sbouber1 32:1e4919a44196 115
sbouber1 57:8dc3192ff150 116 float solution_gram_per_ten = 1.16f; // 1.0f for our solution
sbouber1 57:8dc3192ff150 117 float sol_volume = 10; // 10ml
sbouber1 32:1e4919a44196 118
sbouber1 57:8dc3192ff150 119 float ideal_ppt_constant = 0.007f; //7 ppt / 1000
sbouber1 57:8dc3192ff150 120 float x1 = volume_in_body * ideal_ppt_constant;
sbouber1 57:8dc3192ff150 121 float x2 = sol_volume * ideal_ppt_constant;
sbouber1 32:1e4919a44196 122
sbouber1 57:8dc3192ff150 123 x1 = x1 - grams_in_body;
sbouber1 57:8dc3192ff150 124 x2 = solution_gram_per_ten - x2;
sbouber1 32:1e4919a44196 125
sbouber1 57:8dc3192ff150 126 float output_ml = (x1 / x2 * sol_volume);
sbouber1 32:1e4919a44196 127
sbouber1 57:8dc3192ff150 128 return output_ml; // amount in ml to get 7 ppt.
sbouber1 35:c9261391a995 129 }
sbouber1 35:c9261391a995 130
sbouber1 57:8dc3192ff150 131 bool PIDController::isHeating() {
sbouber1 35:c9261391a995 132 return this->heating;
sbouber1 35:c9261391a995 133 }
sbouber1 35:c9261391a995 134
sbouber1 57:8dc3192ff150 135 bool PIDController::isPumping() {
joran 40:1668630544c7 136 return this->pumping;
joran 40:1668630544c7 137 }
joran 40:1668630544c7 138
sbouber1 57:8dc3192ff150 139 void PIDController::setHeating(bool enabled) {
sbouber1 35:c9261391a995 140 if(enabled == this->heating) return;
sbouber1 35:c9261391a995 141
sbouber1 35:c9261391a995 142 this->heating = enabled;
sbouber1 35:c9261391a995 143 if(enabled) {
sbouber1 57:8dc3192ff150 144 #ifdef TEST_MODE
sbouber1 35:c9261391a995 145 printf("Should set heater to 1\r\n");
sbouber1 35:c9261391a995 146 #else
sbouber1 35:c9261391a995 147 heater = 1;
sbouber1 35:c9261391a995 148 #endif
sbouber1 35:c9261391a995 149 } else {
sbouber1 57:8dc3192ff150 150 #ifdef TEST_MODE
sbouber1 35:c9261391a995 151 printf("Should set heater to 0\r\n");
sbouber1 35:c9261391a995 152 #else
sbouber1 35:c9261391a995 153 heater = 0;
sbouber1 35:c9261391a995 154 #endif
sbouber1 32:1e4919a44196 155 }
sbouber1 35:c9261391a995 156 }
sbouber1 32:1e4919a44196 157
sbouber1 32:1e4919a44196 158 float PIDController::getMlFreshWater(float ppt, float volume) {
sbouber1 32:1e4919a44196 159 return (volume * (ppt / 7.0)) - volume;
sbouber1 32:1e4919a44196 160 }
sbouber1 32:1e4919a44196 161
sbouber1 46:7e4c1f2ab76c 162 void PIDController::doTestingStuff(int ml) {
sbouber1 46:7e4c1f2ab76c 163 while(1)
sbouber1 57:8dc3192ff150 164 this->pumpSaltWater(ml);
sbouber1 46:7e4c1f2ab76c 165 }
sbouber1 46:7e4c1f2ab76c 166