12: BLITTER OBJECTS (BOBS) 155 ---------------------------- While hardware sprites are certainly powerful, they do suffer from a couple of annoying restrictions. The solution is to make use of the Amiga's infamous Blitter chip. This is capable of copying images to the screen at rates approaching a million pixels per second! With the help of the blitter it's possible to create what are known as bobs. Bobs, like sprites, can be moved around completely independently of the screen without destorying any existing graphics. But unlike sprites, bobs are sroted as part of the current screen, so you can create them in any graphics mode you wish. This allows you to generate bobs with up to 64 colours. Furthermore the only limit to the number of bobs you can display is dictated by the available memory. Bobs are slightly slower than sprites and they consume considerably more memory. Therefore there's a trade-off between the speed of sprites, and the flexibility of bobs. Fortunately there's nothing stopping you from using both bobs and sprites in the same program. BOB (draw a bob on the current screen) BOB n,x,y,i The BOB command creates bob n at coordinates x,y using the image # i. n is the identification number of the bob. Permissible values normally range from 0 to 63, but the number of bobs may be increased using an option from the AMOS configuration program. Providing you've enough memory, you can set this limit to any number you wish. x and y specify the position of the bob using standard screen coordinates. These coordinates are not the same as the hardware coordinates used by the equivalent SPRITE command. Like sprites, each bob is controlled through a *hot spot*. This may be changed at any time with the HOT SPOT command. i refers to an image which is to be assigned to the bob from the sprite bank. The format of this image is identical to that used by the sprites, so you can use the same images for either sprites or bobs. After you've created a bob, you can independently change either its position or its appearance by omitting one or more parameters from this instruction. Any of the numbers x,y or "image" may be left out, with the missing parameters retaining their original values. This is particularly useful if you are animating your bob with AMAL, as it allows you to move your object anywhere you like, without disturbing your existing animation sequence. However you must always include the commas in their original order. Example: Load "AMOS_DATA:Sprites/Octopus.abk" Flash Off : Get Sprite Palette Channel 1 To Bob 1 Bob 1,0,100,1 Amal 1,"Anim 0,(1,4)(2,4)(3,4)(4,4)" 156 Amal On For X=1 To 320 Bob 1,X,, Wait Vbl Next x Whenever a bob is moved, the area underneath is replaced in its original position, producing an identical effect to the equivalent SPRITE command. Unlike STOS on the ST, each object is allocated its own individual storage area. This reduces the amount of memory used by bobs, and improves the overall performance dramatically. Due to the Blitter, of course, therse's no real comparison between STOS sprites and AMOS bobs. Although the BOB command works fine for small number of bobs, there's an annoying flicker when you try to use more than three or four objects on the screen at once. This happens because the bobs are updated at the same time as the screen. You can therefore see the bobs while they are being drawn which results in an unpleasant shimmering effect. One alternative for improving the quality of your animations is to just limit your bobs to the bottom quarter of the screen. Since bobs are redrawn extremely quickly, the updates can often be completed before the lower part of the screen has been displayed. This provides you with acceptably smooth movements while consuming very little memory, so it's a useful trick if you're running short of space. See EXAMPLE 12.1 Obviously this cannot be seen as a serious solution to such a glaring problem. So before you throw away your copy of AMOS Basic in disgust, you'll be relieved to hear that there's a simple way of eliminating this flicker completely, even when you're using dozens of bobs anywhere on the screen: DOUBLE BUFFER (create a double screen buffer) DOUBLE BUFFER Creates a second invisible copy of the current screen. All graphics operations, including bob movements, are now performed directly in this *logical screen*, without disturbing your TV picture in the slightest. Once the image has been redrawn, the logical screen is displayed, and the original *physical* screen becomes the new logical screen. The entire process now cycles continuously, producing a rock solid display even when you're moving hundreds of bobs around the screen at once. The entire procedure is performed automatically by AMOS Basic, so after you've executed this instruction you can forget about it completely. Note that since the hardware sprites are always displayed using the current physical screen, this system will have absolutely no effect on any existing sprite animations. Double buffering works equally well in all of the AMIGA's graphics modes. It can even be used in conjuction with dual playfields. But be warned: Double buffering doubles the amount of memory used by your screens. If you attempt to double buffer too many screens, you'll quickly run out of memory. See EXAMPLE 12.2 In practice, double buffering is an incredibly useful technique, which can be readily exploited for most types of games. It has seen service in the vast majority of commercial games, including Starglider - that's why it's such an integral part of AMOS Basic. A detailed explanation of this process can be found in the SCREENS chapter. ALso see the SCREEN SWAP and AUTOBACK commands. SET BOB (set drawing mode of bob) 157 SET BOB n,back,planes,minterms The SET BOB command changes the drawing mode used to display a bob on the screen. n is the number of the bob you wish to affect. "back" chooses the way the background underneath your bob will be redrawn. There are three possibilities: - A value of 0 indicates that the area underneath your bob should be saved in memory. The old image data is automatically replaced when the bob is moved, resulting a smooth movement effect. - if the "back" parameter is positive then the original background will be discarded altogether, and the area behind the bob will be filled with colour "back"-1. This is ideal for moving bobs over a solid block of colour such as a clear blue sky, as it's much faster than the standard drawing system. - Turn of the redrawing process completely by loading "back" with a negative value such as -1. You can now deactivate the automatic updating process using BOB UPDATE, and manually move your bobs with a call to BOB DRAW. This allows you to regenerate the screen background using your own customised drawing routines. "planes" is a bit map which tells AMOS which screen planes your bob will be drawn in. As you may know, the Amiga's screen is divided up into a number of separate bit-planes. Each plane sets a single bit in the final colour which is displayed on the screen. The first plane is represnted by bit one, the second by bit two and so on. Normally the bob is drawn in all the bit-planes in the current screen mode. This corresponds to a bitpattern of %111111. By changing some of these bits to zero, you can omit selected colours from your bobs when they are drawn. This can be used to generate a number of intriguing screen effects. "minterms" selects the blitter mode used to draw your bobs on the screen. A full description of the available modes can be found in the section on SCREEN COPY. "minterm" is usually set to one of two values: %11100010 If the bob is used with a mask %11001010 if NO MASK has been set Feel free to experiment with the various combinations. There's no danger of crashing your Amiga if you make a mistake. Advanced Amiga users find the following information useful. Blitter source Purpose 158 -------------- ------------------ A Blitter mask B Blitter object C Destination screen Note that you are recommended to use SET BOB *before* displaying your bobs on the screen. If you don't, the Amiga won't crahsh, and you won't get an error message, but your screen display may be corrputed. NO MASK (remove blitter mask) NO MASK [n] As a default, a blitter mask is automatically created for every bob you display on the screen. This mask is combined with the screen background to make colour zero transparent. It's also used by the various collision detection commands. The NO MASK command removes this mask, and forces the entire image to be drawn on the screen. Any parts of the image in colour zero will now be displayed directly over the existing background. n is the image number whose mask is to be removed. This mask should never be erased if the image is active on the screen, otherwise the sasociated bob will be corrupted. If you must remove the mask in this way, it's important to deactivate the relevant bobs with BOB OFF first. Here's an example: Centre "Click mouse button to remove mask" Double buffer : Load "AMOS_DATA:Sprites/Octopus.abk" Get Sprite Palette Do Bob 1,X Screen(X Mouse),Y Screen(Y Mouse),1 If Mouse Click Then Bob Off : No Mask 1 Loop See MAKE MASK AUTOBACK (set automatic screen copying mode) AUTOBACK n When you are using a double bufferend screen, it's essential to synchronize your drawing operations with the movements of your blitter objects. Remember that each double buffered screen consists of two separate displays. There's one screen for the current picture, and another for the image whilst it's being constructed. If the background underneath a bob changes while it's being redrawn, the contents of these screens will be different, and you'll get an intense and annoying flickering efect. The unique AMOS AUTOBACK system provides you with a perfect solution to this problem. It allows you to generate your graphics in any one of three graphics modes, depending on the precise requirements of your program. Just for a change, we'll list tese options in reverse order. AUTOBACK 2 (automatic mode - default) 159 In this mode, all drawing operations are automatically combined with the bob updates. So anything you draw on the screen will be displayed directly underneath your bobs, as if by magic. The principles behing this system can be demonstrated by the following code: Bob Clear : Rem Draw on first screen ... Remove Bobs Plot 150,100 : Rem This can be anything you wish Bob Draw : Rem Redraw bobs Screen Swap : Rem Next Screen Wait Vbl Bob Clear Plot 150,100 : Rem Perform your operation a second time Bob Draw Screen Swap : Rem Get back to first screen Wait Vbl As you can see, all screen updates are performed exactly twice. There's one operation for both the logical and the physical screen. See EXAMPLE 12.3 for a demonstration. One obvious side effect, is that your graphics now take twice as long to be drawn. Furthermore, the program will be halted by at least 2 vertical blanks, every time you output something to the screen. This may cause annoying delays in the execution of critical activities such as collision detection. AUTOBACK 1 (half-automatic mode) Performs each graphical operation in both the physical and logical screens. Absolutely no account is taken of your bobs, so you should only use this system for drawing outside the current playing area. Unlike the standard mode, there's no need to halt your program until the next vertical blank. Mode 1 is therefore ideal for objects such as control panels or hi-score tables, which need to be updated continually during the game. AUTOBACK 0 (manual mode) Stops the AUTOBACK system in it's tracks. All graphics are now output straight to the logical screen at the maximum possible speed. You should use this option if you need to repeatedly redraw large sections of your background screen during the course of a game. This will allow you to safely perform your collision detection routines at regural intervals, without destroying the overall quality of the animation effects. Here's a typical program loop for you to examine. Bob Update Off Repeat Screen Swap Wait Vbl Bob Clear Rem Now redraw any of your gfxs which have changed 160 Rem Perform your game routines (Collision detection etc...) Bob draw Until WIN Note that this procedure will ONLY work if there's a smooth progression from screen to screen. It's entirely up to you to keep the contents of physical and logical screen in step with each other. An example of this technique can be found in EXAMPLE 12.4 Supposing for instance, you wanted to display a bob over a series of random blocks. You might try to use a routine like: Load "AMOS_DATA:Sprites/Sprites.abk" : Flash Off Get Sprite Palette : Double Buffer : Cls 0 : Autoback 0 Update Off : Bob 1,160,100,1 Do Bob Clear X=Rnd(320)+1 : Y=Rnd(200)+1 : W=Rnd(80)+1 H=Rnd(50)+1 : I=Rnd(15) Ink I : Bar X,Y To X+W,Y+H Rem Bob Draw Screen swap : Wait Vbl Loop But since there's no relationship between the physical and logical screens, the display will now flick continuously from screen to screen. To overcome this problem, you'll need to mimic the original AUTOBACK system. Replace the lines in the previous example between the lines Do and Loop as follows: Rem Update first screen Screen Swap : Wait Vbl Bob Clear X=Rnd(320)+1 : Y=Rnd(200)+1 : W=Rnd(80)+1 H=Rnd(50)+1 : I=Rnd(15) Ink I : Bar X,Y To X+W,Y+H Bob Draw Rem Update second screen Screen Swap : Wait Vbl Bob Clear Ink I : Bar X,Y To X+W,Y+H Bob Draw The two screens are now updated with exactly the same information, and 161 the display remains as steady as a rock, even though there's a great deal of activity going on in the background. Autoback can be safely used at any point in your program. So it's perfectly possible to use separate drawing methods for the different parts of your screen. It's also totally compatible with all graphics operations including Blocks, Icons, and Windowing. Bob Control commands ==================== BOB UPDATE (control bob movements BOB UPDATE [ON/OFF] Normally all bobs are updated once every 50th of a second using a built-int interrupt routine. Alhouth this is convenient for most programs, there are some applications which require much finer control over the redrawing process. BOB UPDATE OFF turns off the bob updates and deactivates all automatic screen switching operations if they've been selected. You may now redraw your bobs at the most appropriate point in your program using the BOB UPDATE command. This is ideal when you are animating a large number of objects as it enables you to move your bobs into position before drawing them on the screen. Inevitably this results in far smoother movements in your game. One word of warning: The bob updates will only occur at the NEXT vertical blank. Also note that BOB UPDATE will always redraw the bobs on the current logical screen, so if you forget to use the SCREEN SWAP command, nothing will apparently happen. BOB CLEAR (remove all the bobs from the screen) BOB CLEAR Removes all active bobs from the screen, and redraws the background regions underneath. It's inteded for use with BOB DRAW to provide an alternative to the standard BOB UPDATE command BOB DRAW (redraw bobs) BOB DRAW Whenever the bobs are redrawn on the screen, the following steps are automatically performed: 1. All active bobs are removed from the LOGICAL screen and the background regions are replaced. This step is performed by BOB CLEAR. 2. A list is made of all bobs which have moved since the previous update. 3. The background regions under the new screen coordinates are saved in memory. 4. All active bobs are redrawn at their new positions on the logical 162 screen 5. If the DOUBLE BUFFER feature has been activated, the physical and logical screens are now swapped The BOB DRAW command performs steps 2 to 4 of this process directly. Supposing you wished to create a screen scrolling arcade game. In this situation, it would be absolutely vital for your scrolling operations to be perfectly synchronized with movement effects. If the aliens were to move while the scrolling was taking place, their background areas would be redrawn at the wrong place. This would totally corrupt your display, and would result in a hopeless jumble on the screen. Load EXAMPLE 12.5 for a demonstration of this process. =X BOB (get X coordinate of bob) x1=X BOB(n) Returns the current X coordinate of bob number n. This coordinate is measured relative to the current screen. See also Y SPRITE, X MOUSE and Y MOUSE. =Y BOB (get Y coordinate of bob) y1=Y BOB(n) Y BOB complements the X BOB command by returning the Y coordinate of bob number n. This value will be returned using normal screen coordinates. =I BOB (return current image of bob) Image=U BOB(n) This function returns the current image number being used by bob n. A value of zero will be reported if the bob isn't displayed. LIMIT BOB (limit a bob to a rectangular region of the screen) LIMIT BOB [n,] x1,y1 TO x2,y2 This command restricts the visibility of your bobs to a rectangular screen area enclosed by the coordinates x1,y1 to x2,y2. The x coordinates are rounded up to the nearest 16-pixel boundary. Note that the width of this region must always be greater than the width of your bobs, otherwise you'll get an "illegal function call" error. If it's included, n specifies the number of a single bob which is to be affected by this instruction, otherwise *all* bobs will be restricted. You can restore the visibility limit to the entire entire screen by typing: LIMIT BOB GET BOB (load a section of the screen 163 into the sprite bank) GET BOB [s,] i,x1,y1 TO x2,y2 This instruction is identical to the GET SPRITE command. It grabs an image into the sprite bank from the current screen. x1,y1 to x2,y2 are the coordinates of the top and bottom corners of the rectangular area to be grabbed. i specifies the image number which is to be loaded with this area. s selects an optional screen number from which the image is to be taken. See GET SPRITE for more details. See also EXAMPLE 12.6. PUT BOB (fix a xopy of a bob onto the screen) PUT BOB n This is the exact opposite of the previous GET BOB command. The action of PUT BOB is to place a copy of bob number n at its present position on the screen. It works by preventing the background underneath the bob from being redrawn during the next vertical blank period. In order to synchronise the bob updates with the screen display, you should always follow this command with a WAIT VBL instruction. Note that after this instruction has been performed, the original bob may be moved or animated with no ill efects. PASTE BOB (draw an image from the sprite bank on the screen) PASTE BOB x,y,i The PASTE BOB command draws a copy of image number i at *screen* coordinates x,y. Unlike PUT BOB this image is drawn on the screen immediately, and all the normal clipping rules are obeyed. See PASTE ICON. BOB OFF (remove a bob from the display) BOB OFF [n] Occasinoally, you may wish to remove certain bobs from the screen altogether. The BOB OFF command erases bob number n from the screen and terminates any associated animations. If n is omitted, all bobs will be 164 removed by this instruction.