Elements used in the Balls and Things games for the RETRO.

Dependents:   RETRO_BallsAndPaddle RETRO_BallAndHoles

Committer:
maxint
Date:
Wed Feb 25 10:43:15 2015 +0000
Revision:
2:74bc9b16fb88
Parent:
0:3d0db4e183ee
Child:
3:441dc90d10ce
added methods for better bouncing experiments

Who changed what in which revision?

UserRevisionLine numberNew contents of line
maxint 0:3d0db4e183ee 1 #include "Ball.h"
maxint 0:3d0db4e183ee 2
maxint 0:3d0db4e183ee 3 Ball::Ball() : vSpeed()
maxint 0:3d0db4e183ee 4 { // constructor
maxint 0:3d0db4e183ee 5 }
maxint 0:3d0db4e183ee 6
maxint 0:3d0db4e183ee 7 Ball::Ball(LCD_ST7735* pDisp) : vSpeed()
maxint 0:3d0db4e183ee 8 { // constructor
maxint 0:3d0db4e183ee 9 this->pDisp=pDisp;
maxint 0:3d0db4e183ee 10 this->fActive=false;
maxint 0:3d0db4e183ee 11 }
maxint 0:3d0db4e183ee 12
maxint 0:3d0db4e183ee 13 uint16_t Ball::dimmedColor(uint16_t uColor)
maxint 0:3d0db4e183ee 14 {
maxint 0:3d0db4e183ee 15 uint16_t r, g, b;
maxint 0:3d0db4e183ee 16
maxint 0:3d0db4e183ee 17 r=(uColor >> 11) <<3;
maxint 0:3d0db4e183ee 18 g=((uColor >> 5) & 0x3F) <<2;
maxint 0:3d0db4e183ee 19 b=(uColor & 0x1F) << 3;
maxint 0:3d0db4e183ee 20 r=r*2/3;
maxint 0:3d0db4e183ee 21 g=g*2/3;
maxint 0:3d0db4e183ee 22 b=b*2/3;
maxint 0:3d0db4e183ee 23 // r=r/2;
maxint 0:3d0db4e183ee 24 // g=g/2;
maxint 0:3d0db4e183ee 25 // b=b/2;
maxint 0:3d0db4e183ee 26
maxint 0:3d0db4e183ee 27 return(Color565::fromRGB((uint16_t)r,(uint16_t)g,(uint16_t)b));
maxint 0:3d0db4e183ee 28 }
maxint 0:3d0db4e183ee 29
maxint 0:3d0db4e183ee 30 void Ball::initialize(int nX, int nY, int nR, uint16_t uColor)
maxint 0:3d0db4e183ee 31 {
maxint 0:3d0db4e183ee 32 this->pos.set(nX, nY);
maxint 0:3d0db4e183ee 33 this->nRadius=nR;
maxint 0:3d0db4e183ee 34 this->uColor=uColor;
maxint 0:3d0db4e183ee 35 this->uColorHigh=uColor;
maxint 0:3d0db4e183ee 36 this->uColorMid=dimmedColor(uColorHigh);
maxint 0:3d0db4e183ee 37 this->uColorLow=dimmedColor(uColorMid);
maxint 0:3d0db4e183ee 38
maxint 0:3d0db4e183ee 39 }
maxint 0:3d0db4e183ee 40
maxint 0:3d0db4e183ee 41 void Ball::setSpeed(int X, int Y)
maxint 0:3d0db4e183ee 42 {
maxint 0:3d0db4e183ee 43 this->vSpeed.set(X, Y);
maxint 0:3d0db4e183ee 44 }
maxint 0:3d0db4e183ee 45
maxint 0:3d0db4e183ee 46 void Ball::changeSpeed(bool fUp)
maxint 0:3d0db4e183ee 47 {
maxint 0:3d0db4e183ee 48 if(fUp)
maxint 0:3d0db4e183ee 49 {
maxint 0:3d0db4e183ee 50 if(this->vSpeed.getSize()<=4.0) this->vSpeed.add(1.0);
maxint 0:3d0db4e183ee 51 }
maxint 0:3d0db4e183ee 52 else
maxint 0:3d0db4e183ee 53 {
maxint 0:3d0db4e183ee 54 if(this->vSpeed.getSize()>=1.0)
maxint 0:3d0db4e183ee 55 this->vSpeed.add(-1.0);
maxint 0:3d0db4e183ee 56 else // TODO: added code below to allow zero speed pause of ball
maxint 0:3d0db4e183ee 57 this->vSpeed.set(0,0);
maxint 0:3d0db4e183ee 58 }
maxint 0:3d0db4e183ee 59 }
maxint 0:3d0db4e183ee 60
maxint 0:3d0db4e183ee 61 void Ball::unmove()
maxint 0:3d0db4e183ee 62 { // move back to previous position
maxint 0:3d0db4e183ee 63 pos.set(pos.getPrev());
maxint 0:3d0db4e183ee 64 }
maxint 0:3d0db4e183ee 65
maxint 0:3d0db4e183ee 66 void Ball::update()
maxint 0:3d0db4e183ee 67 {
maxint 0:3d0db4e183ee 68 this->pos.move(this->vSpeed);
maxint 0:3d0db4e183ee 69 }
maxint 0:3d0db4e183ee 70
maxint 0:3d0db4e183ee 71 Circle Ball::getBoundingCircle()
maxint 0:3d0db4e183ee 72 {
maxint 0:3d0db4e183ee 73 return(Circle(this->pos.getX(), this->pos.getY(), this->nRadius));
maxint 0:3d0db4e183ee 74 }
maxint 0:3d0db4e183ee 75
maxint 0:3d0db4e183ee 76 bool Ball::collides(Rectangle r)
maxint 0:3d0db4e183ee 77 {
maxint 0:3d0db4e183ee 78 Circle cBall=this->getBoundingCircle();
maxint 0:3d0db4e183ee 79 Rectangle rBall=cBall.getBoundingRectangle();
maxint 0:3d0db4e183ee 80
maxint 0:3d0db4e183ee 81 /*
maxint 0:3d0db4e183ee 82 char szBuffer[256];
maxint 0:3d0db4e183ee 83 sprintf(szBuffer, "c:%d,%d ", cBall.getX(), cBall.getY());
maxint 0:3d0db4e183ee 84 this->pDisp->drawString(font_oem, 0, 0, szBuffer);
maxint 0:3d0db4e183ee 85 */
maxint 0:3d0db4e183ee 86 return(rBall.collides(r));
maxint 0:3d0db4e183ee 87 }
maxint 0:3d0db4e183ee 88
maxint 0:3d0db4e183ee 89 void Ball::Bounce(Vector vBounce)
maxint 0:3d0db4e183ee 90 { // change the direction in a certain direction
maxint 0:3d0db4e183ee 91 this->unmove(); // undo move to pre-bouncing position to avoid drawing on colliding position
maxint 0:3d0db4e183ee 92
maxint 0:3d0db4e183ee 93 this->vSpeed.multiply(vBounce);
maxint 2:74bc9b16fb88 94 //this->vSpeed.bounce(vBounce);
maxint 0:3d0db4e183ee 95
maxint 0:3d0db4e183ee 96 // check speed w/max
maxint 0:3d0db4e183ee 97 if(this->vSpeed.y>5.0) this->vSpeed.y=5;
maxint 2:74bc9b16fb88 98 if(this->vSpeed.x>5.0) this->vSpeed.x=5;
maxint 2:74bc9b16fb88 99 if(this->vSpeed.y<-5.0) this->vSpeed.y=-5;
maxint 2:74bc9b16fb88 100 if(this->vSpeed.x<-5.0) this->vSpeed.x=-5;
maxint 2:74bc9b16fb88 101 }
maxint 2:74bc9b16fb88 102
maxint 2:74bc9b16fb88 103 void Ball::BounceAgainst(Vector vBounce)
maxint 2:74bc9b16fb88 104 { // change the direction in a certain direction
maxint 2:74bc9b16fb88 105 this->unmove(); // undo move to pre-bouncing position to avoid drawing on colliding position
maxint 2:74bc9b16fb88 106
maxint 2:74bc9b16fb88 107 //this->vSpeed.multiply(vBounce);
maxint 2:74bc9b16fb88 108 this->vSpeed.bounce(vBounce);
maxint 2:74bc9b16fb88 109
maxint 2:74bc9b16fb88 110 // check speed w/max
maxint 2:74bc9b16fb88 111 if(this->vSpeed.y>5.0) this->vSpeed.y=5;
maxint 2:74bc9b16fb88 112 if(this->vSpeed.x>5.0) this->vSpeed.x=5;
maxint 2:74bc9b16fb88 113 if(this->vSpeed.y<-5.0) this->vSpeed.y=-5;
maxint 2:74bc9b16fb88 114 if(this->vSpeed.x<-5.0) this->vSpeed.x=-5;
maxint 2:74bc9b16fb88 115
maxint 2:74bc9b16fb88 116 if(abs(vSpeed.x)>abs(vSpeed.y))
maxint 2:74bc9b16fb88 117 vSpeed.x=vSpeed.x/abs(vSpeed.x) * abs(vSpeed.y);
maxint 2:74bc9b16fb88 118
maxint 2:74bc9b16fb88 119 /*
maxint 2:74bc9b16fb88 120 if(this->vSpeed.y>0 && this->vSpeed.y<1.0) this->vSpeed.y=1;
maxint 2:74bc9b16fb88 121 if(this->vSpeed.x>0 && this->vSpeed.x<1.0) this->vSpeed.x=1;
maxint 2:74bc9b16fb88 122 if(this->vSpeed.y<0 && this->vSpeed.y>-1.0) this->vSpeed.y=-1;
maxint 2:74bc9b16fb88 123 if(this->vSpeed.x<0 && this->vSpeed.x>-1.0) this->vSpeed.x=-1;
maxint 2:74bc9b16fb88 124 */
maxint 0:3d0db4e183ee 125 }
maxint 0:3d0db4e183ee 126
maxint 0:3d0db4e183ee 127
maxint 0:3d0db4e183ee 128
maxint 0:3d0db4e183ee 129 void Ball::clear()
maxint 0:3d0db4e183ee 130 {
maxint 0:3d0db4e183ee 131 Point p=pos.getCur();
maxint 0:3d0db4e183ee 132 this->pDisp->fillCircle(p.getX(),p.getY(), this->nRadius, Color565::Black, Color565::Black);
maxint 0:3d0db4e183ee 133 }
maxint 0:3d0db4e183ee 134
maxint 0:3d0db4e183ee 135 void Ball::clearPrev()
maxint 0:3d0db4e183ee 136 {
maxint 0:3d0db4e183ee 137 Point p=pos.getPrev();
maxint 0:3d0db4e183ee 138 this->pDisp->fillCircle(p.getX(),p.getY(), this->nRadius, Color565::Black, Color565::Black);
maxint 0:3d0db4e183ee 139 }
maxint 0:3d0db4e183ee 140
maxint 0:3d0db4e183ee 141
maxint 0:3d0db4e183ee 142 void Ball::draw()
maxint 0:3d0db4e183ee 143 { // render the object on the screen, based on its current position
maxint 0:3d0db4e183ee 144 Point p=pos.getCur();
maxint 0:3d0db4e183ee 145 if(this->nRadius>3)
maxint 0:3d0db4e183ee 146 {
maxint 0:3d0db4e183ee 147 this->pDisp->fillCircle(p.getX(), p.getY(), this->nRadius, this->uColorLow, this->uColorLow);
maxint 0:3d0db4e183ee 148 this->pDisp->fillCircle(p.getX()-this->nRadius/3, p.getY()-this->nRadius/3, this->nRadius/2, this->uColorMid, this->uColorMid);
maxint 0:3d0db4e183ee 149 this->pDisp->setPixel(p.getX()-this->nRadius/2, p.getY()-this->nRadius/2, this->uColorHigh);
maxint 0:3d0db4e183ee 150 }
maxint 0:3d0db4e183ee 151 else
maxint 0:3d0db4e183ee 152 this->pDisp->fillCircle(p.getX(), p.getY(), this->nRadius, this->uColorMid, this->uColorMid);
maxint 0:3d0db4e183ee 153 }
maxint 0:3d0db4e183ee 154
maxint 0:3d0db4e183ee 155 void Ball::redraw()
maxint 0:3d0db4e183ee 156 { // redraw the ball if its position has changed
maxint 0:3d0db4e183ee 157 if(pos.hasChanged())
maxint 0:3d0db4e183ee 158 {
maxint 0:3d0db4e183ee 159 clearPrev();
maxint 0:3d0db4e183ee 160 draw();
maxint 0:3d0db4e183ee 161 }
maxint 0:3d0db4e183ee 162 }