Advertisement
Guest User

softbody

a guest
Mar 18th, 2015
400
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 5.71 KB | None | 0 0
  1. #include <iostream>
  2. #include <math.h>
  3. #include <SDL.h>
  4. #include <vector>
  5. const int scr_w=500;
  6. const int scr_h=500;
  7. using namespace std;
  8. struct Vector
  9. {
  10.     float x;
  11.     float y;
  12. };
  13. float magnitude(Vector a)
  14. {
  15.     float m=sqrt(a.x*a.x+a.y*a.y);
  16.     return m;
  17. }
  18. class Display
  19. {
  20.     public:
  21.         Display(string win_name,int w,int h)
  22.         {
  23.             win=SDL_CreateWindow(win_name.c_str(),SDL_WINDOWPOS_CENTERED,SDL_WINDOWPOS_CENTERED,w,h,SDL_WINDOW_SHOWN);
  24.             ren=SDL_CreateRenderer(win,-1,SDL_RENDERER_ACCELERATED);
  25.         }
  26.         ~Display()
  27.         {
  28.             SDL_DestroyTexture(tex);
  29.             SDL_DestroyRenderer(ren);
  30.             SDL_DestroyWindow(win);
  31.         }
  32.         void initTexture(string path)
  33.         {
  34.             SDL_Surface* surf=NULL;
  35.             surf=SDL_LoadBMP(path.c_str());
  36.             if(surf==NULL)
  37.             {
  38.                 cout<<"Error:\n"<<SDL_GetError();
  39.             }
  40.             tex=SDL_CreateTextureFromSurface(ren,surf);
  41.             texSize={surf->w,surf->h};
  42.             SDL_FreeSurface(surf);
  43.         }
  44.         void drawLine(SDL_Point a,SDL_Point b,SDL_Color c)
  45.         {
  46.             SDL_SetRenderDrawColor(ren,c.r,c.g,c.b,c.a);
  47.             SDL_RenderDrawLine(ren,a.x,a.y,b.x,b.y);
  48.         }
  49.         void renderTexture(int x,int y)
  50.         {
  51.             SDL_Rect paste={x-texSize.x/2,y-texSize.y/2,texSize.x,texSize.y};
  52.             SDL_RenderCopy(ren,tex,NULL,&paste);
  53.         }
  54.         void clearScreen(SDL_Color c)
  55.         {
  56.             SDL_SetRenderDrawColor(ren,c.r,c.g,c.b,c.a);
  57.             SDL_RenderFillRect(ren,NULL);
  58.         }
  59.         void updateScreen()
  60.         {
  61.             SDL_RenderPresent(ren);
  62.         }
  63.     private:
  64.         SDL_Window* win=NULL;
  65.         SDL_Renderer* ren=NULL;
  66.         SDL_Texture* tex=NULL;
  67.         SDL_Point texSize;
  68. };
  69. class Softbody
  70. {
  71.     public:
  72.         Softbody(float restitution,float spring_constant,float damping)
  73.         {
  74.             e=restitution;
  75.             k=spring_constant;
  76.             c=damping;
  77.         }
  78.         void appendPoint(int x, int y)
  79.         {
  80.             SDL_Point newVertex={x,y};
  81.             soft_body.push_back(newVertex);
  82.             Vector zero={0,0};
  83.             velocity.push_back(zero);
  84.         }
  85.         void acceleratePoints()
  86.         {
  87.             vector<SDL_Point> soft_body_copy=soft_body;
  88.             vector<Vector> velocity_copy=velocity;
  89.             for(int i=0;i<soft_body.size();++i)
  90.             {
  91.                 for(int j=0;j<soft_body.size();++j)
  92.                 {
  93.                     if(j==i-1||j==i+1||(j==soft_body.size()-1&&i==0)||(i==soft_body.size()-1&&j==0))
  94.                     {
  95.                         Vector d={(soft_body[j].x-soft_body[i].x)/100.0,(soft_body[j].y-soft_body[i].y)/100.0};
  96.                         float t=atan2(d.y,d.x);
  97.                         float disp=abs(magnitude(d))-natural_length/100.0;
  98.                         velocity_copy[i].x+=(k*disp*cos(t))/10000.0;
  99.                         velocity_copy[i].y+=(k*disp*sin(t))/10000.0;
  100.                         velocity_copy[i].x-=c*velocity_copy[i].x/100.0;
  101.                         velocity_copy[i].y-=c*velocity_copy[i].y/100.0;
  102.                         soft_body_copy[i].x+=velocity_copy[i].x;
  103.                         soft_body_copy[i].y+=velocity_copy[i].y;
  104.                     }
  105.                 }
  106.                 soft_body=soft_body_copy;
  107.                 velocity=velocity_copy;
  108.             }
  109.         }
  110.         void checkCollision()
  111.         {
  112.             for(int k=0;k<soft_body.size();++k)
  113.             {
  114.                 if(soft_body[k].x>=scr_w||soft_body[k].x<=0)
  115.                 {
  116.                     velocity[k].x*=e;
  117.                     soft_body[k].x=soft_body[k].x>scr_w/2?scr_w-1:1;
  118.                 }
  119.                 if(soft_body[k].y>=scr_h||soft_body[k].y<=0)
  120.                 {
  121.                     velocity[k].y*=e;
  122.                     soft_body[k].y=soft_body[k].y>scr_h/2?scr_h-1:1;
  123.                 }
  124.             }
  125.         }
  126.         void drawBody(Display& display,SDL_Color c)
  127.         {
  128.             for(int z=0;z<soft_body.size();++z)
  129.             {
  130.                 display.renderTexture(soft_body[z].x,soft_body[z].y);
  131.                 display.drawLine(soft_body[z],soft_body[(z+1)%soft_body.size()],c);
  132.             }
  133.         }
  134.     private:
  135.         vector<SDL_Point> soft_body;
  136.         vector<Vector> velocity;
  137.         float natural_length=50;
  138.         float e;
  139.         float k;
  140.         float c;
  141. };
  142. int main(int argc,char *argv[])
  143. {
  144.     Softbody body(.5,1000,20);
  145.     Display display("Soft Body Physics",scr_w,scr_h);
  146.     display.initTexture("img/point.bmp");
  147.     SDL_Color white={255,255,255,255};
  148.     SDL_Color red={255,0,0,255};
  149.     bool init=true,quit=false;
  150.     SDL_Event e;
  151.     while(!quit)
  152.     {
  153.         while(SDL_PollEvent(&e)!=0)
  154.         {
  155.             if(e.type==SDL_QUIT)
  156.             {
  157.                 quit=true;
  158.                 break;
  159.             }
  160.             else if(init)
  161.             {
  162.                 if(e.type==SDL_MOUSEMOTION||e.type==SDL_MOUSEBUTTONDOWN)
  163.                 {
  164.                     if(e.button.button==SDL_BUTTON_RIGHT)
  165.                         init=false;
  166.                     else if(e.button.button==SDL_BUTTON_LEFT)
  167.                     {
  168.                         int x,y;
  169.                         SDL_GetMouseState(&x,&y);
  170.                         body.appendPoint(x,y);
  171.                     }
  172.                 }
  173.             }
  174.         }
  175.         if(!init)
  176.         {
  177.             body.checkCollision();
  178.             body.acceleratePoints();
  179.         }
  180.         display.clearScreen(white);
  181.         body.drawBody(display,red);
  182.         display.updateScreen();
  183.         SDL_Delay(10);
  184.     }
  185.     return 0;
  186. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement