Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Dependencies: mbed ll16j23s_test_docs
SnakeBody/SnakeBody.cpp
- Committer:
- JoeShotton
- Date:
- 2020-05-27
- Revision:
- 13:7b7ec5db56b2
- Parent:
- 10:a2d643b3c782
- Child:
- 14:2dfe04ced21c
File content as of revision 13:7b7ec5db56b2:
#include "SnakeBody.h" SnakeBody::SnakeBody() { head_x = 42; head_y = 24; _length = 4; _length_increase = 4; _angle = -1.0; _move_state = 0; _d = 0; } SnakeBody::~SnakeBody() { //destructor } void SnakeBody::init() { body_x.clear(); body_x.push_back(42); body_y.clear(); body_y.push_back(24); } void SnakeBody::update_direction() { if ((head_x % 2) + (head_y % 2) == 0) { // only allows changing movement when the snake is cell-aligned (ie x and y are even) // partition 360 into segments and check which segment the angle is in printf("D: %d\n", _d); if (_angle < 0.0f) { //check for -1.0 angle _d = 0; } else if (_angle < 45.0f) { //North quadrant _d = 1; } else if (_angle < 135.0f) { //East quadrant _d = 2; } else if (_angle < 225.0f) { //South quadrant _d = 3; } else if (_angle < 315.0f) { //West quadrant _d = 4; } else { //NW half - quadrant _d = 1; } } }; void SnakeBody::update_position() { Direction _fsm[5] = { {0, 0, {0,1,2,3,4}}, // Centred {0, -1, {1,1,2,1,4}}, // North, will not go to centre or south {1, 0, {2,1,2,3,2}}, // East, will not go to centre or west {0, 1, {3,3,2,3,4}}, // South, will not go to centre or north {-1, 0, {4,1,4,3,4}} // West, will not go to centre or east }; _move_state = _fsm[_move_state].nextState[_d]; // adjusts fsm state based on direction //printf("State: %d\n", _move_state); head_x += _fsm[_move_state].delta_x; // increments x value based on fsm state value head_y += _fsm[_move_state].delta_y; // increments y value based on fsm state value head_x = ((head_x % 84) + 84) % 84; // wraps x back to within range 0-83 head_y = ((head_y % 48) + 48) % 48; // wraps y back to within range 0-47 //printf("head_x: %d\n", head_x); //printf("head_y: %d\n", head_y); }; void SnakeBody::snake_movement(Gamepad &pad) { _angle = pad.get_angle(); //finds joystick angle //printf("Angle: %f\n", _angle); update_direction(); //converts angle into a integer direction update_position(); //takes integer direction and feeds it into FSM to move snake in correct direction update_body(); //feeds head coords into body vectors and remove old ones } void SnakeBody::update_body() { if ((head_x % 2) + (head_y % 2) == 0) { //only updates body when cell aligned body_x.insert(body_x.begin(), head_x); //sets first array element to head coordinates body_y.insert(body_y.begin(), head_y); body_x.erase(body_x.begin() + _length, body_x.end()); //erases all elements from position after tail (ie [_length]) body_y.erase(body_y.begin() + _length, body_y.end()); //up to end of vector } if(_length_increase > 0) { //converts length increase into length, one unit at a time _length++; _length_increase--; } } void SnakeBody::draw_body(N5110 &lcd) { lcd.drawRect(head_x, head_y, 2, 2, FILL_BLACK); //draws square at head (so new head coords displayed even when not cell-aligned) for(int i = 0; i < _length - 3; i++) { //iterates across vector to draw sqaures at every position lcd.drawRect(body_x[i], body_y[i], 2, 2, FILL_BLACK); } } void SnakeBody::snake_snake_collision(Gamepad &pad, bool &_death) { if (_move_state > 0) { //if body has started to move for(int i = 3; i < _length - 3; i++) { //only checks from 3rd cell onwards since head can't collide with very start of body if (head_x == body_x[i] && head_y == body_y[i]) { //checks if head coord is the same as any of the body coords //printf("S-S Collison \n"); _move_state = 0; _death = true; } } } } void SnakeBody::add_length(int increase) { _length_increase += increase; } void SnakeBody::run(Gamepad &pad, N5110 &lcd, bool &_death) { snake_movement(pad); draw_body(lcd); snake_snake_collision(pad, _death); //printf("Body running!"); } void SnakeBody::reset() { head_x = 42; head_y = 24; for(int i = 3; i < body_y.size(); i++) { body_y.at(i) = 50; //moves all body coordinates off-screen } _length = 4; _length_increase = 4; _move_state = 0; }