January 01, 2018

Bouncing Balls : Turbo C++


   The following program display balls that keeps bouncing around on the screen. It defaults to drawing forty balls. It has been developed using the Turbo C++ 3.0 IDE. It uses BGI Graphics to render all the graphics. 






The screenshots below describe its functionality :


Bouncing Balls - Output

Bouncing Balls - Output

Bouncing Balls - Output

Bouncing Balls - Output


Source Code




       /* Header Files */

       #include <fstream.h>
       #include <conio.h>
       #include <string.h>
       #include <iostream.h>
       #include <stdlib.h>
       #include <dos.h>
       #include <math.h>


       typedef unsigned char BYTE;
       typedef unsigned int WORD;
       typedef unsigned long DWORD;


       #define VIDEO_SEGMENT       0xA000
       #define PALETTE_INDEX       0x03c8
       #define PALETTE_DATA        0x03c9
       #define SCREEN_WIDTH        320      
       #define SCREEN_HEIGHT       200      
       #define NUM_COLORS          256      

       #define BITMAP_WIDTH        32
       #define BITMAP_HEIGHT       25
      

       #define round(x) (x >= (ceil(x)+ floor(x))/2 ? ceil(x) : floor(x))
       #define PI 3.141592654
       #define SPEED 10
      
       enum bool{false, true};
      
       typedef struct tagBITMAP              /* the structure for a bitmap. */
       {
         WORD width;
         WORD height;
         BYTE Palette_Data[256*3];
         BYTE *data;
       } BITMAP;
      
       typedef struct tagOBJECT             
       {
         int x,y;
         int dx,dy;
         BYTE width,height;
       } OBJECT;
      
      
       void SetGraphicsMode()
       {
          _AH = 0;
          _AL = 0x13;
          geninterrupt(0x10);
       }


       void SetTextMode()
       {

         _AH = 0;
         _AL = 0x03;
         geninterrupt(0x10);

       }

       void Putpixel(int x, int y, BYTE color)
       {
          pokeb(VIDEO_SEGMENT,(y*SCREEN_WIDTH)+x,color);
       }

       bool ImgType(char *bmpfile)
       {
              WORD type;
              fstream file;
              file.open(bmpfile,ios::in|ios::binary);
              file.read((char *) &type,sizeof(WORD));
              file.close();
              if(type == 19778)
              return true;
              else
              return false;
       }

       void LoadBitmap(char *bmpfile, BITMAP *b)
       {
              fstream bitmap_file;

              /*****************************************************/

              DWORD index;
              BYTE rgbquad[4];
              WORD num_colors;
             

              /*****************************************************/

              /* Open bitmap file. */

              bitmap_file.open(bmpfile,ios::in|ios::binary);

              if(!bitmap_file)
              {
                     cout<<"Error opening file "<<bmpfile;
                     exit(1);
              }

              /* check to see if it is a valid bitmap file */

              if(ImgType(bmpfile) == false)
              {
                     bitmap_file.close();
                     cout<<bmpfile<<" is not a bitmap file.";
                     exit(1);
              }

              /* read in the width and height of the image, and the
                     number of colors used; ignore the rest */

              bitmap_file.seekg(18,ios::beg);
              bitmap_file.read((BYTE *) &b->width,sizeof(WORD));
              bitmap_file.seekg(2,ios::cur);
              bitmap_file.read((BYTE *) &b->height,sizeof(WORD));
              bitmap_file.seekg(22,ios::cur);
              bitmap_file.read((BYTE *) &num_colors,sizeof(WORD));
              bitmap_file.seekg(6,ios::cur);

              /*---------------------------------------------------------*/
             
             
              /* assume we are working with an 8-bit file */
                           if (num_colors==0) num_colors=256;
                          
              /* try to allocate memory */

                if ((b->data = (BYTE *) malloc((WORD)(b->width*b->height))) == NULL)
                {
                           bitmap_file.close();
                           cout<<"Error allocating memory for file "<<bmpfile;
                           exit(1);
                }


              /* Read the palette information. */

              for(index = 0;index < num_colors;index++)
              {
                     bitmap_file.read((BYTE *) &rgbquad,4);

                     b->Palette_Data[(int)index*3+2] = rgbquad[0]>>2;
                     b->Palette_Data[(int)index*3+1] = rgbquad[1]>>2;
                     b->Palette_Data[(int)index*3+0] = rgbquad[2]>>2;
              }



              /* read the bitmap */

              for(int i=(b->height-1)*b->width;i>=0;i-=b->width)
              {
                     for(int j=0;j<b->width;j++)
                     {
                           bitmap_file.read((BYTE *) &b->data[(int)(i+j)],1);

                     }

              }




              bitmap_file.close();
       }

       void setPalette(BYTE *palette)
       {
                int i;

                outp(PALETTE_INDEX,0);              /* tell the VGA that palette data
                                                                                   is coming. */
                for(i=0;i<256*3;i++)
                     outp(PALETTE_DATA,palette[i]);    /* write the data */
       }
void drawBitmap(int Left, int Top,int OffsetX, int OffsetY,int imgWidth,
                  int imgHeight, int trans, int tcolor, BITMAP *b)
{
              BYTE ch;
              int off_x=OffsetX,off_y=OffsetY;
              int bitmap_offset=(off_y*b->width*imgHeight)+(off_x*imgWidth);
              int offset=bitmap_offset;



              for(int i=0;i<imgHeight;i++)
              {
                     for(int j=0;j<imgWidth;j++)
                     {

                           ch=b->data[offset+j];


                           if(trans==1)
                           {
                                  if((int)ch!=tcolor)
                                         Putpixel((Left+j)>>1,Top+i>>1,ch);
                           }
                           else
                           Putpixel((Left+j)>>1,Top+i>>1,ch);

                     }
                     offset+=b->width;
              }



      }


       void ClearScreen()
       {
              for(int i=0;i<200;i++)
                     for(int j=0;j<320;j++)
                           Putpixel(j,i,0);
       }


       void main()
       {
              int num_objects=40;
              int whichball=0;
              int ball_x=0,ball_y=0;

              OBJECT *object;
              BITMAP bmp;

              LoadBitmap("balls.bmp",&bmp);

              /* allocate memory for objects */
                if ((object = (OBJECT *) malloc(sizeof(OBJECT)*num_objects)) == NULL)
                {
                     cout<<"Not enough memory for objects.";
                     exit(1);
                }


              for(int i=0;i<num_objects;i++)
              {
                     object[i].width   = BITMAP_WIDTH;
                     object[i].height  = BITMAP_HEIGHT;
                     object[i].x       = rand() % (SCREEN_WIDTH - BITMAP_WIDTH );
                     object[i].y       = rand() % (SCREEN_HEIGHT- BITMAP_HEIGHT);
                     object[i].dx      = (rand()%5) - 2;
                     object[i].dy      = (rand()%5) - 2;
              }

              SetGraphicsMode();
              setPalette(bmp.Palette_Data);

              while(!kbhit())
              {

                           for(i=0;i<num_objects;i++)
                           { drawBitmap(object[i].x, object[i].y, ball_x,  ball_y, BITMAP_WIDTH, BITMAP_HEIGHT, 1, 0, &bmp);
                             /* check to see if the object is within boundries */
                             if (object[i].x + object[i].dx < 0 ||
                                    object[i].x + object[i].dx > 610-object[i].width-1)
                                         object[i].dx=-object[i].dx;
                             if (object[i].y + object[i].dy < 0 ||
                                    object[i].y + object[i].dy > 380-object[i].height-1)
                                         object[i].dy=-object[i].dy;
                             /* move the object */
                             object[i].x+=object[i].dx;
                             object[i].y+=object[i].dy;
                           }
                           delay(SPEED);
                           ClearScreen();

                           whichball++;
                           ball_x=whichball;
                           if(whichball>=10&&whichball<=19)
                           {
                                  ball_x=whichball-10;
                                  ball_y=1;
                           }
                           if(whichball>=20&&whichball<=23)
                           {
                                  ball_x=whichball-20;
                                  ball_y=2;
                           }
                           if(whichball>23)
                           {
                                  ball_x=0;
                                  ball_y=0;
                                  whichball=0;
                           }
              }


              free(bmp.data);
              free(object);

          getch();
          SetTextMode();

       }







Downloads :


 
Click here to view and download the source code of Bouncing Balls (41 KB). 

Click here to download the executable file of Bouncing Balls (39 KB) (Please note that it is a 16-bit executable and will not run on 64-bit systems).

Click here to download balls.bmp file.






No comments:

Post a Comment