Artem Solomatin
/
pendudu
fsdfds
main.cpp@4:fd49edfabfb2, 2020-05-17 (annotated)
- Committer:
- teamat
- Date:
- Sun May 17 16:13:43 2020 +0000
- Revision:
- 4:fd49edfabfb2
- Parent:
- 3:8708e61475fe
- Child:
- 5:9aae12408a54
Try to restore old
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
teamat | 3:8708e61475fe | 1 | #include "mbed.h" |
teamat | 3:8708e61475fe | 2 | |
teamat | 3:8708e61475fe | 3 | #define M_PI 3.14159265358979323846f |
teamat | 3:8708e61475fe | 4 | #define smoothingNumber 6 |
teamat | 3:8708e61475fe | 5 | |
teamat | 3:8708e61475fe | 6 | #define STATE_ERROR 0 |
teamat | 3:8708e61475fe | 7 | #define STATE_INIT 1 |
teamat | 3:8708e61475fe | 8 | #define STATE_GOTO_START 2 |
teamat | 3:8708e61475fe | 9 | #define STATE_GOTO_END_COUNTING 3 |
teamat | 3:8708e61475fe | 10 | #define STATE_GOTO_MIDDLE 4 |
teamat | 3:8708e61475fe | 11 | #define STATE_WAITING 5 |
teamat | 3:8708e61475fe | 12 | #define STATE_GOTO_SWING 6 |
teamat | 3:8708e61475fe | 13 | #define STATE_START_SWING 7 |
teamat | 3:8708e61475fe | 14 | #define STATE_SWING_RIGHT 8 |
teamat | 3:8708e61475fe | 15 | #define STATE_SWING_LEFT 9 |
teamat | 3:8708e61475fe | 16 | #define STATE_EMPTY_SWING 10 |
teamat | 3:8708e61475fe | 17 | |
teamat | 3:8708e61475fe | 18 | #define DIR_LEFT 0 |
teamat | 3:8708e61475fe | 19 | #define DIR_RIGHT 1 |
teamat | 3:8708e61475fe | 20 | |
teamat | 3:8708e61475fe | 21 | //Serial pc(D1,D0,4800); |
teamat | 3:8708e61475fe | 22 | DigitalOut RCout(D10); |
teamat | 3:8708e61475fe | 23 | DigitalOut dir(D9); |
teamat | 3:8708e61475fe | 24 | InterruptIn leftSwitch(D2); |
teamat | 3:8708e61475fe | 25 | InterruptIn rightSwitch(D3); |
teamat | 3:8708e61475fe | 26 | Ticker tick; |
teamat | 4:fd49edfabfb2 | 27 | Ticker speedTicker; |
teamat | 4:fd49edfabfb2 | 28 | Ticker swingTicker; |
teamat | 3:8708e61475fe | 29 | DigitalOut myled(LED2); |
teamat | 3:8708e61475fe | 30 | RawSerial rpc(D1,D0,9600); |
teamat | 3:8708e61475fe | 31 | |
teamat | 3:8708e61475fe | 32 | int period_us = 26;//300 26 |
teamat | 3:8708e61475fe | 33 | |
teamat | 3:8708e61475fe | 34 | long pos=0; |
teamat | 3:8708e61475fe | 35 | |
teamat | 3:8708e61475fe | 36 | long railLength = 0; |
teamat | 3:8708e61475fe | 37 | |
teamat | 3:8708e61475fe | 38 | uint8_t state=STATE_INIT; |
teamat | 3:8708e61475fe | 39 | |
teamat | 3:8708e61475fe | 40 | Timer t; |
teamat | 3:8708e61475fe | 41 | SPI spi(D11,D12,D13);// mosi, miso, sclk |
teamat | 3:8708e61475fe | 42 | DigitalOut cs(D5); |
teamat | 3:8708e61475fe | 43 | |
teamat | 4:fd49edfabfb2 | 44 | float radius = 0.0025; |
teamat | 3:8708e61475fe | 45 | |
teamat | 3:8708e61475fe | 46 | float angularPosNew = 0; |
teamat | 3:8708e61475fe | 47 | float angularPosOld = 0; |
teamat | 3:8708e61475fe | 48 | |
teamat | 3:8708e61475fe | 49 | float timeOld = 0.0f; |
teamat | 3:8708e61475fe | 50 | float timeStart = 0.0f; |
teamat | 3:8708e61475fe | 51 | |
teamat | 3:8708e61475fe | 52 | float dx = 0; |
teamat | 3:8708e61475fe | 53 | float xPosNew = 0; |
teamat | 3:8708e61475fe | 54 | float xPosOld = 0; |
teamat | 4:fd49edfabfb2 | 55 | float speed = 0; |
teamat | 3:8708e61475fe | 56 | |
teamat | 3:8708e61475fe | 57 | double dAngle = 0.0f; |
teamat | 3:8708e61475fe | 58 | double anSpd = 0.0f; |
teamat | 3:8708e61475fe | 59 | |
teamat | 3:8708e61475fe | 60 | float timeOldPos = 0.0f; |
teamat | 3:8708e61475fe | 61 | float timeStartPos = 0.0f; |
teamat | 3:8708e61475fe | 62 | |
teamat | 4:fd49edfabfb2 | 63 | float angle=0.0f; |
teamat | 3:8708e61475fe | 64 | float angleOffset = 0; |
teamat | 3:8708e61475fe | 65 | |
teamat | 4:fd49edfabfb2 | 66 | float control = 0.0f; |
teamat | 4:fd49edfabfb2 | 67 | |
teamat | 3:8708e61475fe | 68 | double PIPI = 6.28; |
teamat | 3:8708e61475fe | 69 | |
teamat | 3:8708e61475fe | 70 | bool canSend = false; |
teamat | 3:8708e61475fe | 71 | |
teamat | 3:8708e61475fe | 72 | typedef union { |
teamat | 4:fd49edfabfb2 | 73 | float number[6]; |
teamat | 4:fd49edfabfb2 | 74 | uint8_t numberCh[24]; |
teamat | 3:8708e61475fe | 75 | } my_union; |
teamat | 3:8708e61475fe | 76 | |
teamat | 3:8708e61475fe | 77 | my_union myUnion; |
teamat | 3:8708e61475fe | 78 | |
teamat | 3:8708e61475fe | 79 | bool isPendulumSwinging() { |
teamat | 3:8708e61475fe | 80 | return state == STATE_SWING_RIGHT || state == STATE_SWING_LEFT; |
teamat | 3:8708e61475fe | 81 | } |
teamat | 3:8708e61475fe | 82 | |
teamat | 3:8708e61475fe | 83 | float getPosMM() { |
teamat | 3:8708e61475fe | 84 | //return (pos-railLength/2) * 550.0f/railLength; |
teamat | 3:8708e61475fe | 85 | //return (pos - railLength / 2) * (350.0f / railLength); |
teamat | 3:8708e61475fe | 86 | return pos / 3500.0f; |
teamat | 3:8708e61475fe | 87 | } |
teamat | 3:8708e61475fe | 88 | |
teamat | 3:8708e61475fe | 89 | uint16_t getPendulumPos(){ |
teamat | 3:8708e61475fe | 90 | cs=0; |
teamat | 3:8708e61475fe | 91 | wait_ms(1); |
teamat | 3:8708e61475fe | 92 | uint16_t d=spi.write((short)0x00); |
teamat | 3:8708e61475fe | 93 | d=d<<1;//fucking shithole fakebit |
teamat | 3:8708e61475fe | 94 | d=d>>6;//no need debug info |
teamat | 3:8708e61475fe | 95 | cs=1; |
teamat | 3:8708e61475fe | 96 | wait_ms(1); |
teamat | 3:8708e61475fe | 97 | return (uint16_t)d; |
teamat | 3:8708e61475fe | 98 | } |
teamat | 3:8708e61475fe | 99 | |
teamat | 3:8708e61475fe | 100 | |
teamat | 3:8708e61475fe | 101 | float getPendulumAngle(){ |
teamat | 3:8708e61475fe | 102 | angle = getPendulumPos(); |
teamat | 3:8708e61475fe | 103 | angle = angle * 6.28f / 1024.0f; |
teamat | 4:fd49edfabfb2 | 104 | angle += angleOffset; |
teamat | 4:fd49edfabfb2 | 105 | if (angle > PIPI + 0.01) { |
teamat | 4:fd49edfabfb2 | 106 | angle = fmod((angle + 3.14), PIPI) - 3.14; |
teamat | 4:fd49edfabfb2 | 107 | if (angle < -3.14) { |
teamat | 4:fd49edfabfb2 | 108 | angle += PIPI; |
teamat | 4:fd49edfabfb2 | 109 | } |
teamat | 4:fd49edfabfb2 | 110 | } |
teamat | 3:8708e61475fe | 111 | return angle; |
teamat | 3:8708e61475fe | 112 | } |
teamat | 3:8708e61475fe | 113 | |
teamat | 3:8708e61475fe | 114 | |
teamat | 3:8708e61475fe | 115 | /* |
teamat | 3:8708e61475fe | 116 | ANGULAR SPEED CALC |
teamat | 3:8708e61475fe | 117 | */ |
teamat | 3:8708e61475fe | 118 | |
teamat | 3:8708e61475fe | 119 | void getDeltaAng(){ |
teamat | 3:8708e61475fe | 120 | |
teamat | 3:8708e61475fe | 121 | angularPosNew = getPendulumAngle(); |
teamat | 3:8708e61475fe | 122 | |
teamat | 3:8708e61475fe | 123 | dAngle = fmod((angularPosNew - angularPosOld + 3.14), PIPI) - 3.14; |
teamat | 3:8708e61475fe | 124 | if (dAngle < -3.14) { |
teamat | 3:8708e61475fe | 125 | dAngle += PIPI; |
teamat | 3:8708e61475fe | 126 | } |
teamat | 3:8708e61475fe | 127 | |
teamat | 3:8708e61475fe | 128 | angularPosOld = angularPosNew; |
teamat | 3:8708e61475fe | 129 | |
teamat | 3:8708e61475fe | 130 | } |
teamat | 3:8708e61475fe | 131 | |
teamat | 3:8708e61475fe | 132 | void getAngularSpeed(){ |
teamat | 3:8708e61475fe | 133 | float deltaTime; |
teamat | 3:8708e61475fe | 134 | |
teamat | 3:8708e61475fe | 135 | timeStart = float(t.read()); |
teamat | 3:8708e61475fe | 136 | deltaTime = (timeStart - timeOld); |
teamat | 3:8708e61475fe | 137 | getDeltaAng(); |
teamat | 3:8708e61475fe | 138 | anSpd = dAngle / deltaTime; |
teamat | 3:8708e61475fe | 139 | timeOld=timeStart; |
teamat | 3:8708e61475fe | 140 | //взятие по модулю, спросить |
teamat | 3:8708e61475fe | 141 | } |
teamat | 3:8708e61475fe | 142 | |
teamat | 3:8708e61475fe | 143 | /* |
teamat | 3:8708e61475fe | 144 | SPEED CALC |
teamat | 3:8708e61475fe | 145 | */ |
teamat | 3:8708e61475fe | 146 | |
teamat | 3:8708e61475fe | 147 | void getDeltaPos() |
teamat | 3:8708e61475fe | 148 | { |
teamat | 3:8708e61475fe | 149 | float delta = 0; |
teamat | 3:8708e61475fe | 150 | xPosNew = getPosMM(); |
teamat | 3:8708e61475fe | 151 | delta = xPosNew - xPosOld; |
teamat | 3:8708e61475fe | 152 | dx = delta; |
teamat | 3:8708e61475fe | 153 | xPosOld = xPosNew; |
teamat | 3:8708e61475fe | 154 | } |
teamat | 3:8708e61475fe | 155 | |
teamat | 4:fd49edfabfb2 | 156 | /*float getSpeed(){ |
teamat | 3:8708e61475fe | 157 | float deltaTime; |
teamat | 3:8708e61475fe | 158 | float speed; |
teamat | 3:8708e61475fe | 159 | getDeltaPos(); |
teamat | 3:8708e61475fe | 160 | timeStartPos = float(t.read()); |
teamat | 3:8708e61475fe | 161 | deltaTime = (timeStartPos - timeOldPos); |
teamat | 3:8708e61475fe | 162 | speed = (dx) * deltaTime; |
teamat | 3:8708e61475fe | 163 | timeOldPos = timeStartPos; |
teamat | 3:8708e61475fe | 164 | //взятие по модулю, спросить |
teamat | 3:8708e61475fe | 165 | return speed; |
teamat | 4:fd49edfabfb2 | 166 | }*/ |
teamat | 4:fd49edfabfb2 | 167 | |
teamat | 4:fd49edfabfb2 | 168 | void calcSpeed() { |
teamat | 4:fd49edfabfb2 | 169 | xPosNew = getPosMM() / 1000; |
teamat | 4:fd49edfabfb2 | 170 | speed = xPosNew - xPosOld; |
teamat | 4:fd49edfabfb2 | 171 | xPosOld = xPosNew; |
teamat | 4:fd49edfabfb2 | 172 | } |
teamat | 4:fd49edfabfb2 | 173 | |
teamat | 4:fd49edfabfb2 | 174 | void calcControl() { |
teamat | 4:fd49edfabfb2 | 175 | float frequency = 1000000 / (period_us / 2); |
teamat | 4:fd49edfabfb2 | 176 | float rates = frequency / 6400; |
teamat | 4:fd49edfabfb2 | 177 | control = rates * PIPI * radius; |
teamat | 3:8708e61475fe | 178 | } |
teamat | 3:8708e61475fe | 179 | |
teamat | 3:8708e61475fe | 180 | |
teamat | 3:8708e61475fe | 181 | |
teamat | 3:8708e61475fe | 182 | void stepperFlip() { |
teamat | 3:8708e61475fe | 183 | if (state != STATE_WAITING && state != STATE_ERROR && state != STATE_INIT && state){ |
teamat | 3:8708e61475fe | 184 | RCout = !RCout; |
teamat | 3:8708e61475fe | 185 | pos += (dir.read() * 2 - 1); |
teamat | 3:8708e61475fe | 186 | } |
teamat | 3:8708e61475fe | 187 | if (state == STATE_GOTO_MIDDLE && pos == railLength / 2) { |
teamat | 3:8708e61475fe | 188 | state = STATE_WAITING; |
teamat | 3:8708e61475fe | 189 | } |
teamat | 3:8708e61475fe | 190 | if (state == STATE_SWING_LEFT && state==STATE_SWING_RIGHT) { |
teamat | 3:8708e61475fe | 191 | pos += (dir.read() * 2 - 1); |
teamat | 3:8708e61475fe | 192 | RCout = !RCout; |
teamat | 3:8708e61475fe | 193 | } |
teamat | 3:8708e61475fe | 194 | } |
teamat | 3:8708e61475fe | 195 | |
teamat | 3:8708e61475fe | 196 | |
teamat | 3:8708e61475fe | 197 | void updatePeriod(){ |
teamat | 3:8708e61475fe | 198 | tick.detach(); |
teamat | 3:8708e61475fe | 199 | tick.attach_us (&stepperFlip, period_us / 2.0f); |
teamat | 3:8708e61475fe | 200 | } |
teamat | 3:8708e61475fe | 201 | |
teamat | 3:8708e61475fe | 202 | void leftEnd() { |
teamat | 3:8708e61475fe | 203 | dir = DIR_RIGHT; |
teamat | 3:8708e61475fe | 204 | if (state == STATE_GOTO_START) { |
teamat | 3:8708e61475fe | 205 | state = STATE_GOTO_END_COUNTING; |
teamat | 3:8708e61475fe | 206 | pos = 0; |
teamat | 3:8708e61475fe | 207 | } |
teamat | 3:8708e61475fe | 208 | else if (isPendulumSwinging()) { |
teamat | 3:8708e61475fe | 209 | state = STATE_GOTO_MIDDLE; |
teamat | 3:8708e61475fe | 210 | //angleOffset -= 0.006191; |
teamat | 3:8708e61475fe | 211 | //state = STATE_ERROR; |
teamat | 3:8708e61475fe | 212 | } |
teamat | 3:8708e61475fe | 213 | //при втыкании в концевик меняем смещение (offset) |
teamat | 3:8708e61475fe | 214 | } |
teamat | 3:8708e61475fe | 215 | |
teamat | 3:8708e61475fe | 216 | void rightEnd() { |
teamat | 3:8708e61475fe | 217 | dir=DIR_LEFT; |
teamat | 3:8708e61475fe | 218 | if (state == STATE_GOTO_END_COUNTING) { |
teamat | 3:8708e61475fe | 219 | railLength=pos; |
teamat | 3:8708e61475fe | 220 | state = STATE_GOTO_MIDDLE; |
teamat | 3:8708e61475fe | 221 | } |
teamat | 3:8708e61475fe | 222 | else if (isPendulumSwinging()) { |
teamat | 3:8708e61475fe | 223 | state = STATE_GOTO_MIDDLE; |
teamat | 3:8708e61475fe | 224 | //angleOffset += 0.006191; |
teamat | 3:8708e61475fe | 225 | //state = STATE_ERROR; |
teamat | 3:8708e61475fe | 226 | } |
teamat | 3:8708e61475fe | 227 | } |
teamat | 3:8708e61475fe | 228 | |
teamat | 3:8708e61475fe | 229 | void getSwingDirectory() { |
teamat | 4:fd49edfabfb2 | 230 | control = -control; |
teamat | 4:fd49edfabfb2 | 231 | if (dir == DIR_RIGHT) { |
teamat | 3:8708e61475fe | 232 | state = STATE_SWING_RIGHT; |
teamat | 3:8708e61475fe | 233 | dir = DIR_LEFT; |
teamat | 3:8708e61475fe | 234 | return; |
teamat | 3:8708e61475fe | 235 | } |
teamat | 4:fd49edfabfb2 | 236 | if (dir == DIR_LEFT) { |
teamat | 3:8708e61475fe | 237 | state = STATE_SWING_LEFT; |
teamat | 3:8708e61475fe | 238 | dir = DIR_RIGHT; |
teamat | 3:8708e61475fe | 239 | return; |
teamat | 3:8708e61475fe | 240 | } |
teamat | 3:8708e61475fe | 241 | } |
teamat | 3:8708e61475fe | 242 | |
teamat | 3:8708e61475fe | 243 | void sendData() { |
teamat | 3:8708e61475fe | 244 | myUnion.number[0] = t.read(); |
teamat | 3:8708e61475fe | 245 | myUnion.number[1] = dx; |
teamat | 4:fd49edfabfb2 | 246 | myUnion.number[2] = speed; |
teamat | 4:fd49edfabfb2 | 247 | //myUnion.number[3] = dAngle; |
teamat | 4:fd49edfabfb2 | 248 | myUnion.number[3] = angle; |
teamat | 3:8708e61475fe | 249 | myUnion.number[4] = anSpd; |
teamat | 4:fd49edfabfb2 | 250 | myUnion.number[5] = control; |
teamat | 4:fd49edfabfb2 | 251 | for(int i = 0; i < 24; i++) { |
teamat | 3:8708e61475fe | 252 | rpc.putc(myUnion.numberCh[i]); |
teamat | 3:8708e61475fe | 253 | } |
teamat | 3:8708e61475fe | 254 | } |
teamat | 3:8708e61475fe | 255 | |
teamat | 3:8708e61475fe | 256 | void Rx_interrupt() { |
teamat | 4:fd49edfabfb2 | 257 | int command = rpc.getc(); |
teamat | 4:fd49edfabfb2 | 258 | if (command == 50) { |
teamat | 3:8708e61475fe | 259 | canSend = true; |
teamat | 3:8708e61475fe | 260 | } |
teamat | 3:8708e61475fe | 261 | return; |
teamat | 3:8708e61475fe | 262 | } |
teamat | 3:8708e61475fe | 263 | |
teamat | 3:8708e61475fe | 264 | int main() { |
teamat | 3:8708e61475fe | 265 | RCout = 1; |
teamat | 3:8708e61475fe | 266 | wait_ms(500); |
teamat | 3:8708e61475fe | 267 | spi.format(16,2); |
teamat | 3:8708e61475fe | 268 | spi.frequency(1000000); |
teamat | 3:8708e61475fe | 269 | t.start(); |
teamat | 3:8708e61475fe | 270 | leftSwitch.rise(&leftEnd); |
teamat | 3:8708e61475fe | 271 | rightSwitch.rise(&rightEnd); |
teamat | 4:fd49edfabfb2 | 272 | rpc.attach(&Rx_interrupt, Serial::RxIrq); |
teamat | 3:8708e61475fe | 273 | for (int i=5; i>0; i--) { |
teamat | 3:8708e61475fe | 274 | getPendulumAngle(); |
teamat | 3:8708e61475fe | 275 | wait_ms(500); |
teamat | 3:8708e61475fe | 276 | } |
teamat | 4:fd49edfabfb2 | 277 | angleOffset= 3.14 - angle; |
teamat | 3:8708e61475fe | 278 | updatePeriod(); |
teamat | 3:8708e61475fe | 279 | state=STATE_GOTO_START; |
teamat | 3:8708e61475fe | 280 | dir=DIR_LEFT; |
teamat | 3:8708e61475fe | 281 | while(1) { |
teamat | 4:fd49edfabfb2 | 282 | getAngularSpeed(); |
teamat | 3:8708e61475fe | 283 | if(canSend) { |
teamat | 3:8708e61475fe | 284 | sendData(); |
teamat | 3:8708e61475fe | 285 | } |
teamat | 3:8708e61475fe | 286 | switch(state) { |
teamat | 3:8708e61475fe | 287 | case STATE_WAITING: |
teamat | 3:8708e61475fe | 288 | state = STATE_GOTO_SWING; |
teamat | 3:8708e61475fe | 289 | break; |
teamat | 3:8708e61475fe | 290 | case STATE_GOTO_START: |
teamat | 3:8708e61475fe | 291 | break; |
teamat | 3:8708e61475fe | 292 | case STATE_GOTO_END_COUNTING: |
teamat | 3:8708e61475fe | 293 | break; |
teamat | 3:8708e61475fe | 294 | case STATE_GOTO_SWING: |
teamat | 4:fd49edfabfb2 | 295 | speedTicker.attach(calcSpeed, 1); |
teamat | 4:fd49edfabfb2 | 296 | swingTicker.attach(getSwingDirectory, 1); |
teamat | 4:fd49edfabfb2 | 297 | state = STATE_SWING_LEFT; |
teamat | 3:8708e61475fe | 298 | break; |
teamat | 3:8708e61475fe | 299 | case STATE_SWING_LEFT: |
teamat | 3:8708e61475fe | 300 | break; |
teamat | 3:8708e61475fe | 301 | case STATE_SWING_RIGHT: |
teamat | 3:8708e61475fe | 302 | break; |
teamat | 3:8708e61475fe | 303 | default: |
teamat | 3:8708e61475fe | 304 | break; |
teamat | 3:8708e61475fe | 305 | } |
teamat | 3:8708e61475fe | 306 | //wait_ms(5); |
teamat | 3:8708e61475fe | 307 | } |
teamat | 3:8708e61475fe | 308 | } |