|  | 
 
 If you are new to Blitz, then in all probability you will have downloaded quite a few examples of code, and have probably seen either an image that has been rippled about on the screen, or a sine wave scroller. These are really easy effects to achieve, so here for you is a beginners guide to creating those sorts of effects. Before we start doing that however, lets start at the beginning. Say that you want to plot a circle - not very exciting I know, and doesn't initially appear to have anything to do with creating wavy graphics, but lets walk before we can run. To plot a circle, we'll take 360 degrees, and for every degree plot a pixel at a radius of, say, 50 pixels from the center of our circle. Then we use the following to plot the circle: 
x = radius * Sin (angle)
 As you probably know, Sin & Cos are trigonometry functions. That's right, the stuff you never paid attention to in math's class because why on earth would you ever need to know about it... The following piece of code would do - paste it in to Blitz and run it. 
 Easy, yeah? Notice the plot command adds 320 pixels to the x value to be plotted and 240 to the y value. This centers our circle on the screen. Now try changing one of the '50' values to '20' (or whatever you like). There you go - instant oval! So what's that got to do with wobbly wavy effects? Well instead of calculating both x & y, lets plot a line across the entire screen a pixel at a time: 
 Still not wavy, so lets apply what we've learnt from plotting the circle to just one of the values (the y value) in the Plot command. 
 This time round our loop is used to increment the x position of the pixel to plot, so the angle is assigned to a variable and incremented within the loop. When the value of angle reaches 360, we set it back to 0 so that we can start again from the beginning (0 degrees and 360 degrees are the same in case you haven't noticed yet). "Which means," says a voice at the back " 361 degrees will give us the same result as 1 degree, 362 the same as 2", etc and so on. Which also means that you don't really have to check and reset the angle to 0 degrees, and which also means you could get rid of the angle variable altogether and just use the value of x for the angle as well as for the pixel position on the screen! Confused? Then look at the following code, and then I'll tell you why we don't want to it this way. 
 Much better? Well, it is unless you want to pregenerate a sine table... 
 Imagine that we did most of the math's work before we started plotting pixels all over the place. That's got to be much faster hasn't it? Well, it is. By a long way. 
 This sets up a 1 dimensional array of 360 values (0 to 359), which gives us space to store 360 numbers, or in our case somewhere to precalculate and store a sine wave. The values created could of course then be used to offset either the 'x' or 'y' position (or even both) of the pixels we plot on the screen. 
 After we've generated the sine table, we use the 'angle' variable to work our way through the 'sinetable' array which only has 360 (0 to 359) entries. This means we need to reset 'angle' to 0 when it reaches 360 because if we don't our program will try to access the 361st element in an array that only has 360 elements. You'll notice that the above code generates exactly the same effect as before, but this time the values for plotting our sinewave have already been calculated, which amounts to a hugh speed increase for our program, even though this isn't visibly apparent in our small example. All the way through this tutorial, we have been using the plot command, which you will know unless you are really new to Blitz, is really slow. Lets optimize the rest of the code then. 
 Ok, so there are a few noticeable changes here. Firstly the precalculated array is only 256 elements in size instead of 360, and we calculate the angle to be stored approximately every 1.4 degrees instead of every 1-degree. What this does is let us get rid if the 'If angle =' check that occurs 640 times within the For-Next loop. This is done by limiting our 'angle' counter to one single byte (or 0 to 255), which is why the sinetable uses 256 elements. The 'And $ff' does this by masking off everything but the low byte of 'angle'. If you don't understand how, just trust me that it does. Now imagine that for some reason that you are plotting this sinewave every frame (at say 60 frames a second), and we've just got rid of 38400 'If...Then' checks for every second the program is running... Oh yeah, and because we're only plotting the wave in the middle of the screen, we add the offset to center it on the screen (the + 240) to the precalc at the beginning of the code. The last thing we've done is to get rid of 'Plot' and replaced it with 'WritePixelFast'. This requires that we use the LockBuffer / UnlockBuffer commands, and limits the drawing options you have while the buffer is locked. Check the online manual for more info on this, but the most important thing to remember is NOT to draw off screen when using 'WritePixelFast'... 
 To round all of this off, let's look at a "practical" use for all of this. Don't forget to change "pic.bmp" to a 640 x 480 image that you've put in the same directory as the following code. 
 Try changing the value added to 'angle' and 'startangle'. You can get a wide variety of effects from this very simple routine. Check out my bLiquid demo on the BlitzCoder showcase if you want some ideas! I hope this has been of help to someone, and if you find a neat effect, let me know. 
 For a printable copy of this article, please click HERE. 
 This site is Copyright© 2000-2004, BlitzCoder. All rights reserved.   |