POOL!

Travis Bartholomew
Nick Matteo
Jon Ward
Anatoly Zlotnik



Description     

        It's time to become a man and test your pool talents.  This program is an immersive, hyper-realistic, billiards simulation.  It uses the latest digital graphics technology to realistically create a game of 8 ball on your desktop.  Beat up on a friend, or play against the AI.  The AI even has ten difficulty settings, controlling how intelligently it plays.  It's time to step up to the table and floss your mad 8-ballin' skills.

Instructions

        After you download the program, simply run the installer to set up the program on your computer.  Then run the pool program to get started.



        When you're ready to rack 'em up, start up the program and choose how you want to play.  You can select either one player or two players.  If you choose the "1 player" option, you will be playing against an AI.  If you're playing with an AI, you'll be asked to select the difficulty.  If you select one of the first few difficulty settings, the AI will simply shoot at it's closest ball with a random velocity, with a random chance of missing.  However, if you select one of the higher settings, the AI will actually try to play.  The AI will attempt to find the ball with the best chance of going in.  Good luck trying to beat it.  MWAHAHAHA!



        After the balls have been racked, the play is simple.  Move your mouse around the screen to line up your shot.  The force of your shot depends on how far away from the cue ball you click.  



        When you're ready to go, click the mouse and watch the action.  The current player's turn is displayed in the upper left hand corner, along with the word "stripes" or "solids", denoting which balls they are shooting for.

                   

        Play is standard 8-ball rules.  If you're not familiar with the rules of 8 ball, just click on the "help" tab in the menu to get the rules.  Try to get all of your balls into the pockets, then go for the 8-ball.  If you scratch the 8 ball, it's game over.  If your opponent scratches the cue ball, click on the screen to place the ball.  It's "ball in hand" rules, so you can place it anywhere and shoot in any direction.



        Have fun, and good luck!

Design issues

Windowing (Jon):
        My job was to make the windows front end to give our program a "professional" look. I looked at different libraries on the internet, but I didn't really find one that looked good enough. I was looking around on Microsoft's website and found some great documentation on the Windows API. I had fiddled around with the MFC before in Visual Studio, but had never been able to make a functional program. The Platform SDK helped immensely, but it still wasn't easy. Windows programming is totally different than any other programming I have ever seen. Windows uses some strange data types and the format of the program is new. Instead of being linear like console applications, Windows applications have to be driven by the user. The user can do a multitude of things and the program has to be programmed for that. It took my 6 hours just to figure out how the sample application was displaying a dialog box! My first program had a menu with a random message option. The user clicks on the item and one of eight random messages appear. I liked it so much that I included it into the final project.

Graphics and Integration (Nick):
        The graphics display itself went fairly smoothly.  I used placeholder graphics until Ward made the polished final ones, and beyond figuring out how CDX works (which I did by changing everything in their sample Breakout game), no big deal.  More of my time was spent on gameplay...writing win conditions, allowing for placement of the cue ball after scratching, figuring out who's turn it is.  Playtesters would bring up new rules every time they played, and I'd have to write more conditions, which led to less and less readable code.  They'd also request features like the tracer or placing the cue ball on break, which are options now.  I also continually added more feedback, in the way of saying who's supposed to be shooting, whether  they were solids or stripes, then showing the ai's side, and showing the player's side while they were placing the cue ball...the more of that the easier on the player.  Writing the intelligent AI took a huge amount of time, but the vast majority of coding was done in a very short time thanks to the excellent algorithm developed by Travis.  The only problem was that it didn't work perfectly; I had to find corrections on various aspects, each of which took a lot of investigation, and finally one morning I hit upon a new method of finding the cue ball's target that worked exactly right.  Managing everyone's code was also a pain.  Every time someone wrote new code they'd send it to me and I'd integrate it.  Since we didn't use any project management system this could take a while, and some physics functionality may have been lost at some point.

Physics (Anatoly):
        My part in the project was to design the physics engine.  The requirements were (1) to take a set of positions and velocities and output positions and velocities after a set amount of time, and (2) to simulate the laws of physics as closely as possible.  The major obstacle was the absence of a graphics engine while designing the physics.  It was impossible to see the effects of what was done except by looking at numbers scrolling across a MSDOS console.    I wrote a sprawling ball class and an even bigger table class that contained all the functions I needed to write the actual collision check and algorithm.    Once this was done the engine functions were relatively easy to write.  However, I still did not understand what the output was because I could not see it.
        I expected failure as I walked to a group meeting to integrate the various parts.    The results were as I suspected; the balls just began to accelerate until they were a blur all over the playing area.  Purely by accident I decided to adjust the time step parameter, and the balls began to behave in a way resembling actual collisions!!    After several days of debugging, I realized the problem was in the C++ arctan function.  It had no checks to guarantee a valid output if the x or y term was zero.  I implemented an adjusted arctan function with checks which eliminated problems such as vortexint, ghosting, "gravity", and other anomalies.
        The basic structure of the algorithm is to go through the balls one by one, check for a collision with every other ball, and if there is a collision to adjust the velocity of the ball by analyzing the relative velocity and the angle between the relative velocity and the relative position of the balls.    Initially of a ball was altered after all checks on it were added up.  At this time a collision would only affect the ball of higher number!    This was fixed by waiting until all the checks were done to
alter the velocities of the balls, and only then the actual midpoint algorithm was implemented.
        The midpoint algorithm actually comprises the simplest part of the program; it is only 4 lines.  It is a slight modification of Euler's algorithm that yields much greater accuracy.  Although the error is 2nd order like in the Euler algorithm, it is still much more accurate and yields life-like drag on the balls from the table.  I had originally planned to use the Verlet algorithm, which has a 4th order error, but it requires the data from steps [n] and [n - 1] to obtain the data for step [n + 1], unlike the midpoint algorithm that uses only the [n] step data.
   
    The Midpoint Algorithm:

    V[n + 1] = V[n] + t*A
    X[n + 1] = X[n] + t*(V[n] + V[n + 1])/2

    t = 1/tau     where tau is the frequency of iterations, and t is the time step
    A = -d*V    A is the acceleration where d is the drag coefficient

    The algorithm used thus appears:

    V[n + 1] = V[n] - (1/tau)*d*V[n]
    X[n + 1] = X[n] + (1/tau)*(V[n] + V[n + 1])/2

        The major design problem was, however, the arctan function.  It is not clear why it malfunctioned the way it did, even after checks for zero terms were implemented.  I believe it may be due to the way that the CDX graphics engine orients its coordinate system.

AI and website (Travis):
        Developing the algorithm for the Artificial Intelligence took quite some time, but the time invested was worth it.  Since I had everything laid out before I began any coding,  all I had to do was employ the relevant functions from the ball class.  The less intelligent AI settings simply have the AI shooting at its closest ball with a random velocity.  However, the more intelligent AI is different.  It attempts to find its ball with the most direct route to a corner pocket.  It compares the distances from the cue ball to the target ball, the target ball to a corner pocket, and the cue ball to the same pocket.  It then finds the angle the cue ball needs to shoot at and attempts to offset that angle so the ball is hit into the pocket.  The intelligent AI looked good in theory, but it was much more difficult in reality.  My thanks to Nick for integrating the AI seemlessly into the rest of the program.  As for the website, it was a simple matter of using Mozilla's slick composer to drag and drop images and add the text in directly, without any messy HTML.  It was a little difficult having to do this on my laptop, without being connected to the internet, thanks to the spectactular crashing on my PC.  Nevertheless, I survived and perservered and here I am, finished with the final project.

Source code / Program download

Thanks to:
CDX graphics library
Tutorials by Ioannis Karagiorgos
Platform SDK
The sample breakout game included with CDX

Download the game!
If you need the Windows Installer setup files get this updater for Windows 95, 98 or ME or this updater for Windows NT or 2000.