********* Welcome to Project 64! The goal of Project 64 is to preserve Commodore 64 related documents in electronic text format that might otherwise cease to exist with the rapid advancement of computer technology and declining interest in 8- bit computers on the part of the general population. Extensive efforts were made to preserve the contents of the original document. However, certain portions, such as diagrams, program listings, and indexes may have been either altered or sacrificed due to the limitations of plain vanilla text. Diagrams may have been eliminated where ASCII-art was not feasible. Program listings may be missing display codes where substitutions were not possible. Tables of contents and indexes may have been changed from page number references to section number references. Please accept our apologies for these limitations, alterations, and possible omissions. Document names are limited to the 8.3 file convention of DOS. The first characters of the file name are an abbreviation of the original document name. The version number of the etext follows next. After that a letter may appear to indicate the particular source of the document. Finally, the document is given a .TXT extension. The author(s) of the original document and members of Project 64 make no representations about the accuracy or suitability of this material for any purpose. This etext is provided "as-is". Please refer to the warantee of the original document, if any, that may included in this etext. No other warantees, express or implied, are made to you as to the etext or any medium it may be on. Neither the author(s) nor the members of Project 64 will assume liability for damages either from the direct or indirect use of this etext or from the distribution of or modification to this etext. Therefore if you read this document or use the information herein you do so at your own risk. ********* The Project 64 etext of the ~Commodore 64 MicroComputer User Manual (2d ed)~, converted to etext by Frank Jeno Kontros . C64UG210.TXT, June 1997, etext #251# ********* Commodore 64 MicroComputer User Manual _____ / ___|___ | / |__/ c o m m o d o r e | \___|__\ C O M P U T E R \_____| COMMODORE 64 USER'S GUIDE Published by Commodore Business Machines, (UK) Ltd. Copyright (C) 1984 by Commodore Business Machines, (UK) Ltd. All rights reserved. This manual is copyrighted and contains proprietary information. No part of this publication may be reproduced, stored in a retrieval system, or transmitted in any form or by any means, electronic, mechanical, photocopying, recording, or otherwise, without the prior written permission of COMMODORE BUSINESS MACHINES, (UK) Ltd. TABLE OF CONTENTS INTRODUCTION 1. SETTING UP 1.1. Unpacking and Connecting the 64 1.2. Installation 1.3. Optional Connections 1.4. Operation 1.5. Troubleshooting Chart 1.6. Color Adjustment 1.7. Expanding Your System With Optional Peripherals 2. GETTING STARTED 2.1. Communicating with your 64: The Keyboard 2.2. Loading Programs 2.3. How to Format a New Disk 2.4. Saving Programs 2.5. Listing a Directory of Programs on a Disk 3. BEGINNING BASIC 3.1. Printing and Calculating 3.2. Mathematical Functions 3.3. Multiple Calculations on One Line 3.4. Execution Order in Calculations 3.5. Combining PRINT's Capabilities 4. WRITING SIMPLE PROGRAMS IN BASIC 4.1. Line Numbers 4.2. The GOTO Statement 4.2. Using the LIST Command 4.3. Editing Tips 4.4. How to Use Variables 4.5. Using FOR ... NEXT Loops 4.6. Using IF ... THEN Statements to Control Programs 5. ADVANCED BASIC 5.1. Simple Animation 5.2. INPUT 5.3. Using the GET Statement for Data Input 5.4. Using GET to Program Function Keys 5.5. Random Numbers and Other Functions 5.6. Guessing Game 5.7. Your Roll 5.8. Random Graphics 6. COLOR AND GRAPHICS 6.1. How to Use Color and Graphics on Your Computer 6.2. PRINTing Colors 6.3. Color CHR$ Codes 6.4. How to use PEEKs and POKEs 6.5. Screen Graphics 6.6. Screen Memory Map 6.7. Color Memory Map 6.8. More Bouncing Balls 7. INTRODUCTION TO SPRITES 7.1. Bits and Bytes 7.2. Creating a Sprite 7.3. Designing a Sprite 7.4. Sprite Pointers 7.5. Turning Sprites On 7.6. Sprite Colors 7.7. Positioning Sprites 7.8. Expanded Sprites 7.9. Creating More Than One Sprite 7.10. Sprite Priorities 7.11. Turning Sprites Off 8. MAKING SOUND AND MUSIC 8.1. The SID Chip 8.2. Sample Sound Program 8.3. Playing a Song on Your 64 8.4. Creating Sound Effects 8.5. Filtering 8.6. Music Composer 9. ADVANCED DATA HANDLING 9.1. READ and DATA Statements 9.2. Calculating Averages 9.3. Subscripted Variables 9.4. Dimensioning Arrays 9.5. Simulated Dice Roll with Arrays 9.6. Two-dimensional Arrays APPENDICES Introduction A: Expanding Your Commodore 64 Computer System B: Description of DOS Error Messages C: Commodore 64 BASIC D: Abbreviations for BASIC Keywords E: Screen Display Codes F: ASCII and CHR$ Codes G: Screen and Color Memory Map H: Deriving Mathematical Functions I: Pinouts for INPUT/OUTPUT Devices J: Programs to Try K: Converting Standard BASIC Programs to Commodore 64 BASIC L: Error Messages M: Music Note Values N: Bibliography O: Sprite Register Map P: 6566/6567 (VIC-II) Chip Register Map Q: Commodore 64 Sound Control Settings R: 6581 Sound Interface Device (SID) Chip Specifications S: Disk and Printer Commands and Statements INDEX THE INFORMATION IN THIS MANUAL HAS BEEN REVIEWED AND IS BELIEVED TO BE ENTIRELY RELIABLE. NO RESPONSIBILITY, HOWEVER, IS ASSUMED FOR INACCURACIES. THE MATERIAL IN THIS MANUAL IS FOR INFORMATION PURPOSES ONLY, AND IS SUBJECT TO CHANGE WITHOUT NOTICE. THIS MANUAL IS COPYRIGHTED AND CONTAINS PROPRIETARY INFORMATION. NO PART OF THIS PUBLICATION MAY BE REPRODUCED, STORED IN A RETRIEVAL SYSTEM, OR TRANSMITTED IN ANY FORM OR BY ANY MEANS, ELECTRONIC, MECHANICAL, PHOTOCOPYING, RECORDING, OR OTHERWISE, WITHOUT THE PRIOR WRITTEN PERMISSION OF COMMODORE BUSINESS MACHINES, (UK) LTD. Copyright (c) 1984 Commodore Business Machines (UK) Ltd. All rights reserved. INTRODUCTION Your new COMMODORE 64 is the best home computer available today. You can use your COMMODORE 64 for everything from business applications to household paperwork to exciting games. The 64 offers you lots of memory (64K), lots of color (16 different colors), lots of sound (music and sound effects), and lots of fun and practical uses. You can use prepackaged software, or you can write your own programs in easy-to-learn BASIC. This easy-to-read user's guide contains all the information you need to set up your equipment properly, understand how to operate your new COMMODORE 64, and learn how to create your own simple BASIC programs. This user's guide is intended to introduce you to computers, but it is beyond the scope of this manual to tell you everything you need to know about computers or about BASIC. However, this guide does refer you to a variety of publications that explain the topics we present here in more detail. For those of you who don't want to learn how to program, you won't have to search through the whole book to learn how to use Commodore prepackaged programs and games, or other prepackaged, third party software. We've put all the information you need to know right up front in Chapters 1 and 2. Many exciting features are waiting for you inside your COMMODORE 64. Your new computer gives you the microcomputer industry's most advanced graphics, which we call SPRITE GRAPHICS. Sprite graphics let you: o Design your own pictures in different colors, just like the ones you see on arcade-type video games. o Animate as many as 8 different picture levels at a time. o Move your creations anywhere on the screen. o Double their size. o Pass images in front or behind each other. o Use automatic collision detection that tells the computer to do whatever you want when sprites hit each other. These features let you design your own games. The COMMODORE 64 also has built-in music and sound effects that rival many well known music synthesizers. This part of your computer gives you: o 3 independent voices, each with a full 9 octave piano-type range. o 4 different waveforms (sawtooth, triangle, variable pulse and noise). o A programmable ADSR (attack, decay, sustain, and release) envelope generator. o A programmable high, low, and bandpass filter that you can use for each voice. o Variable resonance and volume controls. If you want your music to play back with professional sound reproduction, the COMMODORE 64 lets you connect your audio output to almost any high-quality amplification system. As your computing needs grow, so can your system. You can expand your system by connecting your COMMODORE 64 to other pieces of equipment, known as peripherals. These accessories include items like these: o The DATASSETTE* recorder, for tapes. o The VIC 1541 disk drive (as many as five at a time). o The COMMODORE dot matrix printers, for hard copies of your programs, letters, etc. o The MODEM cartridge, for access through your telephone to the massive data bases of larger computers, as well as the services of hundreds of specialists and a variety of information networks. o The Commodore 1701 color monitor. If you already have a VIC 1540 disk drive, your dealer can upgrade it for use with the COMMODORE 64. Commodore wants you to really enjoy your new COMMODORE 64. And to have fun, bear in mind that programming takes time to learn. Be patient with yourself as you go through the USER'S GUIDE. But, before you start, please take a few minutes to fill out and mail in the owner/registration card that came with your computer. This will ensure that your COMMODORE 64 is properly registered with Commodore Headquarters and that you receive the most up-to-date information regarding future enhancements for your machine. NOTE: Many programs are under development while this manual is being produced. Please check with your local Commodore dealer and with Commodore User's Magazines and Clubs, which will keep you up to date on the wealth of applications programs being written for the COMMODORE 64, worldwide. * DATASSETTE is a registered trade mark of Commodore Business Machines, Inc. 1. SETTING UP 1.1. UNPACKING AND CONNECTING THE 64 The following step-by-step instructions show you how to connect the 64 to your television set, sound system, or monitor and make sure everything is working properly. Before attaching anything to the computer, check the contents of the 64 container. Besides this manual, you should find the following items: 1. Commodore 64 2. Power supply (black box with an AC plug and supply cord) 3. Video cable If any items are missing check back with your dealer immediately for a replacement. First, take a look at the arrangement of the various connections on the computer and what each one does. /####\________________ /####______________________| ____/#### | / ---- ---- __ /-\ | | \--/ \--/ == \_/ | \________________\___/______/____|__/ \/ / | 3 2 1 GAME POWER POWER PORTS SWITCH SOCKET SIDE PANEL CONNECTIONS 1. POWER SOCKET. The free end of the cable from the power supply is attached here to supply power to the 64. 2. POWER SWITCH. Turns on power to the 64. 3. GAME PORTS. Each game connector can accept a joystick or game controller paddle, while the lightpen can only be plugged into the game port closest to the front of your computer. ___/###\__/##_##_##_##_##_##_##_##_##_##_##_##_##_##_##_##\__ |-------------------------------------------------------------| | +--------------+ /-\ /-\ +------+ +----------+ | | |==============| [=] O \_/ \_/ |======| |==========| | +-----/-------------/----/-----\-----\--------\---------\-----+ / / / \ \ \ \ 4 5 6 7 8 9 10 CARTRIDGE CHANNEL TV AUDIO/VIDEO SERIAL CASSETTE USER SLOT SELECTOR CONNECTOR CONNECTOR PORT INTERFACE PORT REAR CONNECTIONS 4. CARTRIDGE SLOT. The rectangular slot to the left accepts program or game cartridges. 5. CHANNEL SELECTOR. Use this switch to select which TV channel the computer's picture will be displayed on. 6. TV CONNECTOR. This connector supplies both the picture and sound to your television set. 7. AUDIO & VIDEO OUTPUT. This connector supplies direct audio, which can be connected to a high quality sound system, and a composite video signal, which can be fed into a television, or monitor, such as the Commodore 1701 color monitor. 8. SERIAL PORT. You can attach a COMMODORE printer or a VIC 1541 single disk drive directly to the Commodore 64 through this connector. 9. CASSETTE INTERFACE. A DATASSETTE recorder can be attached to the computer so you can save information on tape for use at a later time. 10. USER PORT. Various interface cartridges can be attached to the user port, such as the MODEM, or RS-232 communication cartridge. 1.2. INSTALLATION CONNECTIONS TO YOUR TV Connect the computer to your TV as shown bellow. +--+-----------------+--+ | | /-------------\#| | /--------------------------| | | |#| | | | | | |#| | | | | | | | | | | | | | | | | | | \-------------/ | | | +==+=================+==+ | /------------------------\ | |=---\ | #################### ## | | | #################### ## | | | ################## ## | | | ############## ## | | \________________________/ | | | | +---+ | | POWER | | SUPPLY +---+ | | 1. Attach one end of the TV cable to the phono type TV signal jack on the rear of the 64. Just push it in. Either end of the cable can be used. 2. Connect the other end of the cable to the antenna switchbox. Just push it in. 3. Plug the power supply cable into the power socket on the side of the Commodore 64. Just push it in. It is "keyed" to allow insertion in only one direction, so you can't connect the power cord the wrong way. The power supply converts household current into the form the computer uses. The 64 is now correctly connected. No additional connections are required to use the computer with your TV. 1701 MONITOR CONNECTIONS [REAR PANEL] Commodore 64 /---------------\ | AUDIO | __###__######################__ | _ | | | +-------------> |O| | |-------------_---_-------------| | | ~ | | ======== | | | | === ===== | # | COMMODORE VIDEO | +------------/------------------+ |W| | _ _ | / ^ \ / +----> |O| |O| <---+ Video Out / | # | | ~ ~ | | # | # | LUMA CHROMA | # | | W = White | |Y| | | |R| \ / Y = Yellow | \ / | SIGNAL SELECT | \ / # R = Red | # | [.##] | # # | | | FRONT | REAR | | # | | \_______|_______/ | # AUDIO = Audio Input | | | | # LUMA = Luminance Input | | ________|___________| # CHROMA = Chroma Input | | | | # \ | / Signal Selector # \|/ ____ # # FRONT | ###| REAR # Monitor Cable # ~~~~ ############################### ---> 1.3. OPTIONAL CONNECTIONS Since the 64 furnishes a channel of high fidelity sound, you may wish to play it through a quality amplifier to realize the best sound possible. In addition, the 64 also provides a standard composite video signal, that can be fed into a television monitor. These options are made possible by the audio/video output jack on the rear panel of the 64. The easiest way to gain access to these signals is by using a standard 5-Pin DIN audio cable (not supplied). This cable connects directly to the audio/video connector on the computer. Two of the four pins on the opposite end of the cable contain the audio and video signals. You can construct your own cable, using the pinouts shown in Appendix I as a guide. Normally, the BLACK connector of the DIN cable supplies the AUDIO signal. This plug may be connected to the AUXILIARY input of an amplifier, or the AUDIO IN connector of a monitor or other video system, such as a video cassette recorder (VCR). The WHITE or RED connector usually supplies the direct VIDEO signal. This plug is connected to the VIDEO IN connector of the monitor or video input section of some other video system, such as a VCR. Depending on the manufacturer of your DIN cable, the color coding of the plugs may be different. Use the pinouts shown in Appendix I to match up the proper plugs if you don't get an audio or video signal using the suggested connections. __###__################################__ | AUDIO/VIDEO | | OUTPUT | |-----------------_---_-------------------| | ========= = o | | | | ===== ========= | +-----------------------------------------+ ^ | /-\ | | | | # | | TO AUXILIARY | INPUT OR | ____________ TUNER INPUT | / \ / \ TO VIDEO IN +----++------------++----+ <-#-/ \-#-> +------------+---+ | || ### ====== || | | /--------\ | O | | || === OoooO || | || || = | | ||------------|| | || || o | | || | | | || | | \________/ | | | || | | | || | +------------+---+ +----++============++----+ TV MONITOR AUDIO SYSTEM If you purchased peripheral equipment, such as a VIC 1541 disk drive, an MPS 801, 802 or 803 printer, a 1520 plotter or a 1701 monitor, you may wish to connect it at this time. Refer to the user's manuals supplied with any additional equipment for the proper procedure for connecting it to the computer. A completed system might look like this. [ Picture omitted ] 1.4. OPERATION USING THE 64 1. Turn on the computer using the rocker switch on the right-side panel when you're looking at the computer from the front. 2. After a few moments the following will be displayed on the TV screen: **** COMMODORE 64 BASIC V2 **** 64K RAM SYSTEM 38911 BASIC BYTES FREE READY. _ <----------- CURSOR SIGNALS COMMODORE 64 IS WAITING FOR YOUR INPUT 3. If your TV has a manual fine tuning knob, adjust the TV until you get a clear picture. 4. You may also want to adjust the color and tint controls on the TV for the best display. You can use the color adjustment procedure described later to get everything set up properly. When you first get a picture, the screen should appear mostly dark blue, with a light blue border and letters. If you don't get the expected results, recheck the cables and connections. The accompanying chart will help you isolate any problem. 1.5. TROUBLESHOOTING CHART +-----------------------------------------------------------------------+ | Symptom Cause Remedy | +-----------------------------------------------------------------------+ | Indicator Light Computer not "On" Make sure power switch | | not "On" is in "On" position | +-----------------------------------------------------------------------+ | Power cable not Check power socket for | | plugged in loose or disconnected | | power cable | +-----------------------------------------------------------------------+ | Power supply not Check connection with | | plugged in wall outlet | +-----------------------------------------------------------------------+ | Bad fuse in Take system to authorized | | computer dealer for replacement of | | fuse | +-----------------------------------------------------------------------+ | No picture TV on wrong Check other channel | | channel for picture (3 or 4) | +-----------------------------------------------------------------------+ | Incorrect Computer hooks up to | | hookup VHF antenna terminals | +-----------------------------------------------------------------------+ | Video cable not Check TV output cable | | plugged in connection | +-----------------------------------------------------------------------+ | Computer set for Set computer for same | | wrong channel channel as TV (3 or 4) | +-----------------------------------------------------------------------+ | Random patterns on Cartridge not Reinsert cartridge after | | TV with cartridge properly inserted turning off power | | in place | +-----------------------------------------------------------------------+ | Picture without Poorly tuned TV Retune TV | | color | +-----------------------------------------------------------------------+ | Picture with Bad color Adjust color/hue/ | | poor color adjustment on TV brightness controls on TV | +-----------------------------------------------------------------------+ | Sound with excess TV volume up high Adjust volume of TV | | background noise | +-----------------------------------------------------------------------+ | Picture OK, TV volume too low Adjust volume of TV | | but no sound | +-----------------------------------------------------------------------+ | Aux. output not Connect sound jack to | | properly connected aux. input on amplifier | | and select aux. input | +-----------------------------------------------------------------------+ +-----------------------------------------------------------------------+ | TIP: The 64 was designed to be used by everyone. | | But we at Commodore recognize that computer users may, occasionally, | | run into difficulties. To help answer your questions and give you | | some fun programming ideas, Commodore has created several | | publications to help you. You might also find that it's a good idea | | to join a Commodore Users Club to help you meet some other 64 owners | | who can help you gain knowledge and experience. | +-----------------------------------------------------------------------+ CURSOR The flashing square under READY is called the cursor. It's a marker that shows where what you type on the keyboard will be displayed on the screen. As you type, the cursor moves ahead one space as the original cursor position is replaced with the character you typed. Try typing on the keyboard and watch the cursor move while characters you type are displayed on the screen. 1.6. COLOR ADJUSTMENT There is a simple way to get a pattern of colors on the monitor so you can easily adjust the set. Even though you may not be familiar with the operation of the computer right now, just follow along, and you'll see how easy it is to use your computer. First, look on the left side of the keyboard and locate the key marked . This stands for ConTRoL and is used, in conjunction with other keys, to instruct the computer to do a specific task. To use a control function, you hold down the key while pressing a second key. Try this: hold the key while also pressing the <9> key. Then release both keys. Nothing obvious should have happened, but if you touch any key now, the screen will show the character displayed in reverse type, rather than normal type -- like the opening message or anything you typed earlier. Hold down the . What happens? If you did the above procedure correctly, you should see a light blue bar move across the screen and then move down to the next line as long as the is pressed. READY. ____________________________ __________ Now, hold while pressing any of the other number keys. Each of them has a color marked on the front. Anything displayed from this point will be in that color. For example, hold and the <8> key and release both. Now hold the . Watch the display. The bar is now in yellow! In a like manner you can change the bar to any of the colors indicated on the number keys by holding and the appropriate key. Change the bar to a few more different colors and then adjust the color and tint controls on your monitor so the display matches the colors you selected. The display should appear something like this: READY. _________________________ <------ <3> RED BAR _______ ____________ ____ <------ <3>,<6>,<7> RED, GREEN, BLUE BARS __________ ______________ <------ <7>,<8> BLUE, YELLOW BARS ____________ <------ <8> YELLOW BAR At this point everything is properly adjusted and working correctly. The following chapters will introduce you to the BASIC language. However, you can immediately start using some of the many prewritten applications and games available without knowing anything about computer programming. Each of these packages contains detailed information about how to use the program. It is suggested, though, that you read through the first few chapters of this manual to become more familiar with the operation of your new system. 1.7. EXPANDING YOUR SYSTEM WITH OPTIONAL PERIPHERALS Commodore offers a variety of peripheral devices that expand the capabilities of your computer. These peripherals include: o storage devices o printers and plotters o monitors o modems for telecommunications o game attachments o speech and graphics modules o desktop controllers STORAGE DEVICES Disk Drives Commodore's disk drives let you store large amounts of information on 5-1/4" floppy diskettes. Diskettes offer fast storage and retrieval, and they automatically keep track of all your files in a directory, or table of contents, that you can display on your screen or print on a printer. In addition, you can add extra disk drives by daisy-chaining them to your computer. Daisy-chaining means connecting one drive to the computer, and then connecting additional drives to each other. By acquiring the Commodore 64 IEEE Interface Expansion Card, you can also attach any IEEE disk drive, such as Commodore's CBM 8050 or 4040 Dual Floppy Disk Drives, to the 64. Chapter 2 contains detailed information on using disk drives. PRINTING AND PLOTTING DEVICES Printers You can attach Commodore printers to the 64. These are inexpensive dot matrix printers. By acquiring the Commodore 64 IEEE Interface Expansion Card, you can also attach any IEEE printer, such as Commodore's 6400 letter quality printer, or the high speed 8023 dot matrix printer, to the 64. Printer/Plotter Commodore's 1520 Printer/Plotter prints and draws graphics in four colors (black, blue, red and green). With the 1520, you can draw bar charts, pies, and a variety of complex graphics. THE 1701/1702 MONITOR Commodore's 14" color monitor offers a superior color picture with high resolution that enhances your computing experience. This monitor can be connected to the 64. The monitor is connected to the computer by an 8-pin DIN cable. The 1701/1702 Color Monitor User's Guide that comes with the monitor clearly explains connections. You can also consult Appendix I for information about the pinouts in the 8-pin connector. ATTACHMENTS FOR GAMES AND OTHER USES Commodore offers joysticks and paddles that enhance game-playing on your computer. These attachments also have other applications. Also available is the Commodore lightpen which, with appropriate software allows communication with the computer on the screen. COMMODORE GRAPHIC AIDS Commodore provides a variety of graphics programming aids, including SIMON'S BASIC which adds 114 powerful new commands to BASIC, including programming help and graphics commands; and LOGO, an easy-to-learn programming language with TURTLE graphics. MUSIC ATTACHMENTS Commodore will also soon offer a Musical Keyboard and a 3-pad percussion attachment called the Digi-drum. Both products will include special software packages. These attachments will increase the music making capabilities of the 64 computers. CONNECTING TO A STEREO SYSTEM The sound and music-making capabilities of the COMMODORE 64 can be enhanced by connecting your computer to a high quality amplifier and stereo speakers. The 8-pin DIN cable discussed in the 1701/1702 Color Monitor section can also be used to connect your computer to an amplifier. DESIGNING A COMPUTER SYSTEM FOR YOUR NEEDS Commodore offers a variety of peripherals that let you create your own customized computer system. We offer different types of storage, printing, and telecommunications devices so you can choose what's best for you. For more information about Commodore peripherals, read The Commodore Peripherals Guide and the Commodore magazines discussed in Appendix H and consult your Commodore dealer. 2. GETTING STARTED 2.1. COMMUNICATING WITH YOUR 64: THE KEYBOARD The computer keyboard lets you communicate with your 64. You use the keys to tell the computer what you want it to do and to answer the questions the computer displays on the screen. The keyboard looks like a regular typewriter, but the computer has special keys that let the 64 do more than a typewriter. While you read the next few pages, take a look at these special keys. The key tells the computer to look at what you typed and put this information in memory. The key also moves the cursor to the next line. NOTE: Memory is all the information the computer currently knows without needing you to tell it where to look. The key works like the shift key on a regular typewriter: it lets you print capital letters or the top characters on double character keys. ___ ___ ___ / ! \ / " \ / # \ || 1 || || 2 || || 3 || /\___/\ /\___/\ /\___/\ |_____| |_____| |_____| When you are using the graphics on the font of the keys, the key displays the graphic character on the RIGHT side of the key. ___ ___ ___ / \ / \ / \ || Q || || W || || E || /\___/\ /\___/\ /\___/\ |_|_-_| |_-_|_| |_|_-_| When you are using the four special function keys at the right side of the keyboard, the key gives you the functions on the FRONT of the key (F2, F4, F6, and F8). KEYS THAT LET YOU MAKE CHANGES The cursor is the little colored rectangle that marks your place on the screen. There are two CuRSoR keys: moves the cursor up and down moves the cursor left and right You must use the key with the key to move the cursor up, and with the key to move the cursor to the left. You don't have to keep tapping a key to get it to move more than one space. Just hold it down until the cursor is where you want it. DEL stands for DELete. When you press the key, the cursor moves back a space and erases the character that's there. PRINT "ERROR"#_ PRINT "ERROR"# When you DELete in the middle of a line, move the cursor just to the left of the character you want to DELete. FIX IT AGAINS, SAM FIX IT AGAINS_ SAM Then press the key. The characters to the right automatically move over to close up the space. FIX IT AGAIN, SAM INST stands for INSerT. You have to use the key with the key when you want to insert characters in a line. If you've left some characters out of a line, use the keys to move the cursor back to the error. WHILE U WERE OUT WHILE _ WERE OUT Then, while you hold down the key, press the key until you have enough space to add the missing characters. doesn't move the cursor; it adds space between the cursor and the character to its right. WHILE _ U WERE OUT WHILE YOU WERE OUT Use the and keys together to fix wrong characters. WE'RE NUMBER TWO! WE'RE NUMBER ! WE'RE NUMBER _ ! WE'RE NUMBER ONE! HOME moves the cursor back to the upper left corner of the screen. This is called the "HOME" position. CLR stands for CLeaR. When you use the key with the key, the screen CLeaRs and the cursor returns to the home position. The RESTORE key returns the computer to its normal state by RESTOREing the default conditions (e.g., the default screen color is blue, the default for I/O chips is OFF, etc.). RESTORE does such things as clear the screen, returning it to the original color, and turn off the picture- and sound-making chips. NOTE: For to work, you must hold down the key while you press the key. For example, suppose you've just played a music program that also turned your screen red and yellow while it LISTed the program. When you press and at the end of the program, the last note from the program will cease, your screen will turn blue and the only thing displayed will be the READY prompt. FUNCTION KEYS The keys on the right side of the keyboard, F1-F8, are function keys that you can program to perform a variety of tasks. The explanation of the GET statement in Chapter 5 tells you how to program function keys in BASIC. The ConTRoL key lets you set colors and do other special tasks called control functions. To set colors, hold down the key while you press the key with the color you want. You can get eight more colors with the key. Chapter 6 also has more about colors. To get a control function, hold the key down while you press the other key. Control functions are commonly used in prepackaged software such as a word processing system. You can halt a BASIC program while it is still RUNning by pressing the key. You can also use the key to halt a printout while it is still printing. lets you load a program automatically from cassette. When you want to use the key, you must also use the key. COMMODORE KEY The Commodore key can do two things: 1. lets you switch back and forth between the upper and lower case display mode (the letters and characters on the tops of the keys) and the upper case/graphic display mode (capital letters and the graphics on the fronts of the keys). To switch modes, press the and keys at the same time. When you first turn on your 64, it is in the upper case/graphic mode, which means that everything you type in is in capital letters. When you are in this mode, you can also print all the graphics on the fronts of the keys. o To print the graphic on the right side of a key, hold down the key while you press the key with the graphic you want to print. You can only print the right side graphics when you are in the upper case/ graphic mode. o To print the graphic on the left side of a key, hold down the key while you press the graphic key. You can print the left side graphic in either mode. 2. The key also lets you use the second set of eight alternate colors not shown on the color keys. To get these other colors, hold down the key while you press the number for the color you want. 1 ORANGE 5 GREY 2 2 BROWN 6 LT. GREEN 3 LT. RED 7 LT. BLUE 4 GREY 1 8 GREY 3 2.2. LOADING PROGRAMS The COMMODORE 64 accepts programs from disk, cartridge, or cassette tapes. This means you can use prewritten software simply by loading it. But more important, the 64 lets you save your own programs for reuse. To reuse a program you wrote and saved on disk or tape, all you do is load and run it. When you use tapes or disks with your COMMODORE 64 be sure that your disk drive or cassette unit is correctly connected. Loading Cartridges You can use a special line of programs and games on cartridge with your 64. The programs include a wide variety of business and personal applications. The games are just like real arcade games, not imitations. Follow these steps to load games and other cartridges: 1. Turn OFF your COMMODORE 64. YOU MUST TURN OFF YOUR COMMODORE 64 BEFORE YOU INSERT OR REMOVE CARTRIDGES. IF YOU DON'T, YOU MAY DAMAGE THE CARTRIDGE AND THE COMPUTER. 2. Insert the cartridge label uppermost in the slot on the back of your computer. 3. Turn on your 64. 4. Begin the game by typing the START key that's listed in the game's instruction sheet. Loading Prepackaged Cassette Tapes You can also buy prepackaged software on cassette tape. These cassettes are just like the ones with recorded music that you can play on a stereo. 1. Insert the cassette into your 1530 DATASSETTE recorder. 2. Make sure the tape is completely rewound to the beginning of the first side. 3. Type LOAD on your keyboard. The computer answers by displaying: PRESS PLAY ON TAPE 4. Press PLAY on your DATASSETTE. The screen goes blank until the computer finds the program. Then the screen displays the message FOUND (PROGRAM NAME). 5. Press the key. This actually loads the program into the computer. If you want to stop the loading, press the key. Loading Your Own Programs From Cassette Tape The COMMODORE 64 lets you write and save programs on any brand of cassette tape. All you need is a 1530 DATASSETTE recorder and the same kind of blank tape you'd use to record music for a stereo tape player. Follow these simple steps to load a program you wrote and saved on tape: 1. Rewind the tape to the beginning. 2. Type LOAD "PROGRAM NAME". If you don't remember the program name, just type LOAD. This loads the first program on the tape into memory. 3. Press . The computer responds with: PRESS PLAY ON TAPE 4. Press the PLAY key. The screen goes blank while the computer searches for the program. When the program is found, the screen displays this message: FOUND PROGRAM NAME 5. Press the key to actually load the program. The screen again goes blank during LOADing. When the program is LOADed, the screen returns to normal and the READY prompt appears. If you want to abort the loading, press the key. NOTE: When you load a new program into the computer's memory, any instructions and unsaved programs in the computer are erased and lost permanently. Before you LOAD a new program, be sure everything you want to keep is saved. After your program is LOADed, you can RUN it, LIST it, or make changes. Remember that you have to reSAVE a changed program if you want to keep the new version. Loading Disks Disks, which are often called "floppy disks", are really easy to use. The advantage of disks over tapes is that you can find data stored on disks much faster. You can also save much more data on a disk than on tape. The steps are the same for loading preprogrammed disks and disks that you program yourself. 1. Insert a disk into your disk drive. Make sure the label on the disk is facing up. Put the disk in so that the labeled end goes in last. Look for a little notch on the disk (it might be covered with a little piece of tape). This notch must be on the left side as you put in the disk, assuming that you're facing your computer. Be sure the disk is all the way in. 2. Close the protective gate on the disk drive after you insert the disk. Just push down the lever. 4. Type LOAD"PROGRAM NAME",8. The 8 is the code for disks. You need to type it here to let the computer know you're loading a disk. NOTE: You can LOAD the first program by using the * sign in place of the program name: LOAD"*",8. 4. Press the key. The disk will spin and your screen will say: SEARCHING FOR PROGRAM NAME LOADING READY _ 5. Type RUN when the screen says READY and the cursor appears. Your software is ready to use. 2.3. HOW TO FORMAT A NEW DISK When you're using a new, unprogrammed disk for the first time, you need to format it. Formatting, which is also called headering, prepares your disk by doing things like dividing the disk into blocks. Formatting also creates a directory that you use as a table of contents for the files you save on the disk. DO NOT header a preprogrammed disk. You only have to format new disks, not disks that already have programs on them unless you want to erase the entire disk and reuse it. To format a new disk, use this special version of the OPEN and NEW commands: OPEN 1,8,15,"N0:," N0 tells the computer to header (NEW) the disk in drive 0. If you have a dual disk drive connected (via a suitable interface) header disks in drive 0. The you use in this command goes in the directory as the name of the entire disk. Give the disk any name up to 16 characters. The is any two characters. Give the disk any you want, but you should give every disk a different code. When the disk drive light goes off, type CLOSE 1 and press . BE CAREFUL! Headering a disk erases all information on the disk, if there is any. Header only a new disk or a disk you are willing to erase. Here are some examples of formatting commands that header a disk: OPEN 1,8,15,"N0:MYFILE,A3" OPEN 1,8,15,"N0:$RECORDS,02" Now that you know how to header a disk, you are ready to use disks to write and save programs on your COMMODORE 64. Appendix S contains more information on the OPEN command. 2.4. SAVING PROGRAMS When you want to reuse a program you've written, be sure to SAVE it before you LOAD another program. If you don't, you'll lose the program. When you change a SAVEd program, you have to SAVE it again if you want to keep the new version. When you reSAVE a program, you are replacing the old version with the new one. If you want to keep both the old and the changed versions, you have to give the new one a different name when you SAVE it. Saving on Disk When you want to SAVE a program you've written on disk, follow these simple steps: 1. Key in SAVE"PROGRAM NAME",8. The 8 is the code for disks. It tells the computer that you're using a disk. 2. Press . The disk makes a noise, and the computer displays this message when the program is saved: SAVING PROGRAM NAME OK READY _ Saving on Cassette Tape When you want to SAVE a program you've written on cassette tape, follow these steps: 1. Key in SAVE"PROGRAM NAME". The program name you use can be up to 16 characters long. 2. Press the key. The computer displays the message PRESS RECORD AND PLAY ON TAPE. 3. Press the RECORD and PLAY keys on your DATASSETTE recorder. The screen goes blank and turns the color of the border. The READY prompt reappears when the program is SAVEd. 2.5. LISTING A DIRECTORY OF PROGRAMS ON A DISK When you SAVE programs on a disk, the computer automatically makes a table of contents, or a DIRECTORY, of the names of the programs on the disk. You can display this directory to see what programs are on your disk. Follow these steps: 1. Key in: LOAD"$",8 and press . The computer displays this message: SEARCHING FOR $ LOADING READY _ 2. Key in: LIST and press . Your programs names are displayed on your screen. 3. BEGINNING BASIC 3.1. PRINTING AND CALCULATING If you don't know BASIC, this section teaches you how to do some simple things like print words and calculate problems. The PRINT statement tells the 64 computer to print something on the screen. PRINT is one of the most useful and powerful commands in the BASIC language. You can use it to display just about anything, including graphics and the results of computations. To use the PRINT command, follow these steps: 1. Key in the word PRINT. This tells the computer what kind of job you want it to do. 2. Key in a quotation mark. This tells the computer where the message you want to print begins. 3. Key in whatever you want to print on the screen. 4. Key in a closing quotation mark. This tells the computer where the message you want to print ends. 5. Press the key. This tells the computer to follow your instructions, which in this case is to print your message exactly as you typed it. When you follow these steps, the computer prints your message and displays the READY prompt. It looks like this: PRINT "I LOVE MY COMMODORE" You key in this and press I LOVE MY COMMODORE The computer prints this READY _ The 64 prints whatever you enclose in quotes. Remember to key in both quotation marks. If you make a mistake in your PRINT statement, use the INST/DEL key to correct your error. You can change as many characters as you like before you press the key. If you made a mistake that you didn't catch before you pressed the key, the computer can't follow your instructions. Instead, it displays an error message to help you figure out what you did wrong. For example: ?SYNTAX ERROR If you get this message, check over what you typed in to see where you made a mistake. The computer is very precise, and it can't follow instructions that contain spelling errors or other mistakes. To avoid mistakes, be sure you type things in the correct form. Remember that the best way to get to know BASIC and your 64 is to try different things and see what happens. USING PRINT TO CALCULATE You can use PRINT to do more than just display what you put in quotation marks. You can also use it to perform calculations and automatically display the results. Follow these steps: 1. Key in PRINT. 2. Key in the calculation you want to solve. DON'T enclose it in quotation marks. 3. Press the key. The computer displays the answer followed by the READY prompt. Here's an example: PRINT 12 + 12 Type this line and press 24 READY The computer displays _ the answer Be sure you leave off the quotation marks when you want the computer to solve a problem. If you type the problem inside quotation marks, the computer assumes you just want to display the problem, not solve it. For example: PRINT "12 + 12" Key in this line and press 12 + 12 READY The computer displays _ what's in quotes So all you have to do to use PRINT as a calculator is omit the quotation marks. You can use PRINT to add, subtract, multiply and divide. You can also use exponents and perform advanced mathematical functions such as figuring square roots. 3.2. MATHEMATICAL FUNCTIONS ADDITION Use the plus sign (+) to tell the computer to add numbers. Remember to press after you type PRINT and the calculation. This tells the computer to follow your instructions. SUBTRACTION Use the minus sign (-) to subtract. Press the key at the end of the calculation. For example: PRINT 12 - 9 Key in this and 3 The computer displays this MULTIPLICATION Use the asterisk (*) to multiply. You can't use the conventional x because the computer would think it's the letter x, not the multiplication sign. Press at the end of the calculation. For example: PRINT 12 * 12 Key in this and 144 The computer displays this DIVISION Use the slash mark (/) for division. Press the key after you type the calculation. For example: PRINT 144/12 Key in this and 12 The computer displays this EXPONENTIATION Use the up arrow (^) to raise a number to a power. Press the key after you type the calculation. For example, to find 12 to the fifth power, type this: PRINT 12^5 Key in this and 248832 The computer displays this This is the same as: PRINT 12*12*12*12*12 248832 +-----------------------------------------------------------------------+ | TIP: | | BASIC has shortcuts that make programming even faster. One shortcut | | is abbreviating BASIC keywords. For example, you can use a ? in place | | of PRINT. Throughout this book, we'll show you other abbreviations | | for BASIC keywords. Appendix D lists these abbreviations and shows | | what is displayed on the screen when you type the abbreviated form. | +-----------------------------------------------------------------------+ 3.3. MULTIPLE CALCULATIONS ON ONE LINE The last example shows that you can perform more than one calculation on a line. You can also perform different kinds of calculations on the same line. For example: ? 3 * 5 - 7 + 2 Key in this and 10 The computer displays this So far our examples have used small numbers and simple problems. But the 64 can do much more complex calculations. The next example adds large numbers. Notice that 78956.87 doesn't have a comma between the 8 and the 9. You can't use commas this way in BASIC. BASIC thinks commas indicate new numbers, so it would think 78,956.87 is two numbers: 78 and 956.87. Remember to press after you type the problem. ? 1234.5 + 3457.8 + 78956.87 83649.17 The next example uses a ten digit number. The 64 can work with numbers that have up to ten digits, but can only display nine digits in the answer. So the 64 rounds numbers that are more than nine digits. Numbers five and over are rounded up, and numbers four and under are rounded down. This means that 12123123.45 is rounded to 12123123.5. Because of rounding, the computer doesn't give the same answer you'd get if you added these numbers by hand. In this case, the answer is 12131364.817. You can see the difference rounding makes. ? 12123123.45 + 345.78 + 7895.687 12131364.9 The 64 prints numbers between 0.01 and 999,999,999 using standard notation, except for leaving out commas in large numbers. Numbers outside this range are printed using scientific notation. Scientific notation lets you express a very large or very small number as a power of 10. For example: ? 123000000000000000 1.23E+17 Another way of expressing this number is 1.23 * 10 ^ 17. The 64 uses scientific notation for numbers with lots of digits to make them easier to read. There is a limit to the numbers the computer can handle, even using scientific notation. These limits are: Largest numbers : +/- 1.70141183E+38 Smallest numbers: +/- 2.93873588E-39 3.4. EXECUTION ORDER IN CALCULATIONS If you tried to perform some mixed calculations of your own, you might not have gotten the results you expected. This is because the computer performs calculations in a certain order. In this calculation: 20 + 8 / 2 the answer is 14 if you add 20 to 8 first, and then divide 28 by 4. But the answer is 24 if you first divide 8 by 2, and then add 20 and 4. On the 64, you always get 24 because the computer always performs calculations in the same order. Problems are solved from left to right, but within that general movement, some types of calculations take precedence over others. Here is the order of precedence: First : - minus sign for negative numbers, not for subtraction. Second: ^ exponentiation, left to right Third : * / multiplication and division, left to right Fourth: + - addition and subtraction, left to right This means that the computer checks the whole calculation for negative numbers before doing anything else. Then it looks for exponents; then it performs all multiplication and division; then it adds and subtracts. This explains why 20 + 8 / 2 is 24: 8 is divided by 2 before 20 is added because division has precedence over addition. There is an easy way to override the order of precedence: enclose any calculation you want solved first in parentheses. If you add parentheses to the equation shown above, here's what happens: ? (20 + 8) / 2 14 You get 14 because the parentheses allow 20 and 8 to be added before the division occurs. Here's another example that shows how you can change the order, and the answer, with parentheses: ? 30 + 15 * 2 - 3 57 ? (30 + 15) * 2 - 3 87 ? 30 + 15 * (2 - 3) 15 ? (30 + 15) * (2 - 3) -45 The last example has two calculations in parentheses. As usual, they're evaluated from left to right, and then the rest of the problem is solved. When you have more than one calculation in parentheses, you can further control the order by using parentheses within parentheses. The problem in the innermost parentheses is solved first. For example: ? 30 + (15 * (2 - 3)) 15 In this case, 3 is subtracted from 2, then 15 is multiplied by -1, and -15 is added to 30. As you experiment with solving calculations, you'll get familiar with the order in which mixed calculations are solved. 3.5. COMBINING PRINT'S CAPABILITIES The 64 computers let you combine the two types of print statements that you've read about in this book. Remember that anything you enclose in quotation marks is displayed exactly as you type it. The next example shows how you can combine the types of PRINT statements. The equation enclosed in quotes is displayed without being solved. The equation not in quotes is solved. The semicolon separates the two parts of the PRINT statement (semicolon means no space). ? "5 * 9 ="; 5 * 9 You key in this and 5 * 9 = 45 The computer displays this Remember, only the second part of the statement actually solves the calculation. The two parts are separated by a semicolon. You always have to separate the parts of a mixed PRINT statement with some punctuation for it to work the way you want it to. If you use a comma instead of a semicolon, there is more space between the two parts when they're displayed. A semicolon leaves out space. The 64's screen is organized into 4 zones of 10 columns each. When you use a comma to separate parts of a PRINT statement, the comma works as a tab, sending each result into the next zone. For example: ? "TOTAL:";95,"SHORTAGE:";15 TOTAL: 95 SHORTAGE: 15 If you have more than four results, they are automatically displayed on the next line. For example: ? 2 * 3,4 - 6,2 ^ 3,6 / 4,100 + (-48) 6 -2 8 1.5 52 Here's the difference when you use semicolons: ? 2 * 3;4 - 6;2 ^ 3;6 / 4;100 + (-48) 6 -2 8 1.5 52 You can use the difference between the comma and the semicolon in formatting PRINT statements to create complex displays. 4. WRITING SIMPLE BASIC PROGRAMS So far this book has shown you how to do simple things with your 64. You've experimented with typing single lines of instructions into your computer and getting instant results by pressing the key. This easy way of doing things on your computer is called the IMMEDIATE or CALCULATOR mode. But you'll probably want to use your computer to do more complex jobs that use more than one statement. When you combine a number of statements into a PROGRAM, you can use the full power of your 64. To see how easy it is to write your first program on 64, follow these steps: 1. Clear the screen by holding down the key while you press the key. 2. Key in NEW and press . This clears out information that might still be in the computer's memory after your experimenting. 3. Key in the following two lines exactly as they appear here: 10 ? "COMMODORE 64" 20 GOTO 10 4. Remember to press the key after each line. After you key in the first line and press , you'll notice that the computer doesn't respond to the PRINT command right away like it did before when you typed in the same kind of commands. This is because you are now beginning the command with a line number (10). When you use line numbers, the computer knows that you're writing a program, so it waits for you to finish keying in the whole program before following any of your instructions. 5. Key in RUN and press . The RUN command tells the computer that you've finished keying in program statements, and you're ready to have your instructions followed. Here's what happens when you RUN this program: COMMODORE 64 COMMODORE 64 COMMODORE 64 COMMODORE 64 COMMODORE 64 COMMODORE 64 6. Stop the program's execution by pressing the key. The computer continues to follow your orders by printing COMMODORE 64 over and over until you interrupt with the key. Here's how your screen looks when you press STOP. COMMODORE 64 COMMODORE 64 COMMODORE 64 COMMODORE 64 COMMODORE 64 COMMODORE 64 BREAK IN 10 READY This simple program introduces several important concepts that are the basis for all programming. 4.1. LINE NUMBERS We mentioned before in step 4 that line numbers tell the computer that you're writing a program. They also tell the computer in what order you want the statements in your program to execute. Without line numbers to tell the computer when to follow which instruction, the computer doesn't know what to do first. The longer and more complex your program is, the more important it is to remember that the computer relies on you to tell it WHEN to do things, as well as WHAT to do. One good thing about this is that you can key in line 20 before line 10 because the computer just checks the line numbers to find out the order for executing the program. The computer doesn't check for the order your lines appear on the screen. Another advantage of line numbers is that you can use the number to refer to the statement on the line. When you want to go back and repeat the execution of a statement, all you do is refer to it by line number in a GOTO statement, as you did in the example above. 4.2. THE GOTO STATEMENT When you told the computer to RUN the sample program above, COMMODORE 64 was PRINTed repeatedly instead of just once because of the GOTO statement in line 20. The GOTO statement tells the computer to go directly to a specified line. Then the computer follows the instructions in the specified line and goes on to the next line. You can use a GOTO statement to tell the computer to go back to a line that's already been executed. Or GOTO can tell the computer to skip forward, even if this means that some lines in the program don't get executed. In our example, the program PRINTs the message in line 10 and moves to line 20. There, the GOTO statement tells the computer to go back to line 10 and do what line 10 says to do. So, the program prints the message in line 10 again, and then moves to line 20, which sends the computer back to line 10 and so on. This repetition is called a LOOP. Because the example doesn't give the computer a way out of the loop, the circle repeats endlessly. You have to halt the cycle by interrupting the program with the key. It's best to include a statement in your program that ends the loop so you don't have to use the key. We'll explain more above ending loops later in this chapter. 4.3. USING THE LIST COMMAND Now that you've interrupted execution of the sample program, type in LIST and press . Your program is now displayed intact because it's still in the computer's memory, even though you interrupted the program's execution. The only difference is that the computer changed your ? into the word PRINT. This doesn't affect your program, it's just the way the computer does things. When you use the LIST command, the computer also displays the lines of the program in correct numerical order, even if you entered the lines out of order. One of the important differences between writing programs and entering single lines in the immediate/calculator mode is that you permanently lose an immediate statement once you execute it and clear the screen. But, until you start a new program, you can always get a program back just by keying in LIST. From here, you can change the program, SAVE it, or RUN it again. 4.4. EDITING TIPS When you make a mistake in a line you've keyed in, or when you just want to change a line, the 64 offers you a number of editing options. 1. You can retype a line any time, and the computer automatically substitutes the new line for the old one. All you have to do to replace a line is use the same line number. For example: 10 ? "MY NAME IS SARAH" 20 ? "I WAS BORN IN CALIFORNIA" 20 ? "I LIVE IN PENNSYLVANIA" RUN MY NAME IS SARAH I LIVE IN PENNSYLVANIA As you can see, the first line 20 never executes because it is replaced by the second line 20. If you now key in a LIST command, you'll see that only the second line 20 is still part of the program. 2. You can easily erase a line you don't want just by keying in the line number and pressing the key. If you now key in LIST, you'll see that the line is gone, and so is the line number. 3. You can easily edit an existing line. Use the CuRSoR keys to move the cursor back to the line you want to change, and then just edit the line any way you want to. As soon as you press the key, the edited line will replace the old line. Remember to use the key to insert or delete. When you finish editing, you can check your program again to verify changes by keying in the LIST command. Remember that LIST also puts lines in numerical order if you've keyed them in out of order. Try editing our sample program by adding a semicolon to the end of the line, and omitting the 64. After you finish the changes, be sure to move the cursor past line 20 before you RUN the program. Here's how the program works now: LIST 10 PRINT "COMMODORE"; 20 GOTO 10 RUN COMMODORE COMMODORE COMMODORE COMMODORE COMMODORE COMMODORE COMMODORE COMMODORE BREAK IN 10 READY 4.5. HOW TO USE VARIABLES A variable is a symbol that stands for a value. Sometimes the value of a variable is unknown before you RUN a program. One of the purposes of a program may be to find one or more values for a variable. Look at this line from a program: 20 LET X = 28 + Y The = sign means "become" or "take the value of". The LET instruction is optional and may be omitted. In this equation, X and Y are variables. Suppose X stands for the number of days in a month. One of the best things about a variable is that you can reuse it in a program, so X can stand for the days in all the months, not just one month. This is where Y comes in. All months have 28 days, so Y stands for the days over 28. Later in this chapter there's a program that gives values to these two variables. The most important thing now is understanding how variables work, because variables allow you to do complex tasks with your computer. Variables also let you write programs that are very reusable. Imagine that your computer contains a bunch of little slots, like a bank of mail boxes. When you write a program, you can use some of these slots to hold values. All you do is give a name to the slots you need, and during the program you can put values into each slot by using the slot's name. For example, in the equation above, we used two slots by naming one X and one Y. At the beginning of a program, these slots have names, but they're empty. Here's what happens when you put a value in Y's slot: +--------+--------+--------+--------+--------+--------+--------+ | X | Y | | | | | | +--------+--------+--------+--------+--------+--------+--------+ | | 3 | | | | | | +--------+--------+--------+--------+--------+--------+--------+ Now the variable Y has the value 3. You can give Y this value just by writing this simple statement: 10 Y = 3 Since X equals 28 plus Y, when you RUN the program X's slot gets a value, too. +--------+--------+--------+--------+--------+--------+--------+ | X | Y | | | | | | +--------+--------+--------+--------+--------+--------+--------+ | 31 | 3 | | | | | | +--------+--------+--------+--------+--------+--------+--------+ Here's how the program looks: 10 Y = 3 20 X = 28 + Y 30 ? "THE NUMBER OF DAYS IN MAY IS ";X RUN THE NUMBER OF DAYS IN MAY IS 31 Here's another program that uses variables: 10 X% = 15 20 X = 23.5 30 X$ = "TOTAL:" 40 Y = X% + X 50 ? X$;Y When you RUN the program, the imaginary slots look like this after line 30 is executed: +--------+--------+--------+--------+--------+ | X% | X | X$ | Y | | +--------+--------+--------+--------+--------+ | 15 | 23.5 | TOTAL: | | | +--------+--------+--------+--------+--------+ On completion of the program, Y has the value: 38.5 The above example uses the three types of variables: EXAMPLE TYPE SYMBOL DESCRIPTION EXAMPLES VALUES --------------------------------------------------------------------- Integer % whole numbers X%, A1% 15,102,3 Text string $ characters in X$, AB$ "TOTAL:", quotes "DAY 1" Floating real (decimal) X, AB 23.5, 12, point or whole numbers 1.3E+2 Be sure you use the right variable types in your programs. If you try to do something like assign a text string to an integer variable, your program won't work. There are a few other things to keep in mind when you assign names to variables: o A variable name can have one or two characters, not counting the special symbol used with integer and text string variables. o You can use more than two alphabetic characters in a variable name, but the computer only recognizes the first two. So the computer would think PA, PARTNO and PAGENO are the same variable referring to the same "slot". o A program is easier for people to read when you use longer variable names, but when you use more than two characters in a name, be sure the first two are unique. o You can use X, X%, and X$ in one program because the special symbols % and $ make each variable name unique. The same is true of A2, A2%, and A2$. o The first character must be alphabetic (A to Z). The second and any later characters can be either alphabetic or numeric (0 to 9). Remember that the computer ignores every character after the second unless it's a % or $ in the third position. o Variable names can't contain BASIC keywords, which are also called reserved words. These are the words like PRINT and RUN that are part of the BASIC language. Appendix D lists all the BASIC reserved words. Here's one more sample program that shows you how to use variables. This example also uses some of the other things you've learned so far. NEW 10 X = 1.05 20 Y = 300 30 Z = X * Y 40 PRINT "SEATS AVAILABLE:";Y 50 PRINT "TICKETS AVAILABLE:";Z 60 Y = Y + 1 70 PRINT "OVERBOOKING POINT:";Y RUN SEATS AVAILABLE: 300 TICKETS AVAILABLE: 315 OVERBOOKING POINT: 301 Lines (10-30) assign variable names. Lines 40 and 50 PRINT a message and the current value of variables Y and Z. Notice that at line 40, the value for Y is 300. Line 60 gives Y a new value, and this new value is PRINTed in line 70. Line 60 shows that a variable can have more than one value in a program. Line 60 also shows another of the powerful features of variables: you can make a variable equal to itself and another value. This isn't allowed in regular algebra, but this kind of statement is commonly used in programming. It means: take the current value of a variable, combine it with another value, and replace the first value of the variable with this new value. You can also use statements like these: Y = Y - 1 Y = Y + X Y = Y / 2 Y = Y * (X + 2) 4.6. USING FOR/NEXT LOOPS We mentioned loops earlier in this chapter during the explanation of the GOTO statement. As you'll recall, loops are repeated executions of one or more lines in a program. The FOR/NEXT statement lets you create very useful loops that control the number of times a segment of a program is executed. The FOR statement sets a limit on the number of times the loop will execute by assigning a range of values to a variable. For example: FOR COUNT=1 TO 4 The NEXT statement marks the end of a FOR/NEXT loop. When the program reaches a NEXT statement, the computer checks the FOR statement to see if the limit of the loop has been reached. If the limit hasn't been reached, the loop continues and the variable in the FOR statement is incremented by one. For example, if you add a FOR/NEXT loop to the program at the beginning of this chapter, here's what happens: 10 FOR CT =1 TO 4 20 ? "COMMODORE 64" 30 NEXT CT RUN COMMODORE 64 COMMODORE 64 COMMODORE 64 COMMODORE 64 Now that you've added the FOR/NEXT loop, you don't have to break in with the STOP key to halt the program's execution. This FOR/NEXT loop works like this: Line 10 gives the variable CT a range of values from 1 to 4, and tells the computer to execute the next lines until CT equals 4. Line 20 tells the computer to print COMMODORE 64. Line 30 tells the computer to add 1 to the current value of CT. As long as the value of CT remains within the range of 1 to 4, the program repeats, and COMMODORE 64 is PRINTed again. When CT equals 4, line 20 executes one more time. When line 30 again adds 1 to CT, the computer knows that CT is now out of range. So the computer stops executing the loop, and the program ends by itself. To make sure you understand how the FOR/NEXT loop works, we'll add more PRINT statements to line 20 that let you keep track of the value of CT. 20 PRINT"COMMODORE 64 ";"COUNT =";CT RUN COMMODORE 64 COUNT = 1 COMMODORE 64 COUNT = 2 COMMODORE 64 COUNT = 3 COMMODORE 64 COUNT = 4 As you can see, the program ends automatically when CT is out of the range set up in the FOR statement. You can increment the value of the variable in a FOR/NEXT statement by values other than 1. All you do is add both the word STEP and the value you want to use to the end of the FOR statement. For example: NEW 10 FOR NB=1 TO 10 STEP .5 This comma tells the computer to print each 20 PRINT NB, value beginning at the first position of 30 NEXT NB the next 10 space zone. RUN 1 1.5 2 2.5 3 3.5 4 4.5 5 5.5 6 6.5 7 7.5 8 8.5 9 9.5 10 NEW 10 FOR A=2 TO 8 STEP 2 20 PRINT A, 30 NEXT A RUN 2 4 6 8 You can also use a FOR/NEXT loop to count backwards. When you do this, make sure your STEP is negative. For example, if you change line 10 to this: 10 FOR A=8 TO 2 STEP -2 Here's how the output looks: RUN 8 6 4 2 4.7. USING IF/THEN STATEMENTS TO CONTROL PROGRAMS An IF/THEN statement is another way to control program execution. This statement tells the computer to check IF a condition is true. IF that condition is true, the instructions after the word THEN execute. IF that condition is false, the program goes on to the next line without following the instructions in the THEN statement. For example: 10 X = 60 20 X = X + 1 30 IF X = 64 THEN PRINT "GOT IT": END 40 GOTO 20 You can use an IF statement to start a loop or to decide whether certain parts of program will execute. For example: 10 A = 0 20 IF A <= 8 THEN 40 30 END 40 ? "FRODO LIVES ";A 50 A = A + 2 60 GOTO 20 RUN FRODO LIVES 0 FRODO LIVES 2 FRODO LIVES 4 FRODO LIVES 6 FRODO LIVES 8 In this example, the IF/THEN statement in line 20 tells the computer to check the current value of A. IF A is equal to or less than 8, THEN the program skips line 30 and continues RUNning at line 40. IF A is more than 8, in other words, IF the condition in line 20 is false, the computer ignores the instructions after the THEN statement. IF line 20 is false, THEN line 30 is executed. Line 40 PRINTs the message and the current value of A. Line 50 adds 2 to the value of A each time the loop RUNs. As soon as A becomes 10, line 20 becomes false, line 30 becomes true, and the program ends immediately. You can use any of these relational operators in IF/THEN statements: SYMBOL MEANING < Less than > Greater than = Equal to < > Not equal to > = Greater than or equal to < = Less than or equal to 5. ADVANCED BASIC The next few chapters are for people who are familiar with BASIC programming language and the concepts necessary to write advanced programs. Those of you who are just starting to learn how to program may find some of the information too technical to understand completely. But you'll find some simple examples that are written for new users in two chapters, SPRITE GRAPHICS and CREATING SOUND. These examples will give you a good idea of how to use the sophisticated graphics and sound capabilities available on your 64. If you want to learn more about writing programs in BASIC, check the bibliography in the back of this manual (Appendix N). If you are already familiar with BASIC programming, the following chapters will help you get started with advanced BASIC programming techniques. You'll find extensive information about advanced programming in the COMMODORE 64 PROGRAMMER'S REFERENCE GUIDE, which is available through your local Commodore dealer. 5.1. SIMPLE ANIMATION You can use some of the 64's graphic capabilities by putting together what you've learned so far in this manual, along with a few new concepts. Try entering the following program to see what you can do with graphics. Notice that you can include cursor controls and screen commands within a PRINT statement. When you see something like (CRSR left) in a program listing, hold down the key and press the key. The screen shows the graphic representation of a cursor left, which is two vertical reversed bars. The graphic representation of the SHIFTed key is a reversed heart. _____________ NEW / \ 10 REM BOUNCING BALL /| ":" INDICATES | 20 PRINT "{CLR/HOME}" / | NEW COMMAND | /--------------------/ \_____________/ 25 FOR X=1 to 10: PRINT "{CRSR DOWN}": NEXT 30 FOR BL=1 to 40 40 PRINT" O{CRSR LEFT}";: REM (O is a SHIFT-Q) \---------------------\ _______________ 50 FOR TM=1 TO 5 \ / \ 60 NEXT TM \ _____| THESE SPACES | 70 NEXT BL / | ARE INTENTIONAL | 75 REM MOVE BALL RIGHT TO LEFT / \_______________/ 80 FOR BL=40 TO 1 STEP -1 / /--------------------/ 90 PRINT" {CRSR LEFT}{CRSR LEFT}O{CRSR LEFT}"; 100 FOR TM=1 TO 5 110 NEXT TM 120 NEXT BL 130 GOTO 20 +-----------------------------------------------------------------------+ | TIP: | | All words in this text will be completed on one line. However, as | | long as you don't hit your 64 will automatically move to the | | next line even in the middle of a word. | +-----------------------------------------------------------------------+ When this program RUNs, it displays a bouncing ball moving across the screen from left to right and back again. Take a close look at the program to see how this is done. NEW 10 REM BOUNCING BALL +---------> 20 PRINT "{CLR/HOME}" | +------> 25 FOR X=1 to 10: PRINT "{CRSR DOWN}": NEXT | | 30 FOR BL=1 to 40 | | 40 PRINT" O{CRSR LEFT}";: REM (O is a SHIFT-Q) | | +---> 50 FOR TM=1 TO 5 | | +---- 60 NEXT TM | + ------ 70 NEXT BL | 75 REM MOVE BALL RIGHT TO LEFT | + -----> 80 FOR BL=40 TO 1 STEP -1 | | 90 PRINT" {CRSR LEFT}{CRSR LEFT}O{CRSR LEFT}"; | | +---> 100 FOR TM=1 TO 5 | | +---- 110 NEXT TM | +------- 120 NEXT BL +---------- 130 GOTO 20 Line 10 is a REMark that tells you what the program does. A REMark statement has no effect on the program itself. Line 20 clears the screen. Line 25 PRINTs ten cursor-down commands. This just positions the ball in the middle of the screen. Without this line, the ball would move across the top line of the screen. Line 30 sets up a loop to move the ball 40 columns from left to right. Line 40 does three things: 1. PRINTs a space to erase the previous ball positions. 2. PRINTs the ball. 3. Performs a cursor-left to get ready to erase the current ball position again. Line 50 and 60 set up a loop that slows down the ball's movement. Without this loop, the ball would move too fast for you to see clearly. Line 70 completes the loop set up in line 30 to PRINT balls on the screen. Each time the loop executes, the ball moves another space to the right. As you can see from the illustration, the program contains a loop within a loop. You can include up to ten loops within a loop. The only time you get in trouble is when the loops cross over each other. The loops have to be NESTED inside each other. In other words, if you start loop A and then start loop B inside loop A, you must finish loop B (the inside loop) first. A maximum of nine loops may be nested in this way. When you're writing a program with loops, it's a good idea to draw arrows from the beginning to the end of the loops. If your loops cross, the computer can't figure out what you want, so it can't execute your program. Lines 80 through 120 just reverse the steps in the first part of the program, and move the ball from right to left. Line 90 is slightly different from line 40 because the ball is moving in the opposite direction, and you have to erase the ball to the right and move to the left. Line 130 sends the program back to line 20 to start the whole process over again. For a variation on the program, change line 40 to read: 40 PRINT "(SHIFT-Q)" Run the program and see what happens now. Because you left out the cursor control, each ball remains on the screen until it is erased by the ball moving right to left in the second part of the program. 5.2. INPUT Up to now, everything in a program has been set up before the program RUNs. Once you executed the program, you couldn't change or add anything. The INPUT statement lets you send information to a program WHILE it is RUNning. Not only does the program act on this information you supply, but the program won't continue until you supply it. To get an idea of how INPUT works, type NEW, press , and enter this short program. 10 INPUT A$ 20 PRINT "YOU TYPED ";A$ 30 PRINT 40 IF A$ = "STOP" THEN END 50 GOTO 10 _________ RUN / \ ? GO ----------------------------------| YOU TYPED | YOU TYPED GO / \_________/ ? CONTINUE ----------------------/ YOU TYPED CONTINUE / ? STOP ----------------------/ YOU TYPED STOP Here's what happens in this program: Line 10 tells the computer to display a question mark to prompt you to INPUT a value for A$, and to wait until you supply the value before continuing the program execution. Line 20 PRINTs a message and the INPUT value, and line 30 PRINTs a blank line. Line 40 tells the computer to end the program immediately IF the value you INPUT for A$ is STOP. Line 50 returns the program to line 10 so you can INPUT another value. IF line 40 is true because the last value you INPUT for A$ was STOP, then line 50 isn't executed. You can INPUT numeric or string variables, and you can have the INPUT statement print a message along with a question mark to describe the kind of INPUT the computer is waiting for. For example, here's what happens when you add a prompt message to line 10 of the previous example: 10 INPUT "KEEP GOING";A$ Prompt message can't be more than 38 RUN characters KEEP GOING? GO YOU TYPED GO KEEP GOING? STOP YOU TYPED STOP Here's a more complex example that demonstrates a lot of what's been presented so far, including the INPUT statement. NEW 1 REM TEMPERATURE CONVERSION PROGRAM 5 PRINT "(SHIFT-CLR/HOME)" 10 PRINT "CONVERT FROM FAHRENHEIT OR CELSIUS (F/C): ": INPUT A$ 20 IF A$ = "" THEN 10 30 IF A$ = "F" THEN 100 40 IF A$ <> "C" THEN 10 50 INPUT "ENTER DEGREES CELSIUS: ";C 60 F = (C*9)/5+32 70 PRINT C;" DEG. CELSIUS ="; F ;"DEG. FAHRENHEIT" 80 PRINT 90 GOTO 10 100 INPUT "ENTER DEGREES FAHRENHEIT: ";F 110 C = (F-32)*5/9 120 PRINT F;" DEG. FAHRENHEIT ="; C ;"DEG. CELSIUS" 130 PRINT 140 GOTO 10 Line 10 uses the INPUT statement to print a prompt message and to wait for you to type in a value for A$. Lines 20, 30 and 40 check what you typed in and tell the computer where to go next. Line 20 tells the computer to go back to line 10 and ask for INPUT again IF nothing was typed in (IF just was pressed). Line 30 tells the computer to go straight to line 100 and perform the Fahrenheit-to-Celsius conversion IF the value you typed for A$ is F. Line 40 checks to be sure that you haven't typed in anything beside F or C. IF you have, line 40 ends the program. IF you typed in a C, the computer automatically moves to line 50 to perform the Celsius-to- Fahrenheit conversion. It may seem like too much detail to include all these IF statements to check what you INPUT. But this is a good programming practice that can spare you a lot of frustration. You should always try to be sure that your program takes care of all possibilities. Back to the example: once the program knows what type of conversion to make, the calculations are made. Then the program PRINTs the temperature you entered and the converted temperature. The calculation this program performs is just straight math, using the standard formula for temperature conversion. After the calculation finishes and the answer is PRINTed, the program loops back and starts over. Here's a sample execution of this program: CONVERT FROM FAHRENHEIT OR CELSIUS (F/C): ? F ENTER DEGREES FAHRENHEIT: 32 32 DEG. FAHRENHEIT = 0 DEG. CELSIUS CONVERT FROM FAHRENHEIT OR CELSIUS (F/C): ? After you RUN this program, you might want to save it on disk. This program, as well as others in this manual, can form part of your program library. 5.3. USING THE GET STATEMENT FOR DATA INPUT GET lets you input one character at a time from the keyboard without pressing the key. This really speeds up entering data in many cases. When you RUN a program that has a GET statement, whatever key you press is assigned to the variable you include in the GET statement. Here's an example: 1 PRINT "(SHIFT-CLR/HOME)" 10 GET A$: IF A$ = "" THEN 10 No space between quotes 20 PRINT A$; 30 GOTO 10 Line 1 clears the screen. Line 10 lets you type in any key on the keyboard. In effect, the loop in line 10 tells the computer to wait until you type in a key before moving to line 20. Line 20 displays the keys you type on the screen. Line 30 sends the program back to GET another character. It's important to remember that the character you type in won't be displayed unless you PRINT it to the screen, as we've done in line 20. The IF statement in line 10 is very important. GET continually works, even if you don't press a key (unlike INPUT, which waits for your response), so the second part of line 10 continually checks the keyboard until you hit a key. Try leaving out the second part of line 10 and see what happens. To stop this program, press the and keys. You can easily rewrite the beginning of the temperature conversion program to use GET instead of INPUT. If you've SAVEd this program, LOAD it and change lines 10 and 20 like this: 10 PRINT "CONVERT FROM FAHRENHEIT OR CELSIUS (F/C)" 20 GET A$: IF A$ = "" THEN 20 This change makes the program operate more smoothly because nothing happens unless you type in one of the two responses (F or C) that selects the type of conversion. If you want to keep the program, be sure to SAVE it again. 5.4. USING GET TO PROGRAM FUNCTION KEYS As you'll recall from an earlier chapter, we told you that the keys on the right side of the keyboard (F1 through F8) are function keys that you can program to perform a variety of tasks. Here's how to program a function key: 1. Use a GET statement to read the keyboard. 2. Use IF statements to compare the key you press to the CHR$ code for the function key you want to use. Every character on the keyboard has a unique CHR$ number. For example, the CHR$ code of F1 is 133. Appendix F lists the CHR$ code for all keys. 3. Use THEN statements to tell the computer what you want the function key to do. When you RUN the program, all you do is press a function key you programmed, and the key will follow the instructions you gave it in the THEN statement. For example: 10 GET A$: IF A$ = "" THEN 10 20 IF A$ = CHR$(137) THEN PRINT CHR$(14) 30 IF A$ = CHR$(134) THEN PRINT "YOURS TRULY" Line 10 tells the program to assign the key you press to the variable A$. As you'll recall from the previous example, the loop in line 10 continually checks the keyboard for input. Line 20 programs function key 2, CHR$(137). Line 20 tells the computer to make A$ equal to CHR$(14) if you press function key 2. CHR$(14) is the switch from upper to lower case letters on the keyboard. When you RUN this program, you'll see that the characters on the screen immediately make this switch if you press F2. Line 30 programs function key 3, CHR$(134). Line 30 tells the computer to make A$ equal to the character string YOURS TRULY and CHR$(13) if you press F3 during program execution. CHR$(13) is the code for the key. THE CHR$ codes for the function keys are: F1 = CHR$(133) F2 = CHR$(137) F3 = CHR$(134) F4 = CHR$(138) F5 = CHR$(135) F6 = CHR$(139) F7 = CHR$(136) F8 = CHR$(140) The COMMODORE 64 PROGRAMMER'S REFERENCE GUIDE has more information about programming function keys. You can purchase this extensive guide from your local Commodore dealer. 5.5. RANDOM NUMBERS AND OTHER FUNCTIONS The 64 also has built-in functions that you can use to perform special tasks. Functions are like built-in programs included in BASIC. The great advantage of these built-in functions is that you don't have to type in a number of statements every time you want to perform a specialized calculation. Instead, all you do is type the command for the function you want and the computer does all the rest. These built-in functions include figuring square roots (SQR), finding out the contents of a memory location (PEEK), generating random numbers (RND), etc. Appendix C lists all the functions available on your computer. One function you can have a lot of fun with is the random number function, RND. If you want to design a game or an educational program, you'll often need to be able to program your computer to make up random numbers. For example, you'd need to do this to simulate the tossing of dice. Of course you could write a program that would generate these random numbers, but it's much easier to be able to do this just by calling upon the prewritten RaNDom number function. To see how RND works, try this short program: NEW 10 FOR X = 1 TO 10 20 PRINT RND(1), IF YOU LEAVE OUT THE COMMA, YOUR 30 NEXT LIST OF NUMBERS APPEARS AS 1 COLUMN When you RUN this program, the screen displays: .789280697 .664673958 .256373663 .0123442287 .682952381 3.90587279E-04 .402343724 .879300926 .158209063 .245596701 Your numbers don't match? It would be incredible if they did because the program generates a completely random list of ten numbers. If you RUN the program a few more times, you'll see that the results are always different. Though the numbers don't have a pattern, you'll notice a few consistencies about the list the program displays. For one thing, the results are always between 1 and 0, but never equal to 1 or 0. For another, the numbers are real numbers (with decimal points). Now, we started out to simulate dice tosses, and the results from this program aren't exactly what we're looking for. Now we'll add a few more features to this program to get what we want. First, add this line to the program to replace line 20, and RUN the program again: 20 PRINT 6*RND(1), RUN 3.60563664 4.52687513 5.48602315 1.09650123 3.10045018 4.39052168 3.91302584 5.06321506 2.32056144 4.10781302 Now we've got results larger than 1, but still have real numbers. To solve this, we'll use another function. The INT function converts real numbers to integer (whole) numbers. So try replacing line 20 again: 20 PRINT INT(6*RND(1), RUN 2 3 1 0 2 4 5 5 0 1 Now we're even closer to our goal, but you'll notice that the numbers range from 0 to 5, not 1 to 6. So as a final step, we'll replace line 20 again: 20 PRINT INT(6*RND(1))+1 Now when you RUN the program, you'll get the results you want. When you want to generate a range of real numbers instead of whole numbers, the formula is slightly different because you must subtract the lower limit of the range from the upper limit. For example, you can generate random numbers between 1 and 25 by typing: 20 PRINT RND(1)*(25-1)+1 The general formula for generating random numbers in a certain range is: NUMBER = RND(1) * (UPPER LIMIT - LOWER LIMIT) + LOWER LIMIT 5.6. GUESSING GAME Here's a game that uses random numbers. This game not only uses the RND function, but it also introduces some additional programming theory. When you RUN this program, the computer generates a random number, NM, whose value you'll try to guess in as few turns as possible. ______________ NEW / \ 1 REM NUMBER GUESSING GAME ___________| INDICATES NO | 2 PRINT "(CLR/HOME)" / | SPACE AFTER | 5 INPUT "ENTER UPPER LIMIT FOR GUESS "; LI | QUOTATION MARK | 10 NM = INT(LI*RND(1))+1 \______________/ 15 CN = 0 20 PRINT "I'VE GOT THE NUMBER.": PRINT 30 INPUT "WHAT'S YOUR GUESS "; GU 35 CN = CN + 1 40 IF GU > NM THEN PRINT "MY NUMBER IS LOWER." : PRINT : GOTO 30 50 IF GU < NM THEN PRINT "MY NUMBER IS HIGHER.": PRINT : GOTO 30 60 IF GU = NM THEN PRINT "GREAT! YOU GOT MY NUMBER" 65 PRINT "IN ONLY"; CN ;"GUESSES." : PRINT 70 PRINT "DO YOU WANT TO TRY ANOTHER (Y/N)?" 80 GET AN$ : IF AN$ = "" THEN 80 90 IF AN$ = "Y" THEN 2 100 IF AN$ <> "N" THEN 70 110 END You can specify how large the number will be at the start of the program. Then, it's up to you to guess what the number is. A sample run follows along with an explanation. ENTER UPPER LIMIT FOR GUESS? 25 I'VE GOT THE NUMBER. WHAT'S YOUR GUESS ? 15 MY NUMBER IS HIGHER. WHAT'S YOUR GUESS ? 20 MY NUMBER IS LOWER. WHAT'S YOUR GUESS ? 19 GREAT! YOU GOT MY NUMBER IN ONLY 3 GUESSES. DO YOU WANT TO TRY ANOTHER (Y/N)? The IF/THEN statement (lines 40-60) compare your guess to the random number (NM) generated by line 10. If your guess is wrong, the program tells you whether your guess is higher or lower than NM. Each time you make a guess, line 35 adds 1 to CN. CN is a counter that keeps track of how many guesses you take to get the right number. The purpose of this game, of course, is to guess the number in as few tries as possible. When you get the right answer, the program displays the message, GREAT! YOU GOT MY NUMBER, and tells you how many guesses you took. Remember that the program creates a new random number each time you play the game. You might want to add a few lines to the program that also specify the lower range of numbers generated by this game. +-----------------------------------------------------------------------+ | PROGRAMMING TIPS: | | In lines 40 and 50, a colon separates multiple statements on a | | single line. This not only saves typing time. but it also conserves | | memory space. | | Also notice that the IF/THEN statements in these two lines PRINT | | something before branching to another line. | +-----------------------------------------------------------------------+ 5.7. YOUR ROLL The following program simulates the throw of two dice. You can play this little game by itself, or use it as part of a larger game. 5 PRINT "CARE TO TRY YOUR LUCK?" 10 PRINT "RED DICE = "; INT(RND(1)*6)+1 20 PRINT "WHITE DICE = "; INT(RND(1)*6)+1 30 PRINT "PRESS SPACE BAR FOR ANOTHER ROLL": PRINT 40 GET A$: IF A$ = "" THEN 40 50 IF A$ = CHR$(32) THEN 10 From what you've learned about BASIC and random numbers, see if you can follow what's going on in this program. As you may recall from the section on programming the function keys, CHR$(32) is the character string code for the space bar. 5.8. RANDOM GRAPHICS As a final note on random numbers, and as an introduction to designing graphics, try entering and RUNning this program: 10 PRINT "(SHIFT-CLR/HOME)" 20 PRINT CHR$(205.5 + RND(1)); 30 GOTO 20 The function CHR$ (CHaracter String) gives you a character, based on a standard code number from 0 to 255. Every character the 64 can print is encoded this way. Appendix F lists the CHR$ codes for all keys. A quick way of finding out the code for any character is to use the function ASC (for the standard ASCII code). Type: PRINT ASC("X") X is the character you're checking. X can be any printable character, including graphics characters. You must enclose the character in quotation marks. Here's an example: PRINT ASC("G") 71 The CHR$ function is the opposite of ASC. PRINT CHR$(71) G If you type: PRINT CHR$(205);CHR$(206) the computer displays the two right side graphics on the M and N keys, which are the characters used in the little maze program you just tried. The formula 205.5 + RND(1) tells the computer to pick a random number between 205.5 and 206.5. There is fifty-fifty chance that the random number will be above or below 206. CHR$ ignores fractional values, so half the time the character with code 205 is printed, and the rest of the time code 206 is displayed. You can experiment with this program by adding or subtracting a couple of tenths from 205.5. This gives either character a greater chance of being displayed. 6. COLOR AND GRAPHICS 6.1. HOW TO USE COLOR AND GRAPHICS ON YOUR COMPUTER So far this book has presented some of the sophisticated computing capabilities of your 64. But one of the most exciting features of your new computer is its outstanding ability to produce 16 different colors and a lot of different graphics. You've already seen a very simple demonstration of the graphics in the bouncing ball program and in the maze program at the end of the last chapter. This chapter introduces you to new concepts that explain graphic and color programming, and that suggest ideas for creating your own games and advanced animation. 6.2. PRINTING COLORS When you tried the color alignment test in Chapter 1, you discovered that you can change text colors by simply holding down the key and pressing one of the color keys. The 64 offers a full range of 16 colors. Though only eight colors are printed on the color keys, you can get eight more by holding down the key and pressing a color key. Here's a list of the colors: KEYBOARD COLOR DISPLAY KEYBOARD COLOR DISPLAY --------------------------------------------------------------------- <1> BLACK <1> ORANGE <2> WHITE <2> BROWN <3> RED <3> LT. RED <4> CYAN <4> GRAY 1 <5> PURPLE <5> GRAY 2 <6> GREEN <6> LT. GREEN <7> BLUE <7> LT. BLUE <8> YELLOW <8> GRAY 3 When we showed you the bouncing ball program in the last chapter, you saw that keyboard commands, such as cursor movement, can be written into PRINT statements. In the same way you can also add text color changes to your programs. Type NEW and try experimenting with changing colors. Hold down the key and at the same time press the <1> key. Now release both keys and press the key. Now hold down the key again and press the <2> key. Release the key and type the key. Move through the numbers, alternating with the letters, and type out the word RAINBOW like this: 10 PRINT " R A I N B O W" ^ ^ ^ ^ ^ ^ ^ <1 2 3 4 5 6 7> You'll recall that cursor controls appear as graphic characters in the PRINT statement. Color controls are also represented as graphic characters. The color chart printed above shows the graphic characters that appear with each color. Because of the graphic characters that are displayed when you select color keys, your PRINT statement will look strange, but when you RUN the program, you'll see that only the text of the message is displayed. The letters in the message automatically change colors according to the color controls you placed in the PRINT statement. Now try making up some examples of your own, mixing any number of colors within a single PRINT statement. Don't forget the second set of colors that you can get by holding down the key while you press a color key. +-----------------------------------------------------------------------+ | TIP: | | After you RUN a program with color or mode (reverse) changes, | | you'll notice that the READY prompt and any additional text you key | | in is the same as the last color or mode change you made. To get back | | to the normal display, press these keys together: | | RUN/STOP and RESTORE | +-----------------------------------------------------------------------+ 6.3. COLOR CHR$ CODES Before you start reading this section, take a look at Appendix F, which lists the CHR$ codes for all keys on the keyboard. As you looked over the list of CHR$ codes, you probably noticed that each color has a unique code, just like all the other keys and the keyboard controls. If you print the codes themselves by using the CHR$ function mentioned in the last chapter, you can get the same results you got by typing or and the color key in a PRINT statement. For example, try this: NEW 10 PRINT CHR$(147): REM 20 PRINT CHR$(28);"CHR$(28) CHANGES ME TO?" RUN CHR$(28) CHANGES ME TO? When you RUN this program, the screen clears before the message in line 20 is PRINTed. The text should be red now. In many cases, you'll find that it's much easier to use the CHR$ function to change colors, especially if you want to experiment. The next page shows another way to get a rainbow of colors. There are a number of similar lines in the program (40 through 110), so use the editing keys to spare yourself a lot of typing. See the notes at the end of the program listing to refresh your memory on editing procedures. NEW 1 REM AUTOMATIC COLOR BARS 5 PRINT CHR$(147): REM CHR$(147) = CLR/HOME 10 PRINT CHR$(18); " ";: REM REVERSE BAR 20 CL = INT(8*RND(1))+1 30 ON CL GOTO 40,50,60,70,80,90,100,110 40 PRINT CHR$(5);: GOTO 10 50 PRINT CHR$(28);: GOTO 10 60 PRINT CHR$(30);: GOTO 10 70 PRINT CHR$(31);: GOTO 10 80 PRINT CHR$(144);: GOTO 10 90 PRINT CHR$(156);: GOTO 10 100 PRINT CHR$(158);: GOTO 10 110 PRINT CHR$(159);: GOTO 10 Type lines 1 through 40 normally. Your display should look like this: 1 REM AUTOMATIC COLOR BARS 5 PRINT CHR$(147): REM CHR$(147) = CLR/HOME 10 PRINT CHR$(18); " ";: REM REVERSE BAR 20 CL = INT(8*RND(1))+1 30 ON CL GOTO 40,50,60,70,80,90,100,110 40 PRINT CHR$(5);: GOTO 10 _ EDITING NOTES: Use the key to position the cursor on line 40. Then type 5 over the 4 of 40. Now use the key to move over to the 5 in the CHR$ parentheses. Press and to open up a space, and key in 28. Now just press with the cursor anywhere on the line. The display should look like this now: NEW 1 REM AUTOMATIC COLOR BARS 5 PRINT CHR$(147): REM CHR$(147) = CLR/HOME 10 PRINT CHR$(18); " ";: REM REVERSE BAR 20 CL = INT(8*RND(1))+1 30 ON CL GOTO 40,50,60,70,80,90,100,110 50 PRINT CHR$(28);: GOTO 10 Don't worry about line 40; it's still there, as you can see by LISTing the program. Follow the same steps to modify line 40 with a new line number and CHR$ code until you've entered all the remaining lines. As a final check, LIST the entire program to make sure all the lines are right before you RUN it. You probably understand the color bar program except for line 30. Here's a brief explanation of how this program works. Line 5 prints the CHR$ code for . Line 10 turns on reverse type and prints 5 spaces, which turn out to be a bar since they're reversed. The first time through the program, the bar is light blue, the normal screen display color. Line 20 uses the random function to select at random a color between 1 and 8. Line 30 uses a variation of the IF/THEN statement, called ON/GOTO, which lets the program choose from as list of line numbers where the program will go next. If the ON variable (in this case CL) has a value of 1, the program goes to the first line number listed (here it's line 40). If the variable has a value of 2, the program goes to the second line listed, and so on. Lines 40 through 110 just convert the random key colors to the appropriate CHR$ code for that color and return the program to line 10 to PRINT a section of the bar in that color. Then the whole process starts again. See if you can figure out how to produce 16 random colors. Expand ON/GOTO to handle the additional colors and add the remaining CHR$ codes. 6.4. HOW TO USE PEEKS AND POKES PEEKS and POKES let you search around inside your computer's memory and stick things in exactly where you want them. You'll recall that in Chapter 4 we explained variables as being like little slots in the computer's memory, with the variable name as the slot's address. Well, imagine some more specially defined slots in the computer that stand for specific memory locations and that have numbers for addresses. Your 64 looks at these memory locations to see what the screen's background and border colors should be, what characters to display on the screen and where to display them, etc. You can change the screen colors, define and move objects, and even create music by POKEing a different value into the specific memory slots. Imagine some memory slots looking something like this: +-----------+ +-----------+ +-----------+ +-----------+ | 53280 | | 53281 | | 53282 | | 53283 | | 2 | | 1 | | | | | +-----------+ +-----------+ +-----------+ +-----------+ BORDER BACKGROUND COLOR COLOR The first two slots are the memory locations for the border and background colors on your screen. We've put 2, the value for RED in the border color box, and 1, the value for WHITE in the background color box. Now try typing this: POKE 53281,7 The background color of your screen will change to yellow because we put the value 7, for yellow, in the location that controls background color. Try POKEing different values into the background color location and see what result you get. Here's a list of the values to POKE for each color available on your 64: 0 BLACK 8 ORANGE 1 WHITE 9 BROWN 2 RED 10 light RED 3 CYAN 11 GRAY 1 4 PURPLE 12 GRAY 2 5 GREEN 13 light GREEN 6 BLUE 14 light BLUE 7 YELLOW 15 GRAY 3 Here's a little program that you can use to display various border and background color combinations: NEW 10 FOR BA = 0 TO 15 20 FOR BO = 0 TO 15 30 POKE 53280, BO 40 POKE 53281, BA 50 FOR X = 1 TO 2000: NEXT X 60 NEXT BO : NEXT BA RUN This program uses two simple loops to POKE various values to change the background and border colors. Line 50 contains a DELAY loop, which just slows the program down a little bit. If you're curious about what value is currently in the memory location for background color, try this: ? PEEK (53280) AND 15 PEEK looks at a whole byte, but colors only use half a byte, called a nybble. To PEEK just this nybble, you have to add the AND 15 to your PEEK statement. If you used this PEEK after RUNning the previous program, you'd get 15 as the answer because the last border color POKEd was GRAY 3, which is 15. In general, PEEK lets you see what value is currently in a specific memory slot. Try adding this line to your program to display the values of BORDER and BACKGROUND as the program RUNs. 25 PRINT CHR$(147); "BORDER = "; PEEK(53280) AND 15, "BACKGROUND = "; PEEK(53281) AND 15 6.5. SCREEN GRAPHICS So far when you've PRINTed information, the computer has handled the information sequentially: one character PRINTed after the next, starting from the current cursor position, except when you asked for a new line, or used a comma in PRINT formatting. You can PRINT data in a particular place by starting from a known place on the screen and PRINTing the correct number of cursor controls to format the display. But this takes time and program steps. But just as there certain locations in the 64's memory to control color, there are also memory locations that you can use to control screen locations. 6.6. SCREEN MEMORY MAP The 64's screen can hold 1000 characters (40 columns by 25 lines), so there are 1000 memory locations set aside to represent what is on the screen. Imagine the screen as a grid, 40 by 25, with each square standing for one memory location. Each memory location can contain one of the 256 different characters the 64 can display (see Appendix E). Each of these 256 characters is represented by a number from 0 to 255. If you POKE the value for a character into a specific screen memory location, that character will be displayed in that specific screen location. Here's a grid that represents your screen, complete with the numbers of each screen memory location. COLUMN 1063 0 10 20 30 39 / +------------------------------------------------------------/ 1024 | | 0 1064 | | 1104 | | 1144 | | 1184 | | 1224 | | 1264 | | 1304 | | 1344 | | 1384 | | 1424 | | 10 1464 | | 1504 | | ROW 1544 | | 1584 | | 1624 | | 1664 | | 1704 | | 1744 | | 1784 | | 1824 | | 20 1864 | | 1904 | | 1944 | | 1984 | | 24 +------------------------------------------------------------\ \ 2023 The 64's screen memory normally begins at memory location 1024 and ends at location 2023. Location 1024 is the upper left corner of the screen. Location 1025 is the position of the next character to the right, and so on. Location 1063 is the right-most position of the first row. Following the last character in a row, the next location is the left-most character on the next row down. Suppose you want to control a ball bouncing on the screen. The ball is in the middle of the screen, column 29, row 12. The formula for calculating the memory location on the screen is: POINT = 1024 + X + 40 * Y <---- row ^--------- column where X is the column and Y is the row. Therefore, the memory location of the ball is: POINT = 1024 + 20 + 480 <-- row (40x12) POINT = 1524 ^------- column Clear the screen with and and type: POKE 1524,81 <--- character code ^------ location This POKE statement makes a ball appear in the middle of the screen. You have placed a character directly into screen memory without using the PRINT statement. However, you can't see the ball yet because it's the same color as the screen background. 6.7. COLOR MEMORY MAP You can change the color of the ball that appeared by altering another range of memory. Type: POKE 55796,2 <--- color ^---- location This changes the ball's color to red. Every spot on the 64's screen has TWO memory locations: one for the character code, and one for the color code. The color memory map begins at location 55296 (upper left corner), and continues on for 1000 locations. You use the same color codes, 0 through 15, that you used to change border and background colors, to directly change character color. We can modify the formula for calculating screen memory locations to give us the locations to POKE colors. Here's the new formula: COLOR PRINT = 55296 + X + 40 * Y <--- row ^--------- column 6.8. MORE BOUNCING BALLS Here's a revised bouncing ball program that directly prints on the screen using POKEs rather than cursor controls within PRINT statements. When you RUN this version, you'll see that it's much more flexible than the earlier program and it leads up to programming more sophisticated animation. NEW 10 POKE 53281,1: PRINT"" 20 POKE 53280,7: POKE 53281,6 30 X = 1 : Y = 1 40 DX = 1 : DY = 1 50 POKE 1024 + X + 40 * Y, 81 60 FOR T = 1 TO 10 : NEXT 70 POKE 1024 + X + 40 * Y, 32 80 X = X + DX 90 IF X <= 0 OR X >= 39 THEN DX = -DX 100 Y = Y + DY 110 IF Y <= 0 OR Y >= 24 THEN DY = -DY 120 GOTO 50 Line 10 sets the cursor color to white and then clears the screen. NOTE: Clearing the screen on (NTSC) 64s sets the color RAM to white but on (PAL) 64s the color RAM is set to the current background color (here white). Line 20 sets the background color to blue and the border color to yellow. The X and Y variables in line 30 keep track of the ball's current row and column position. The DX and DY variables in line 40 are the horizontal and vertical direction of the ball's movement. When a +1 is added to the value of X, the ball moves to the right; when -1 is added, the ball moves to the left. A +1 added to Y moves the ball down a row, and a -1 added to Y moves the ball up a row. Line 50 puts the ball on the screen at the current X,Y position. Line 60 is a delay loop, which is included to keep the ball on the screen long enough for you to be able to see it. Line 70 erases the ball by putting a space (code 32) where the ball was on the screen. Line 80 adds the direction factor to X. Line 90 tests to see if the ball has reached one of the side walls, and reverses the ball's direction if there's a bounce. Lines 100 and 110 do the same thing for the top and bottom walls. Line 120 sends the ball back to display and moves the ball again. You can change the ball to any other character by changing the code in line 50 from 81 to another character code. If you change DX or DY to 0 the ball bounces straight instead of diagonally. We can also add a little intelligence to the bouncing ball program. So far the only thing you checked for is whether the ball is going out of bounds on the screen. Try adding the following lines to the program: 21 FOR L = 1 TO 10 25 POKE 1024 + INT(RND(1)*1000), 160 <---(REVERSE SPACE) 27 NEXT L 115 IF PEEK(1024 + X + 40*Y) = 166 THEN DX = -DX : GOTO 80 Lines 21 to 27 put ten blocks on the screen in random positions. Line 115 PEEKs to see if the ball is about to bounce into a block, and, if so, it changes the ball's direction. 7. INTRODUCTION TO SPRITES In previous chapters, we've shown you how to use graphic symbols in PRINT statements to create animation and other visual effects. In chapter 6, we also showed you how to POKE character codes in specific screen memory locations, which put characters directly on the screen in the place you selected. In both of these cases, you have to create objects from existing graphic symbols, so these methods take a lot of work. When you want to move the object, you must use a number of program statements to keep track of the object and move it to a new place. And sometimes the shape and resolution of the object isn't as good as you'd like it to be because of the limitations of using graphic symbols. You can eliminate a lot of these problems by using sprites in animated sequences. A sprite is a high-resolution programmable object that you can make into just about any shape by using BASIC commands. All you have to do to move the object is simply tell the computer the position where you'd like the sprite to go. The computer takes care of the rest. But this isn't all you can do with sprites. For example, you can change their color, you can tell if one object collides with another, you can make them go in front and behind each other, and you can easily expand their size. You have to learn a few more details about your 64 and the way it handles numbers before you can use sprites. It's not difficult, though, so just follow the examples and you'll be making your own sprites do amazing things in no time. 7.1. BITS AND BYTES Before you can use sprites it's important that you understand a few general things about how computers work. In the decimal system, we count in "tens" using values of 0-9. When a particular position overflows its maximum value of 9, it re-cycles to zero and carries one to the next (left-hand) position. For example, the number 64 means 6 x (10) + 4 x (1). The position of each digit is important. The value of 64 is calculated as follows: 6 x 10^1 + 4 x 10^0 NOTE: Any number raised to the power of zero equals 1. Computers store information as a series of electrical charges, representing 1s and 0s. Each cell within memory holds a pattern of eight ones and zeros called binary digits or BITS. These cells are called BYTES. A bit, which is the smallest amount of information a computer can store, can be turned ON, giving it a value of 1, or OFF, which has a value of 0. When you enter information into the computer via the keyboard, key depressions are converted into 8 bit patterns of ones and zeros, and transferred to memory. The rules for binary arithmetic are much simpler than other systems since digits can only have two values, 0 or 1. As illustrated in the previous example, the decimal system uses the base of 10, whereas the binary system uses the base of 2. One bit can contain one of two combinations, 0 or 1. There are four possible combinations of 1s and 0s in two bits (2^2) and with three bits, eight possible combinations (2^3). The following illustration shows the range of values. +---------+--------------+----------------------------------------------+ | NO. OF | NO. OF | | | BITS | VALUES | POSSIBLE COMBINATIONS | +---------+--------------+----------------------------------------------+ | 1 | 2^1 | ON 1 | | | = 2 | OFF 0 | +---------+--------------+----------------------------------------------+ | 2 | 2^2 | ON and ON 1 1 | | | = 4 | ON and OFF 1 0 | | | | OFF and ON 0 1 | | | | OFF and OFF 0 0 | +---------+--------------+----------------------------------------------+ | 3 | 2^3 | ON and ON and ON 1 1 1 | | | = 8 | ON and ON and OFF 1 1 0 | | | | ON and OFF and ON 1 0 1 | | | | ON and OFF and OFF 1 0 0 | | | | OFF and ON and ON 0 1 1 | | | | OFF and OFF and ON 0 0 1 | | | | OFF and ON and OFF 0 1 0 | | | | OFF and OFF and OFF 0 0 0 | +---------+--------------+----------------------------------------------+ As you can see, the number of combinations is 2 raised to the power of the number of bits. For one BYTE, or eight bits, you can store 256 different values i.e. 2^8. When all eight bits are OFF, i.e. set to 0, the byte contains a value of zero. When all eight bits are ON, i.e. set to 1, the byte has a value of 255. Note that the combinations range from 0 to 255 inclusive. You may convert any binary number to a decimal value simply by adding those powers of two where a bit has been set. The example below illustrates how a decimal value of 181 is held in binary form: ------------------------------------------------------------------------- BINARY POSITIONS 2^7 2^6 2^5 2^4 2^3 2^2 2^1 2^0 ------------------------------------------------------------------------- DECIMAL EQUIVALENT 128 64 32 16 8 4 2 1 ------------------------------------------------------------------------- BIT VALUES 1 0 1 1 0 1 0 1 ------------------------------------------------------------------------- Adding up the values of the ON bits gives: 2^7 + 2^5 + 2^4 + 2^2 + 2^0 or 128 + 32 + 16 + 4 + 1 = 181 The following is a table showing binary to decimal conversion. A zero indicates that the bit is OFF, and a 1 shows that a bit is ON. To calculate the value of the entire byte, add the decimal value of each ON bit. BINARY TO DECIMAL CONVERSION +-----------------------------------------------------------------------+ | Decimal Value | +-------+-------+-------+-------+-------+-------+-------+-------+-------+ | 128 | 64 | 32 | 16 | 8 | 4 | 2 | 1 | | +-------+-------+-------+-------+-------+-------+-------+-------+-------+ | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 1 | 2^0 | +-------+-------+-------+-------+-------+-------+-------+-------+-------+ | 0 | 0 | 0 | 0 | 0 | 0 | 1 | 0 | 2^1 | +-------+-------+-------+-------+-------+-------+-------+-------+-------+ | 0 | 0 | 0 | 0 | 0 | 1 | 0 | 0 | 2^2 | +-------+-------+-------+-------+-------+-------+-------+-------+-------+ | 0 | 0 | 0 | 0 | 1 | 0 | 0 | 0 | 2^3 | +-------+-------+-------+-------+-------+-------+-------+-------+-------+ | 0 | 0 | 0 | 1 | 0 | 0 | 0 | 0 | 2^4 | +-------+-------+-------+-------+-------+-------+-------+-------+-------+ | 0 | 0 | 1 | 0 | 0 | 0 | 0 | 0 | 2^5 | +-------+-------+-------+-------+-------+-------+-------+-------+-------+ | 0 | 1 | 0 | 0 | 0 | 0 | 0 | 0 | 2^6 | +-------+-------+-------+-------+-------+-------+-------+-------+-------+ | 1 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 2^7 | +-------+-------+-------+-------+-------+-------+-------+-------+-------+ +-----------------------------------------------------------------------+ | TIP: | | Converting binary numbers to their decimal values is the basis for | | creating data to represent and manipulate sprites. Here's a program | | that does these conversions for you. Since you'll be using this | | program often, you should enter and save it. | | | | 5 REM BINARY TO DECIMAL CONVERTER | | 10 INPUT "ENTER 8-BIT BINARY NUMBER :";A$ | | 12 IF LEN(A$) <> 8 THEN PRINT "8 BITS PLEASE..." : GOTO 10 | | 15 TL = 0 : C = 0 | | 20 FOR X = 8 TO 1 STEP -1 : C = C + 1 | | 30 TL = TL + VAL(MID$(A$,C,1))*2^(X-1) | | 40 NEXT X | | 50 PRINT A$; " BINARY = "; TL ;" DECIMAL" | | 60 GOTO 10 | | | | At line 10 you enter a binary number as the string A$. Line 12 uses | | the LEN (length) function to check to be sure you entered 8 binary | | digits. If you didn't, the program asks for more and repeats line 10. | | In line 15, TL keeps track of the binary number's decimal value, | | and C indicates which bit is being worked on as the program goes | | through the loop. | | Line 30 updates the value of TL. Appendix C explains the VAL and | | MID$ functions. | | Line 50 PRINTs the binary and decimal values of the byte. Line 60 | | returns the program to the beginning. | +-----------------------------------------------------------------------+ 7.2. CREATING A SPRITE Sprite Registers Before going any further you need to know a little about how sprites are manipulated by the COMMODORE 64. Sprites are handled by a special chip inside your COMMODORE 64. This is called the VIC II chip. This chip contains a series of special bytes called REGISTERS which are provided specifically for sprite handling. Each register performs a separate function. For example, the ENABLE REGISTER controls whether a sprite is active or inactive, while the EXPAND REGISTERS control the size of a sprite. When you work with sprites, think of a register as a byte with a specific function. The registers we will be talking about in this chapter are listed below: REGISTER No. DESCRIPTION ------------------------------------ 0-15 SPRITE POSITIONING 16 EXTRA MOVEMENT 21 ENABLE (ON/OFF) 23 EXPAND (VERTICAL) 27 PRIORITIES 28 MULTI-COLOR SELECT 29 EXPAND (HORIZONTAL) 37-38 MULTI-COLORS 39-46 COLOR Each of these registers, or bytes, have been assigned a specific location in the memory of the computer. They start at location 53248. This is the 'base address' of the VIC II chip. To access individual registers, it is easier to assign a variable with the value of the start address and then add the register number to it, e.g. V=53248: POKE V+21,255. This will put the value of 255 into register 21. The VIC II chip in your COMMODORE 64 does all the work of creating and keeping track of characters and graphics, creating colors and moving sprites around. All you have to do is to tell the computer the following three details about the sprite: What it should look like What color it should be Where it should appear The VIC II chip contains 46 registers and controls up to 8 sprites at a time. You can design, create and move your sprite by POKEing the appropriate decimal value in the particular memory location. 7.3. DESIGNING A SPRITE A sprite is made up of 504 dots. These are arranged in a 24 dot wide by 21 dot deep grid. As we mentioned earlier, you can use up to 8 sprites at a time, numbered from 0 to 7. Each dot on the sprite corresponds to a bit. In order to design a sprite, you simply set the relevant bit on the grid. Each line on the grid contains 24 bits (three bytes). Each sprite takes up 64 bytes in memory, i.e. 21 multiplied by 3 plus one spare byte. (For the more technically minded, the number 64 is much easier for the VIC II chip to work with because it is a power of 2 and therefore easier to multiply.) Because you can visualize a sprite inside a grid, the design process is greatly simplified. Suppose you want to create a balloon and make it float around the screen. The grid on page 78 shows its shape. You can set up your own grid preferably using lined, or better still, graph paper. Draw a grid that is 21 squares high and 24 squares across. Divide the 24 squares across into 3 sections of 8 spaces. The next step is to convert the graphic design into data the computer can use. Number the 8 squares in each of the three sections 128, 64, 32, 16, 8, 4, 2 and 1. These values are equivalent to 2^7, 2^6, 2^5, 2^4, 2^3, 2^2, 2^1 and 2^0. Number the squares down the left hand side of the page from 1-21 for each row. Now fill in the grid with any design, or use the balloon that we've drawn. It's easier to outline the shape first, then go back and fill in the grid. Think of the squares you have filled in as ON bits, and substitute a 1 for each filled square. Think of the squares that aren't filled as OFF bits, and give them a value of zero. Now look along row 1 and think of each 8 square section as a byte. Convert each section of 8 bits into a decimal value. You can even use your Binary to Decimal converter program if you wish. Now convert each of the 21 rows into 3 decimal values, giving 63 values in all. SERIES |SERIES |SERIES 1 | 2 | 3 | | 1 1 1 2631 2631 2631 842684218426842184268421 +------------------------+ 1 |.........#######........| 2 |.......###########......| 3 |......#############.....| 4 |......#####...#####.....| 5 |.....#####.###..####....| 6 |.....#####.###.#####....| 7 |.....#####.###..####....| 8 |......#####...#####.....| 9 |......#############.....| R 10 |......#############.....| O 11 |......#.#########.#.....| W 12 |.......#.#######.#......| 13 |.......#..#####..#......| 14 |........#..###..#.......| 15 |........#..###..#.......| 16 |.........#..#..#........| 17 |.........#..#..#........| 18 |..........#####.........| 19 |..........#####.........| 20 |..........#####.........| 21 |...........###..........| +------------------------+ 1 1 2 2 1 5 0 5 0 4 COLUMN Now look at the design of the balloon. The first series of 8 squares on the first row are all blank, therefore the bits are all OFF giving a value of zero. The middle series on row 1 looks like this: 00000000 01111111 00000000 The third series of 8 squares on the first row also contains only blanks so it also equals zero. So the data for the first line is: DATA 0, 127, 0 The three series of dots that make up row two are calculated like this: +-----+-----+-----+-----+-----+-----+-----+-----+ Series 1: | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 1 | +-----+-----+-----+-----+-----+-----+-----+-----+ 1 = 1 +-----+-----+-----+-----+-----+-----+-----+-----+ Series 2: | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | +-----+-----+-----+-----+-----+-----+-----+-----+ ^ ^ ^ ^ ^ ^ ^ ^ | | | | | | | | 128 + 64 + 32 + 16 + 8 + 4 + 2 + 1 = 255 +-----+-----+-----+-----+-----+-----+-----+-----+ Series 3: | 1 | 1 | 0 | 0 | 0 | 0 | 0 | 0 | +-----+-----+-----+-----+-----+-----+-----+-----+ ^ ^ | | 128 + 64 = 192 The data for the second row is: DATA 1, 255, 192 Use this method to convert the three series of 8 squares in each of the remaining rows. Once you have completed these calculations, you are ready to write a BASIC program to use the balloon (or any other shape) since the sprite has now been converted into values your computer can understand. To demonstrate the use of sprites, type in the following program: 1 REM UP, UP, AND AWAY 5 PRINT "(CLR/HOME)" 10 V = 53248 : REM START OF DISPLAY CHIP 11 POKE V + 21,4 : REM ENABLE SPRITE 2 12 POKE 2042,13 : REM SPRITE 2 DATA FROM BLOCK 13 20 FOR N = 0 TO 62 : READ Q : POKE 832+N,Q : NEXT +----------------+ 30 FOR X = 0 TO 200 ^------------------------| GETS ITS INFO. | 40 POKE V + 4,X : REM UPDATE X COORDINATES | FROM DATA | 50 POKE V + 5,X : REM UPDATE Y COORDINATES +----------------+ 60 NEXT X 70 GOTO 30 200 DATA 0,127,0,1,255,192,3,255,224,3,231,224 \ +---------------+ 210 DATA 7,217,240,7,223,240,7,217,240,3,231,224 |--| INFO. READ IN | 220 DATA 3,255,224,3,255,224,2,255,160,1,127,64 | | FROM Q | 230 DATA 1,62,64,0,156,128,0,156,128,0,73,0,0,73,0 | +---------------+ 240 DATA 0,62,0,0,62,0,0,62,0,0,28,0 / If you have entered everything correctly, when you type "RUN" and press , your balloon should sail across the screen. At this stage, you will not understand the meaning of much of the program but, as we explain each stage of sprite handling, we will use the program to illustrate each feature. Line numbers 200-240 relate to the definition of your balloon and contain 21 sets of three values, i.e. one set for each row on your design chart. 7.4. SPRITE POINTERS The sprite pointer indicates where you have stored your sprite in memory. The sprite pointers are stored in 8 bytes from location 2040 to 2047 inclusive. The normal location of the pointer for sprite 0 (the first sprite) is 2040; the location for the pointer for sprite 1 is 2041; and so on with location 2047 used as the location of the pointer for sprite 7. Each sprite pointer can contain a value between 0 and 255. This number, multiplied by 64, corresponds to the start address of your sprite data. Since each sprite uses 64 bytes, the sprite pointer can contain a block number anywhere within the first 16K block of memory accessible by the VIC II chip, i.e. 256 * 64. It is also possible to use other 16K blocks. Further details can be found in the COMMODORE 64 Programmer's Reference Guide. NOTE: It is always advisable to store the data for your first sprite at block 255 and then store data for subsequent sprites in the next available blocks working downwards. This will prevent your sprite data from interfering with the BASIC program. If you find that the sprite data is writing over the end of your BASIC program, you must store your sprite data in the next available 16K block of memory or move the BASIC program above the sprite data. Again, details on how to do this can be found in the COMMODORE 64 Programmer's Reference Guide. In the balloon program, line 10: V = 53248 assigns the value of the start address of the VIC II chip to the variable V. Later in the program you can add the register number to the address stored in V. For example line 11: POKE V + 21,4 references register number 21. Line 12 of the balloon program: POKE 2042,255 places the data from sprite 2 into block 255. 7.5. TURNING SPRITES ON Before you see and use your sprites, you must first activate them. You do this by using the SPRITE ENABLE register, register number 21. As mentioned above, line 11 in the balloon program turns on sprite 2. This is done by placing the value 4 in the register. This is 2 to the power of the sprite number 2, i.e. the sprite you are initializing. Refer to the structure of a byte earlier in the chapter if you do not understand how we get this value. If you had wanted to turn on two sprites, you would simply add the decimal values together. For example, to turn on sprites 2 and 3 add 8 and 4 (2^3 + 2^2). The instruction would then be: POKE V + 21,12 +-----------------------------------------------------------------------+ | TIP: | | An easier way to turn on a selected sprite is to use a simple | | calculation that sets the required bit in the SPRITE ENABLE register. | | In the program statement below, SN equals the sprite number (0-7) | | that you want to turn on. | | | | POKE V+21, PEEK(V+21) OR (2^SN) | +-----------------------------------------------------------------------+ 7.6. SPRITE COLORS A sprite can be any of the 16 colors available on your COMMODORE 64. The colors are numbered 0-15. Chapter 6 and Appendix G contain the colors and their codes. As you can see from the VIC II chip Register Map, each sprite has its own color register. Register numbers 39-46 are used for this purpose. Register 39 holds the color for sprite 0, register 40 for sprite 1, and so on with register 46 holding the color for sprite 7. When you see your sprite on the screen, the dots are displayed in the color contained in the color register. The rest of the sprite is transparent and shows whatever color is behind the sprite. If you wanted to change the color of sprite 2 to light green (code number 13), simply POKE the color code in the sprite's color register as follows: POKE V + 41,13 7.7. POSITIONING SPRITES Now you've made a sprite, you want it to appear and move around the screen. To do this your COMMODORE 64 uses three positioning registers: a) Sprite X Positioning Register b) Sprite Y Positioning Register c) Most Significant X Position Register The X and Y Position Registers work together to pinpoint where your sprite appears on the screen. The X Position Register positions the sprite in the horizontal direction and the Y Position Register positions the sprite in the vertical direction. On the VIC II chip register map notice that registers 0-15 are used for the X and Y co-ordinates. The registers are arranged in pairs as follows: Register 0 holds the X co-ordinate for sprite 0 Register 1 holds the Y co-ordinate for sprite 0 Register 2 holds the X co-ordinate for sprite 1 Register 3 holdo the Y co-ordinate for sprite 1 This pattern is repeated with Registers 14 and 15 holding the X and Y co-ordinates for sprite 7. There is a further register (16) which we shall discuss later. You can position your sprite by simply POKEing values into the appropriate registers. You need both X and Y co-ordinates to position your sprite. Calculate all positions from the TOP LEFT of your sprite area. It does not matter how many dots you fill up in the 24 x 21 dots area allocated to your sprite design. The position is still calculated from the top left corner. If you look at the balloon program once again, statement numbers 30-70 use a FOR...NEXT loop to move the balloon diagonally across the screen from left to right. These statements increment the values of the X and Y co-ordinates by POKEing the positions into registers 4 and 5, the registers for sprite 2, until both values reach 200. Line 70 then runs the program again. You may have noticed that when the program was running, the balloon did not move to the far right hand side of the screen. Positioning in the horizontal direction is difficult since you need 320 locations and you therefore need an additional bit, which will then give you up to 512 positions. If you do not understand how we arrived at this figure, think of an extra bit being added to the left hand side of a byte. This would be the equivalent of 2 raised to the power of 8. The extra bits for all sprites are stored in the Most Significant Bit Register (MSB), register 16. Bits 0-7 of this register correspond to sprites 0-7 respectively. If you are not using positions greater than 255, the corresponding extra bit position must be turned off, i.e. it must contain a value of zero. Here's how the MSB works: after you've moved the sprite to X location 255, POKE the sprite's decimal value into register 16. For example, to move sprite 6 to horizontal locations 256 through 320, use this statement: POKE V + 16,64 Then use a loop to move sprite 6 the 64 spaces from location 256 to 320: FOR X = 0 TO 63 : POKE V + 12,X : NEXT The following program revises the original balloon program so that sprite 2 moves all the way across the screen: 10 V = 53248 : POKE V + 21,4 : POKE 2042,13 20 FOR N = 0 TO 62 : READ Q : POKE 832 + N,Q : NEXT 25 POKE V + 5,100 30 FOR X = 0 TO 255 40 POKE V + 4,X 50 NEXT 60 POKE V + 16,4 70 FOR X = 0 TO 63 80 POKE V + 4,X 90 NEXT 100 POKE V + 16,0 110 GOTO 30 Line 60 sets the most significant bit for sprite 2. Lines 70 through 90 contain the loop that moves sprite 2 across screen locations 256 through 320. Line 100 turns OFF the MSB so that sprite 2 can go back to the left edge of the screen. In other words, when the MSB is ON, the sprite can only move from locations 256 through 320. You have to turn the MSB back OFF before you can move the sprite from locations 0 through 255. Note that the program we used for turning on individual sprites can also be used to set a specific MSB. The complementary statement which will turn OFF a specific bit is: POKE V+21, PEEK(V+21) AND (255-2^SN) where SN is the number of the sprite you wish to move. 7.8. EXPANDED SPRITES You can increase the size of each dot of the sprite so that the sprite is twice as wide, twice as deep or expanded in both directions at once. There are two EXPAND registers: Register 23 doubles the width of the sprite Register 29 doubles the height of the sprite The method for expanding sprites is the same as that used when enabling them, e.g. to expand a specific sprite in the X direction only, use the following statement: POKE V+23, PEEK(V+23) OR 2^SN where SN is the number of the sprite you wish to expand. The same applies when doubling the height of a sprite except that this time you use V+29. Try adding the following line to the original balloon program: 25 POKE V + 23,4 : POKE V + 29,4 : REM EXPAND SPRITE When you type "RUN", the balloon has now doubled in size. This is because you POKEd the decimal value for sprite 2 (2^2) into register 23 which doubles the height of the balloon, and into register 29 which doubles the width of the balloon. 7.9. CREATING MORE THAN ONE SPRITE lt is a simple operation to create and store more sprites. Instructions on how to do this are given earlier in this chapter. To add sprite 3 to your screen, include the following lines in the original balloon program: 11 POKE V + 21,12 12 POKE 2042,13 : POKE 2043,13 30 FOR X = 1 TO 190 45 POKE V + 6,X 55 POKE V + 7,190 - X Line 11 turns ON sprites 2 and 3 by POKEing their combined decimal values (4 and 8) into the SPRITE ENABLE register (21). Line 12 tells the computer to find the data for the sprites in block 255 of the VIC II chip memory. Recall that 2042 is sprite 2's pointer and 2043 is the pointer for sprite 3. Lines 45 and 55 move sprite 3 around the screen by changing the values of the X and Y co-ordinate registers of that sprite (V+6 and V+7). When you RUN the program, you will see two balloons moving around the screen. This is because we POKEd the same address into both sprite pointers. The following lines put sprite 4 on the screen too: 11 POKE V + 21,28 12 POKE 2042,13 : POKE 2043,13 : POKE 2044,13 25 POKE V + 23,12: POKE V + 29,12 48 POKE V + 8,X 58 POKE V + 9,100 Line 11 turns ON sprites 2, 3 and 4 by POKEing their combined decimal values (4, 8 and 16) into the SPRITE ENABLE register (21). Line 12 tells the computer to find the data for all three sprites in block 255 of memory. Line 25 doubles the size of sprites 2 and 3 by POKEing their combined value into the registers that control height and width expansion (23 and 29). Line 48 moves sprite 4 halfway along the X axis (horizontally). Line 58 positions sprite 4 halfway down the screen at location 100. Previously, the Y co-ordinate has been changed in the program by the use of a FOR...NEXT loop. (See line 50 in the original program.) But now the value for the Y co-ordinate for sprite 4 (V + 9) stays the same during the program. This means that sprite 4 only moves horizontally. 7.10. SPRITE PRIORITIES If you are using more than one sprite you may wish to make sprites cross over each other on the screen. Sprite to sprite priority is preset. Sprites having the lowest numbers have the highest priority, i.e. sprite 0 has the highest priority, then sprite 1, sprite 2, etc. Sprite 7 has the lowest priority. Sprites with higher priorities appear in front of sprites with lower priorities. Sprite to background priority is controlled by the SPRITE BACKGROUND PRIORITY register, register 27. Bits 0-7 in this register correspond to sprites 0-7. These bits are normally set OFF (equal to zero) which means that the sprites have a higher priority than the background, i.e. they pass OVER any data on the screen. If you wish to switch this priority for any sprite(s) you must turn ON the relevant bit(s). For example, the statement: POKE V + 27,8 makes sprite 3 appear behind the characters that are on the screen. 7.11. TURNING SPRITES OFF You can make a sprite disappear by setting the relevant bit in the SPRITE ENABLE register (21) OFF. Do this using the following statement: POKE V+21, PEEK(V+21) AND (255-2^SN) where SN is the number of the sprite you wish to turn off. Boolean Operators This instruction in the previous example uses what is known as a LOGICAL OPERATOR, sometimes known as a BOOLEAN OPERATOR. In that example, the AND was the logical operator. It is used to modify the first of two elements in the statement, i.e. register 21. It logically compares each corresponding bit of the result of the PEEK statement according to the following rules: 1 AND 1 = 1 0 AND 1 = 0 1 AND 0 = 0 0 AND 0 = 0 This is known as a TRUTH TABLE. As you can see, the bit being compared is set OFF unless both bits contain 1. You can apply the above statement to set OFF bits in any register for any sprite number. For example, you could have used the same instruction to reduce the size of a sprite by simply substituting either register 23 or 29. Let us see what happens when we turn off sprite 3. Before the instruction is executed, register 21 contains 00001000. The result of the expression after the PEEK statement is: 255 - 2^3 (8) = 247 or 11110111, i.e. after the instruction has been executed, register 21 contains zero. If other sprites had been ON, they would remain in the same state since both bits would have contained 1. The other Boolean operator we have used is OR. The truth table for this operator is as follows: 1 OR 1 = 1 0 OR 1 = 1 1 OR 0 = 1 0 OR 0 = 0 If either bit is set, the corresponding result bit will also be set. This chapter has only been an introduction to sprites. Try experimenting yourself with the design and animation of your own sprites. Further details about sprite handling can be found in the COMMODORE 64 Programmer's Reference Guide. 8. MAKING SOUND AND MUSIC Your COMMODORE 64 computer is equipped with one of the most sophisticated electronic music synthesizers available on any computer. This chapter is an introduction to using your computer's sound chip, the SID chip. The main features that the SID chip provides are: a) Volume control b) Multiple voices c) Waveform d) Frequency e) Envelope generator (attack, decay, sustain, release) 8.1. The SID Chip The SID (Sound Interface Device) chip contains 29 8-bit registers, numbered 0-28, each of which is responsible for a certain component of sound generation. In this chapter, you will only be concerned with the first 25 registers. These are stored between locations 54272 to 54296 inclusive. Here is a summary of the SID register map: REGISTER No. DESCRIPTION 0-6 VOICE 1 7-13 VOICE 2 14-20 VOICE 3 21 LOW FREQUENCY 22 HIGH FREQUENCY 24 VOLUME CONTROL AND FILTERS Before we go on to discuss how sounds are created, type in the following program and RUN it. This will demonstrate just a little of what may be achieved by the SID chip. EXAMPLE PROGRAM 1: 5 S=54272 10 FOR L=S TO S+24:POKE L,0:NEXT: REM CLEAR SOUND CHIP 20 POKE S+5,9:POKE S+6,0 30 POKE S+24,15: REM SET MAXIMUM VOLUME LEVEL 40 READ HF,LF,DR 50 IF HF<0 THEN END 60 POKE S+1,HF:POKE S,LF 70 POKE S+4,33 80 FOR T=1 TO DR:NEXT 90 POKE S+4,32:FOR T=1 TO 50:NEXT 100 GOTO 40 110 DATA 25,177,250,28,214,250 120 DATA 25,177,250,25,177,250 130 DATA 25,177,125,28,214,125 140 DATA 32,94,750,25,177,250 150 DATA 28,214,250,19,63,250 160 DATA 19,63,250,19,63,250 170 DATA 21,154,63,24,63,63 180 DATA 25,177,250,24,63,125 190 DATA 19,63,250,-1,-1,-1 Line 5 stores the start location of the SID chip in S. All other registers are accessed by simply adding their numbers to S. VOLUME CONTROL Your COMMODORE 64 has 16 volume levels, numbered from 0 (off) to 15 (maximum volume). Register 24 in the SID chip controls the volume level. To set the volume, you simply POKE the value you want into this register. Line 30 in the example program sets the maximum volume level (15). You would normally only set the volume at the beginning of your program. Note that the volume level determines the output from all three of your 64's voices. VOICES Your COMMODORE 64 has three voices, which may be played separately or simultaneously. The register map for each voice is shown below: REGISTER NUMBERS VOICE 1 VOICE 2 VOICE 3 DESCRIPTION 0 7 14 LOW FREQUENCY VALUES 1 8 15 HIGH FREQUENCY VALUES 2 9 16 LOW PULSE WIDTH 3 10 17 HIGH PULSE WIDTH 4 11 18 CONTROL REGISTER 5 12 19 ATTACK/DECAY SETTINGS 6 13 20 SUSTAIN/RELEASE SETTINGS FREQUENCY Sound is created by the movement of air. Think of throwing a stone into a pool and seeing the waves radiate outward. When similar waves are created in air, we hear a sound. Every sound produced on your 64 is made up from a high and low frequency value. Each of three voices has two registers in which the frequency values are stored. The two values in each voice are combined to form the frequency value in 16 bit form. A chart showing the memory locations to each voice's high and low frequency registers is shown below: +----------------------+----------------------+-----------------------+ | VOICE | FREQUENCY | POKE NUMBER | +----------------------+----------------------+-----------------------+ | 1 | HIGH | 54273 | +----------------------+----------------------+-----------------------+ | 1 | LOW | 54272 | +----------------------+----------------------+-----------------------+ | 2 | HIGH | 54280 | +----------------------+----------------------+-----------------------+ | 2 | LOW | 54279 | +----------------------+----------------------+-----------------------+ | 3 | HIGH | 54287 | +----------------------+----------------------+-----------------------+ | 3 | LOW | 54286 | +----------------------+----------------------+-----------------------+ To play a musical note or sound, you must POKE the sound's high frequency value into the high frequency location of the voice you want, and POKE the note's low frequency value into the voice's low frequency location. Line 60 in the example program POKEs the high and low frequencies from the DATA statements into registers 1 and 0 respectively. This sets the frequency for voice 1. CREATING OTHER FREQUENCIES To create a frequency other than those listed in the note table, use the following formula: F = FYOUT / .06097 where FYOUT is the frequency you require. To create the high and low frequency values for the note, you must first make F into an integer, i.e. delete any numbers to the right of the decimal point. Now use this formula to calculate the high frequency location: HI = INT ( F / 256 ) and the following formula to give you the low frequency location: LO = F - (256 * HI) Then to obtain the note, simply POKE the value for LO into the low frequency register and the value for HI into the high frequency register of the voice from which you wish to output the sound. WAVEFORMS The type of waveform you select determines the timbre or quality of the sound produced. There are four types of waveforms: TRIANGLE. This waveform contains few harmonics and a mellow flute-like sound. The shape of the triangle waveform looks like this: /\ / \ / \ ............../............\............. \ / \ / \ / \ / \/ \/ SAWTOOTH. This waveform contains all the harmonics. It has a bright, brassy quality. Here is what the sawtooth waveform looks like: + + + /| /| /| / | / | / | / | / | / | .........|..... /......|....../......|........ | / | / | / | / | / | / |/ |/ |/ + + + VARIABLE PULSE WAVE. This waveform contains variable rectangular waves. Changing the pulse width makes sounds ranging from a bright, hollow noise to a nasal, reedy pulse. Here's what it looks like: +-----------+ +-----------+ +-----------+ | | | | | | | | | | | | | | | | | | | | | | ..|...........|...|...........|...|...........|...|.. | | | | | | | | | |<--------->| | | | | | | PULSE | | | | | +---+ WIDTH +---+ +---+ WHITE NOISE. This waveform is used mainly for sound effects (e.g. explosions, gunshots, surf) and ranges from a low rumbling to hissing. It looks like this: . . . . . . . . . . . . ............................ . . . . . . . . . . . The waveforms for each voice is held in three control registers. These are numbered 4, 11 and 18. The component parts of the control register for each voice are as follows: BIT No. DESCRIPTION 0 GATE 1-3 UNUSED 4 TRIANGLE WAVEFORM 5 SAWTOOTH WAVEFORM 6 PULSE WAVEFORM 7 NOISE WAVEFORM The GATE bit controls the Envelope Generator. When this bit is set to 1, it triggers the Envelope Generator and the ATTACK/DECAY/SUSTAIN cycle begins. When the bit is reset to zero, the RELEASE cycle begins. Setting bits 4,5 or 6 to 1 selects that particular waveform. Line 70 in the program sets the output of the sound for voice 1 using a Sawtooth waveform. This line also sets the GATE bit. You can set combinations of these bits, i.e. Pulse and Sawtooth, but this will produce pretty weird sounds! THE ENVELOPE GENERATOR The volume of a musical tone changes from the moment you first hear it until it dies out and you can't hear it any more. When a note is first struck, it rises from zero volume to its peak volume. The rate at which this happens is called the ATTACK. It then falls from the peak to a mid- range volume level. The rate at which this occurs is called the DECAY. The mid-ranged volume is called the SUSTAIN level. When the note stops playing, it falls from the SUSTAIN level to zero volume. The rate at which it falls is called the RELEASE. The following is an illustration of the four phases of a note: + /.\ / . \ / . \ SUSTAIN LEVEL . . / . . . . +-----------+ / . . . \ / . . . \ / . . . \ . . . . . . . . . . . A . D . S . R . NOTE: ATTACK, DECAY and RELEASE are RATES. SUSTAIN is a LEVEL. Each of the cycles above give certain qualities and restrictions to the shape, or ENVELOPE of a sound. These bounds are collectively called parameters. The ATTACK/DECAY/SUSTAIN/RELEASE parameters are collectively called ADSR. There are two registers used for the ADSR parameters for each of the three voices. These are 5 and 6 for voice 1, 12 and 13 for voice 2 and 19 and 20 for voice 3. The ATTACK and DECAY parameters share the first of each pair of registers (5, 12, 19) while the SUSTAIN and RELEASE parameters use registers 6, 13 and 20. These pairings are used because the settings only require 4 bits or half a byte. This amount of storage is called a NYBBLE. The first four bits of a byte are called the HIGH NYBBLE and the last four bits are called the LOW NYBBLE. The ATTACK settings for the three voices are stored in the high nybbles of registers 5, 12 and 19, while the DECAY settings are stored in the low nybbles of these registers. The SUSTAIN settings for the three voices use the high nybbles in registers 6, 13 and 20, while the RELEASE settings use the low nybbles in the same registers. Before POKEing any value into the ADSR registers you must first combine the high and low nybbles by adding them together. For example, the ATTACK rates occupy the 2^7, 2^6, 2^5, and 2^4 bits, so the values are 128, 64, 32 and 16. DECAY rates use the 2^3, 2^2, 2^1 and 2^0 bits, or 8, 4, 2 and 16. Suppose you want to set a high ATTACK value (12) and a low DECAY value (2). An easy way to combine the two rates is to multiply the ATTACK value by 16 and add it to the DECAY value. In this example, the resulting value is 194, i.e. 12*16+2. You can use this formula whenever you wish to combine two values (range 0-15) into a high/low nybble format. Line 20 in the example program sets the ATTACK/DECAY rate to 0 ATTACK and 9 DECAY. The maximum ATTACK rate is achieved by using a value of 15 and multiplying it by 16. You can increase the DECAY rate by adding together all the DECAY values i.e. 8 + 4 + 2 + 1 = 15, which is the MAXIMUM DECAY RATE. Here are some sample ATTACK/DECAY POKEs: +----------------+-------+----------------------+---------------------+ | | VOICE | ATTACK | DECAY | +----------------+-------+----------------------+---------------------+ | POKE 54277,66 | 1 | MED(64) | LOW(2) | | POKE 54284,66 | 2 | MED(64) + | | | | | LOW(32) | MED(4) | | POKE 54291,15 | 3 | ZERO | MAX | | | | | (8 + 4 + 2 + 1) | | POKE 54284,255 | 2 | MAX | MAX | | | | (128 + 64 + 32 + 16 | + 8 + 4 + 2 + 1) | +----------------+-------+----------------------+---------------------+ Here's a sample program that illustrates what you can do with ATTACK/ DECAY settings: 10 FOR L=54272 TO 54296:POKE L,0:NEXT ..... Clears the SID chip 20 POKE 54296,15 .......................... Set maximum volume 30 POKE 54277,64 .......................... Set ATTACK/DECAY 40 POKE 54273,162:POKE 54272,37 ........... POKE one note in voice 1 50 PRINT"PRESS ANY KEY" ................... Screen message 60 GET K$:IF K$="" THEN 60 ................ Check the keyboard 70 POKE 54276,17:FOR T=1 TO 200:NEXT ...... Start triangle waveform 80 POKE 54276,16:FOR T=1 TO 50:NEXT ....... Stop note 90 GOTO 50 ................................ Repeat execution After you RUN the program a few times, try changing the ATTACK/DECAY setting by changing line 30: 30 POKE 54277,190 Now RUN the program again and notice the difference in the note. Try other combinations of ATTACK and DECAY settings to get an idea of how you can use different ATTACK/DECAY rates to create a variety of sound effects. SUSTAIN/RELEASE SETTING. Like ATTACK/DECAY, SUSTAIN/RELEASE share a byte. But remember that this sharing doesn't mean that SUSTAIN and RELEASE are alike. SUSTAIN is a LEVEL, while RELEASE, ATTACK and DECAY are RATES. SUSTAIN is a proportion of maximum volume. You can sustain, or hold, notes and sounds at any of 16 volume levels. This table shows you what numbers to POKE for SUSTAIN/RELEASE values: +--------+--------+--------+--------+--------+--------+--------+--------+ | HIGH | MEDIUM | LOW | LOWEST | HIGH | MED. | LOW | LOWEST | | SUSTAIN| SUSTAIN| SUSTAIN| SUSTAIN| RELEASE| RELEASE| RELEASE| RELEASE| +--------+--------+--------+--------+--------+--------+--------+--------+ | 128 | 64 | 32 | 16 | 8 | 4 | 2 | 1 | +--------+--------+--------+--------+--------+--------+--------+--------+ NOTE: You can increase the SUSTAIN level by adding together all the SUSTAIN values: 128 + 64 + 32 + 16 = 240, which is the MAXIMUM SUSTAIN LEVEL. A SUSTAIN level of 128 is approximately 50% of volume. You can increase the RELEASE rate by adding together all the RELEASE values: 8 + 4 + 2 + 1 = 15, which is the MAXIMUM RELEASE RATE. Combine the SUSTAIN level and RELEASE rate the same way you combine the ATTACK and DECAY rates: add the two values and POKE the total to the memory location of the voice you want. To see the effects of the sustain level setting add this line to the last sample program: 35 POKE 54278,128 Now RUN the program again and note the change. With line 35, we tell the computer to sustain the note at a HIGH SUSTAIN LEVEL (128). You can vary the duration of a note by changing the count in line 70. Remember that the sustain level maintains a note at a proportion of the volume as the note falls from its peak volume; this isn't the same thing as the note's duration. To see the effect of the release rate, try changing line 35 to POKE 54278,89 (SUSTAIN = 80, RELEASE = 9). 8.2. SAMPLE SOUND PROGRAM This brief sound program summarizes what you've learned so far about making music on your 64: 1. Choose the voice(s) you want to use. Recall that each voice uses different memory locations into which you'll POKE values for waveform, ATTACK rate, etc. You can play 1, 2, or 3 voice together, but this program only uses voice 1. 2. Clear the SID chip: 5 FOR L=54272 TO 54296:POKE L,0:NEXT 3. Set VOLUME: 10 POKE 54296,15 4. Set ATTACK/DECAY rates: to define how fast a note rises to and falls from its peak volume level (0-255): 20 POKE 54277,190 5. Set SUSTAIN/RELEASE to define level to hold note and rate to release it: 30 POKE 54278,248 6. Find note you want to play in the TABLE OF MUSICAL NOTES in Appendix M and enter the HIGH- FREQUENCY and LOW-FREQUENCY values for that note (each note requires 2 POKEs): 40 POKE 54273,16:POKE 54272,195 7. Start WAVEFORM (here, TRIANGLE): 50 POKE 54276,17 8. Enter a timing loop to time between notes (we use 250 for a quarter note): 60 FOR T=1 TO 250:NEXT 9. STOP note by turning off chosen waveform: 70 POKE 54276,16 Here's a longer program that further demonstrates your 64's music- making abilities: 5 REM MUSICAL SCALE 7 FOR L=54272 TO 54296:POKE L,0:NEXT clears SID chip 10 POKE 54296,15 .................... sets VOLUME 20 POKE 54277,7:POKE 54278,133 ...... sets ADSR 50 READ A ........................... READs 1st number from line 110 55 IF A=-1 THEN END ................. ENDs loop 60 READ B ........................... READs 2nd number 80 POKE 54273,A:POKE 54272,B ........ POKEs 1st number from line 110 as HIGH-FREQUENCY and 2nd number as LOW-FREQUENCY 85 POKE 54276,17 .................... starts note 90 FOR T=1 TO 250:NEXT:POKE 54276,16 lets note play, then stops it 95 FOR T=1 TO 50:NEXT ............... sets time for RELEASE, time between notes 100 GOTO 20 .......................... restarts program 110 DATA 16,195,18,209,21,31,22,96 .... lists note value 120 DATA 25,30,28,49,31,165,33,135 .... from chart in Appendix M. Each part of numbers = one note (16 and 19 = 4th octave C) 999 DATA -1 .......................... ENDs program (see line 55) You can change to a sawtooth wave by changing line 85 to read POKE 54276,33 and line 90 to read FOR T=1 TO 250:NEXT:POKE 54276,32. Changing the waveform can dramatically change the sound your computer produces. You can also change the sound in other ways. For example, you can change the harpsichord-like sound in the previous program to a banjo-like sound by changing the ATTACK/DECAY rate of each note. Do this by changing line 20 to read: 20 POKE 54277,3:POKE 54278,0 ........ creates banjo effect by setting zero SUSTAIN As this program demonstrates, your 64 can sound like a variety of musical instruments. 8.3. PLAYING A SONG ON YOUR 64 The next program lets you play a line from a song, "Michael Row Your Boat Ashore". The program uses the PULSE waveform, which is a variable width rectangular wave. The third and fourth POKEs in line 10 define the pulse width for this song. In this song, we use a duration count of 125 for an eighth note, 250 for a quarter note, 375 for a dotted quarter note, 500 for a half note, and 1000 for a whole note. When you program your own songs, you can increase or decrease these numbers to match a particular tempo or your own musical taste. 2 FOR L=54272 TO 54296: POKE L,0: NEXT 5 S=54272 10 POKE S+24,15: POKE S+5,88: POKE S+3,15: POKE S+2,15: POKE S+6,89 20 READ H: IF H=-1 THEN END 30 READ L 40 READ D 60 POKE S+1,H: POKE S,L: POKE S+4,65 80 FOR T=1 TO D: NEXT: POKE S+4,64 85 FOR T=1 TO 50: NEXT 90 GOTO 20 100 DATA 33,135,250,42,62,250,50,60,250,42,62,125,50,60,250 105 DATA 56,99,250 110 DATA 50,60,500,0,0,125,42,62,250,50,60,250,56,99 115 DATA 1000,50,60,500 120 DATA -1 Line 2 clears the SID chip. Line 5 assigns the lowest SID chip memory location to the variable S. Throughout the rest of the program, we just add the number of the SID register to this variable. For example, POKE S+24,15 POKEs 15 to the volume register, which is 54296, or 54272+24. Line 10 POKEs values into: 1. The volume register: POKE S+24,15 2. Voice 1, ATTACK/DECAY rates: POKE S+5,88 3. Pulse width: POKE S+3,15 and POKE S+2,15 4. Voice 1, SUSTAIN level/RELEASE rate: POKE S+6,89 Line 20 READs the first number from the DATA statement. If that number is -1, the program ENDs automatically. This occurs when the final DATA statement (line 120) is read. Line 30 READs the second number from the DATA list. Line 40 READs the third number from the DATA list. Line 60 POKEs: 1. The value for H that was assigned in the READ H statement in line 20. Until -1 is read, this value is assigned to the HIGH FREQUENCY register. 2. The value for L that was assigned in the READ L statement in line 30. This value is assigned to the LOW FREQUENCY register. Together these two POKEs determine the pitch for one note. 3. The value that turns ON the variable pulse waveform for voice 1. Line 70 uses a loop to set the duration for the note being played. The value for D is assigned in the READ statement in line 40. As you can see, the numbers in the DATA lists are clustered into threes: the first number (e.g., 35) is the high frequency value for a note, the second number (e.g., 135) is the low frequency value for the same note, and the third number (e.g., 250) sets the duration for that note (e.g., a quarter note C). Line 80 is a timing loop that determines release time between notes. Line 90 sends the program back to READ the number set for another note. Lines 100 through 120 contain all the DATA for the line from this song. 8.4. CREATING SOUND EFFECTS Your 64's SID chip lets you create a wide variety of sound effects, such as an explosion during a game, or a buzzer that warns you when you've made a mistake. Here are just a few suggestions for creating sound effects: 1. Vary rapidly between two notes to create a tremor sound. 2. Use the multivoice effects to play more than one voice at a time, with each voice independently controlled, so you have different noises at once. Or use one voice as an echo or response to another voice. 3. Use the different pulse widths to create different sounds. 4. Use the NOISE WAVEFORM to make white noise to accent tonal sound effects, create explosion noises, gunshots, footsteps, or alarms. When you use the noise waveform with the same musical notes that create music, you can create different types of white noise. 5. Combine several HIGH/LOW FREQUENCIES in rapid succession across different octaves. 6. Try POKEing the extra note settings in Appendix M. Here are some sample sound effects programs. The Commodore 64 Programmer's Reference Guide contains more examples as well as more information on creating sound effects. DOLL CRYING 5 FOR L=54272 TO 54296:POKE L,0:NEXT Clears SID chip 10 S=54272:POKE S+3,15:POKE S+2,40 20 POKE S+24,15 ..................... Sets volume 30 POKE S+4,65 ...................... Turns ON pulse waveform in voice 1 40 POKE S+5,15 ...................... Sets ATTACK/DECAY rate 50 FOR X=200 TO 5 STEP -2 ........... Sets timing loop for RELEASE or time between notes 60 POKE S+1,40:POKE S,X:NEXT ........ Sets hi/lo frequencies 70 FOR X=150 TO 5 STEP -2 ........... Sets faster timing loop 80 POKE S+1,40:POKE S,X:NEXT ........ Sets hi/lo frequencies 90 POKE S+4,0 ....................... Turns OFF pulse waveform SHOOTING 5 FOR L=54272 TO 54296:POKE L,0:NEXT Clears SID chip 10 S=54272 20 FOR X=15 TO 0 STEP -1 ............ Sets up volume loop 30 POKE S+24,X ...................... POKEs X to vol. register 40 POKE S+4,129 ..................... Starts NOISE waveform 50 POKE S+5,15 ...................... Sets ATTACK/DECAY rate 60 POKE S+1,40 ...................... Sets high frequency 70 POKE S,200:NEXT .................. Sets low frequency 80 POKE S+4,128 ..................... Stops NOISE waveform 90 POKE S+5,0 ....................... POKEs 0 to ATTACK/DECAY 100 GOTO 20 .......................... Repeats program The loop that begins in line 20 sets up fading volume so that the sound of the gunshot starts at high volume (15) and fades to 0 as the loops executes. Press the key to end this program. As we've said before, the best way to learn a new area of programming is to experiment. 8.5. FILTERING Sometimes a certain waveform may not have quite the timbre you require. For example, it would be difficult to imagine any of the preset waveforms in the SID chip sounding anything like a trumpet. To give you additional control over the sound parameters, the SID chip is equipped with three FILTERS. HIGH-PASS FILTER. This filter reduces the level of frequencies below the specified cutoff frequency. It passes all the frequencies at or above the cutoff, while cutting down the frequencies below the cutoff. LOW-PASS FILTER. As its name implies, this filter passes the frequencies below the cutoff and reduces the level of those above. BAND-PASS FILTER. This filter passes a narrow band of frequencies around the cutoff and cuts down the level of all others. An extra filter, called the NOTCH REJECT FILTER can be synthesized by combining the high and low pass filters. This passes frequencies away from the cutoff while reducing the level at the cutoff frequency. Register 24 determines which filter type you want to use. Remember that this is also the register used for the volume control. The following bits are used for filters: BIT No. USAGE 4 SELECT LOW-PASS FILTER 5 SELECT BAND-PASS FILTER 6 SELECT HIGH-PASS FILTER A filter is activated by setting the relevant bit in register 24. You may not wish to filter all voices at the same time. Register 23 determines which voices are to be filtered. The bits are as follows: BIT No. USAGE 7-4 FILTER RESONANCE 0-15 3 FILTER EXTERNAL INPUT 2 FILTER VOICE 3 1 FILTER VOICE 2 0 FILTER VOICE 1 When a specific bit is set, the output of that voice will be diverted through the filter. The cutoff frequency is an eleven bit number. The upper eight bits (11-3) are stored in register 22 while the lower three bits (0-2) are stored in register 21. This gives you a range of values between 0 and 2047. Try adding the following lines to the example program to filter the voice and hear the difference in sound. We will be using a Low Pass filter which will allow only the lower components of the sounds to be heard. 30 POKE S+24,31: REM FULL VOLUME PLUS LOW PASS FILTER 35 POKE S+23,1: REM SELECT FILTER FOR VOICE 1 37 POKE S+22,128:POKE S+21,7: REM SELECT CUTOFF FREQUENCY Try experimenting with filters. Filtering a sound as it passes through the ADSR phases of its life can produce interesting effects. For further information on how to use the SID chip, consult the COMMODORE 64 Programmer's Reference Guide. 8.6. MUSIC COMPOSER The Commodore MUSIC COMPOSER cartridge allows you to compose music on your COMMODORE 64 without having to concern yourself with the workings of the SID chip. Facilities are provided to allow you to type in program lines that consist purely of special control characters. This enables you to play any combination of sounds that you require using all the features of the SID chip. Once you have composed your masterpiece, you can save it on tape and then play it back at your leisure. While the music is playing, a music stave scrolls across the screen displaying the notes as they are being played. This allows you to get the most from the SID chip with the minimum of effort. 9. ADVANCED DATA HANDLING 9.1. READ AND DATA STATEMENTS So far we've shown you how to assign values to variables directly (A = 2), and how to assign values while the program is RUNning (INPUT and GET). But often you'll find that neither way suits your needs for variable assignment in a program, especially when you have large amounts of data. In the Chapter 7 when we introduced sprites, we used READ and DATA statements to assign values for sprites. Here's a short program that shows you how these two statements work together: 10 READ X 20 PRINT "X IS NOW :"; X 30 GOTO 10 40 DATA 1, 34, 10.5, 16, 234.56 RUN X IS NOW : 1 X IS NOW : 34 X IS NOW : 10.5 X IS NOW : 16 X IS NOW : 234.56 ?OUT OF DATA ERROR IN 10 READY. _ Line 10 READs a value from the DATA statement at line 40 and assigns the value to X. Line 30 tells the computer to return to line 10, where the READ assigns the next value in the DATA statement to X. The loop continues until all the DATA values are read. There are a few important rules you must remember when you use DATA statements: o Follow the Data statement format precisely: 40 DATA 1, 34, 10.5, 16, 234.56 Comma separates each item. o Use: -- integer numbers (e.g., 34), -- real numbers (e.g., 234.56), -- numbers expressed in scientific notation (e.g., 2.4E+04), -- words (as long as you use a string variable in the READ statement), but DON'T use: -- variables or -- arithmetic operations in DATA statements. The items listed below are treated as strings if you try to READ them, and you can only READ them as strings with string variables in the READ statement. DATA A, 23/56, 2*5, B + 2 When you use a READ statement, you can only get values from a DATA statement because the two statements work as partners. Each time you READ a value, the computer knows to move to the next value in the DATA statement. In effect, there's a pointer in the computer that keeps track of your place in the DATA statement. After READing the first value, the DATA statement looks like this: 40 DATA 1, 34, 10.5, 16, 234.56 | pointer When the last DATA value has been assigned to the variable in the READ statement and the computer tries to execute the loop again, the OUT OF DATA ERROR is displayed. Here's an example that shows one way to avoid the OUT OF DATA ERROR. NEW 10 FOR X = 1 TO 3 15 READ A$ 20 PRINT "A$ IS NOW : "; A$ 30 NEXT 40 DATA THIS, IS, FUN RUN A$ IS NOW : THIS A$ IS NOW : IS A$ IS NOW : FUN READY. This time we put the READ statement inside a FOR/NEXT loop that limited the number of READings to equal the numbers of items in the DATA statement. As long as you know how many items will be in your DATA statements, this method is fine. But often either you won't know or you won't want to bother to count. Sometimes the best way to avoid an OUT OF DATA ERROR is to end your DATA statement with a FLAG. A flag is some value that would not ordinarily appear in your DATA list, such as a negative number, a very large number, a very small number, or a special word, such as END or STOP. When you use a flag, add an IF/THEN statement to tell the computer to branch to another part of the program when the flag is read. For example: 10 READ A 15 IF A < 0 THEN END 20 DATA 13, 35, 29, -999 25 PRINT "TOTAL = "; A 30 GOTO 10 This program READs and PRINTs a value for A until it reaches -999. Line 15 tells the computer to END the program immediately when a negative value is read. There is also a way to reuse the items in a DATA statement by RESTOREing the data pointer to the beginning of the DATA list. Try adding this line: 45 RESTORE to the second program in this chapter and RUN it again. You'll see that the data pointer has been RESTOREd to the first item in the DATA list, and that you can reREAD all the items. 9.2. CALCULATING AVERAGES Here's a program that READs a set of numbers from a DATA list and calculates their average. This program also uses a flag to tell the computer when to stop READing DATA. 5 T = 0: CT = 0 10 READ X 20 IF X = -1 THEN 50: REM CHECK FOR FLAG 25 CT = CT + 1 30 T = T + X: REM UPDATE TOTAL 40 GOTO 10 50 PRINT "THERE WERE"; CT ;"VALUES READ" 60 PRINT "TOTAL ="; T 70 PRINT "AVERAGE ="; T/CT 80 DATA 75, 80, 62, 91, 87, 93, 78, -1 RUN THERE WERE 7 VALUES READ TOTAL = 566 AVERAGE = 80.8571429 Line 5 sets CT, the CounTer, and T, the Total, to zero. Line 10 READs a value from the DATA list and assigns it to X. Line 20 checks to see if the value read to X is our flag (-1). If it is, then the program skips lines 25-40 and goes straight to line 50. Line 25 adds one to CT, the counter, if the value of X is not the flag. Line 30 adds X to T, the running total. Line 40 sends the program back to repeat line 10. Line 50, which isn't executed until line 10 READs the flag, PRINTs the number of values read (CT). Line 60 PRINTs the total of the numbers read (T). Line 70 PRINTs the average. You can also use more than one variable in the READ statement. You can mix the types of DATA in a DATA list when you also mix the types of variables in the READ statement. Here's a program that does just that. It READs a name and some scores and then calculates the average of the scores. NEW 10 READ N$, A, B, C 20 PRINT N$;"'S SCORES WERE :"; A ;" "; B ;" "; C 30 PRINT "AND THE AVERAGE IS :"; (A + B + C) / 3 40 PRINT: GOTO 10 50 DATA MIKE, 190, 185, 165, DICK, 225, 245, 190 60 DATA JOHN, 155, 185, 205, PAUL, 160, 179, 187 RUN MIKE'S SCORES WERE : 190 185 165 AND THE AVERAGE IS : 180 DICK'S SCORES WERE : 225 245 190 AND THE AVERAGE IS : 220 Line 10 READs a value for each of the variables. The DATA statement lists its items in the same order that the READ statement expects to find them. In other words, there's a name to go with the string variable, and numbers to go with the integer variables. 9.3. SUBSCRIBED VARIABLES So far we've only used simple BASIC variables such as X and X$. It's doubtful that you'll write a program that requires more variable names than all the combinations of letters and numbers available in BASIC, but you might want to be able to group variable names together when you're using groups of data. Subscripted variables let you use variable names so that they are obviously grouped together. For example: A(0), A(1), A(2), A(3) The numbers in parentheses are the SUBSCRIPTS of variable A. Be aware that the variable A1 does NOT equal the subscripted variable A(1). You can use variables and arithmetic operation as subscripts. For example: A(X) A(X+1) A(4-1) A(2*X) The expressions within the parentheses are evaluated according to the same rules for arithmetic operations outlined in Chapter 3. Subscripted variables, like simple variables, name a memory location within the computer. But only subscripted variables name values that are organized into an ARRAY. An ARRAY is understood by the computer to be a unit, such as a list or a table, of related values. The following example uses subscripted variables to calculate an average: 5 PRINT CHR$(147) 10 INPUT "HOW MANY NUMBERS :"; X 20 FOR A = 1 TO X 30 PRINT "ENTER VALUE #"; A ;: INPUT B(A) 40 NEXT 50 SU = 0 60 FOR A = 1 TO X 70 SU = SU + B(A) 80 NEXT 90 PRINT: PRINT "AVERAGE ="; SU/X RUN HOW MANY NUMBERS :? 5 ENTER VALUE # 1 ? 125 ENTER VALUE # 2 ? 167 ENTER VALUE # 3 ? 189 ENTER VALUE # 4 ? 167 ENTER VALUE # 5 ? 158 AVERAGE = 161.2 Line 5 clears the screen. Line 10 asks you to enter the total number of items you'll INPUT at line 30. Line 20 sets up a loop that makes A the subscript for the array B. The loop adds 1 to A for every execution. This updates array B. Line 30 prompts you to INPUT a value for the subscripted variable B(A). Lines 50 through 80 keep a running total (SU) of the numbers INPUT. Line 90 PRINTs the average. Each time the INPUT loop executes, A is increased by 1, so the next value entered is assigned to the next element in array B. At the end of the program, array B looks like this: +---------+ B(1) | 125 | +---------+ B(2) | 167 | +---------+ B(3) | 189 | +---------+ B(4) | 167 | +---------+ B(5) | 158 | +---------+ After you INPUT all the values, they are stored in array B. You can now access these values just by using the subscripted variables. For example, see what happens when you add these lines: 100 PRINT B(X-1) 120 PRINT B(3) 130 PRINT B(X-3) 9.4. DIMENSIONING ARRAYS If you try to enter more than ten numbers in an array, you'll get a BAD SUBSCRIPT ERROR. Arrays of more than ten elements need to be predefined in a DIMension statement. For example, if you want an array to hold 25 values, you'd write this statement in your program: DIM B(25) You can also use a variable in a DIMension statement. For example, in the last program you could have used this statement since X equaled the total number of values in array B: 15 DIM B(X) But be careful when you use variables to define arrays: once an array is DIMensioned, it can't be reDIMensioned in another part of the program. So don't use a variable whose value will change in the program. You can use more than one array in a program, and you can DIMension them all on the same line: 10 DIM A(12), B(35), C(3,5) Arrays A and B are one-dimensional arrays, but C is a two-dimensional array. One-dimensional arrays just have rows of data, but two-dimensional arrays have both rows and columns of data, just like a chart. Array C has 3 rows and 5 columns. Rows are always listed first in a DIMension statement. 9.5. SIMULATED DICE ROLL WITH ARRAYS As you begin writing more complex programs, you'll find that subscripted variables cut down on the number of statements and make programs simpler to write. For example, a single subscripted variable can keep track of the number of times each face on a die turns up in a dice roll: 1 REM DICE SIMULATION: PRINT CHR$(147) 10 INPUT "HOW MANY ROLLS: "; X 20 FOR L = 1 TO X 30 R = INT(6*RND(1)) + 1 40 F(R) = F(R) + 1 50 NEXT L 60 PRINT "FACE", "NUMBER OF TIMES" 70 FOR C = 1 TO 6: PRINT C, F(C): NEXT Line 10 asks you how many times you'll throw the dice in the simulated roll. Line 20 sets up a loop to count the number of dice rolls so that the program ends on the Xth roll. Line 30 makes R equal to the random number rolled. Line 40 sets up the array F, for FACE, which keeps track of how many times each face turns up. Whatever value R acquires in the dice roll becomes the subscript for the array, and line 40 adds one to the appropriate array variable. For example, every time a 2 is thrown, F(2) is increased by one. Line 70 PRINTs the number of times each face shows up. Here's a sample RUN: HOW MANY ROLLS: ? 1000 FACE NUMBER OF TIMES 1 148 2 176 3 178 4 166 5 163 6 169 Now we'll show you how much longer your program would be if you didn't use an array: 10 INPUT "HOW MANY ROLLS: "; X 20 FOR L = 1 TO X 30 R = INT(6*RND(1)) + 1 40 IF R = 1 THEN F1 = F1 + 1: NEXT 41 IF R = 2 THEN F2 = F2 + 1: NEXT 42 IF R = 3 THEN F3 = F3 + 1: NEXT 43 IF R = 4 THEN F4 = F4 + 1: NEXT 44 IF R = 5 THEN F5 = F5 + 1: NEXT 45 IF R = 6 THEN F6 = F6 + 1: NEXT 60 PRINT "FACE", "NUMBER OF TIMES" 70 PRINT 1, F1 71 PRINT 2, F2 72 PRINT 3, F3 73 PRINT 4, F4 74 PRINT 5, F5 75 PRINT 6, F6 As you can see, the program has twice as many lines. The longer the program, the more space and time you can save when you use arrays. 9.6. TWO-DIMENSIONAL ARRAYS As we mentioned before, two-dimensional arrays have both rows and columns, like a chart or a table. Two-dimensional arrays have two subscripts: the first one is for the ROW number; the second is for the COLUMN number. For example: A(4,6) has 4 ROWS and 6 COLUMNS Here's what array A would look like as a two-dimensional grid in memory: 0 1 2 3 4 5 6 +-------+-------+-------+-------+-------+-------+-------+ 0 | | | | | | | | +-------+-------+-------+-------+-------+-------+-------+ 1 | | | | | | | | +-------+-------+-------+-------+-------+-------+-------+ 2 | | | | | | | | +-------+-------+-------+-------+-------+-------+-------+ 3 | | | | | | | | +-------+-------+-------+-------+-------+-------+-------+ 4 | | | | | | | | +-------+-------+-------+-------+-------+-------+-------+ You'll notice that there's a zeroth row and column, so when you DIMension A(4,6), you're creating an array with 5 rows and 7 columns, or 35 elements. You can access any element of a two-dimensional array by using its row and column subscripts. For example, suppose you want to assign 255 to A(3,4): 10 LET A(3,4) = 255 Here's what the grid looks like now: 0 1 2 3 4 5 6 +-------+-------+-------+-------+-------+-------+-------+ 0 | | | | | | | | +-------+-------+-------+-------+-------+-------+-------+ 1 | | | | | | | | +-------+-------+-------+-------+-------+-------+-------+ 2 | | | | | | | | +-------+-------+-------+-------+-------+-------+-------+ 3 | | | | | 255 | | | +-------+-------+-------+-------+-------+-------+-------+ 4 | | | | | | | | +-------+-------+-------+-------+-------+-------+-------+ Two-dimensional arrays follow the same rules as one-dimensional arrays: DIMensioning: DIM A(20,20) Assigning data values: A(1,1) = 255 Assign values to other variables: AB = A(1,1) PRINTing values: PRINT A(1,1) Here's an example of how two-dimensional arrays can be used. This example keeps track of responses to a club questionnaire like this: CLUB QUESTIONNAIRE Q1: ARE YOU IN FAVOR OF RESOLUTION #1? 1-YES 2-NO 3-UNDECIDED Lets suppose there are four questions, so the array, which we'll call A, will be DIMensioned A(4,3). Here's how the array table looks: YES NO UNDECIDED +----------------+----------------+----------------+ QUESTION 1 | | | | +----------------+----------------+----------------+ QUESTION 2 | | | | +----------------+----------------+----------------+ QUESTION 3 | | | | +----------------+----------------+----------------+ QUESTION 4 | | | | +----------------+----------------+----------------+ The program that keeps track of the responses is on the next page. This program uses many of the programming techniques that have been presented so far. Lines 30-65 PRINT the questions in numerical order and ask you to INPUT the response. Line 70 adds one to the appropriate array element. Remember that R is the question number, and the questions are in rows. C is the response number, and the responses are in columns. Line 90 asks if you have another set of responses to INPUT. Lines 110 and 120 tell the program where to go, depending on your response to line 90. Lines 130-170 PRINT the total number of each response. Each time you INPUT a response at line 61, line 70 updates the right element of the array. Recall the R is the question number and C is the response number, so if your response to question 2 is 3 (undecided), line 70 adds one to array element A(2,3). You'll notice that we didn't use the zeroth row and column in this example. You don't have to use this row and column, but remember that they are always present in every array you use. 20 PRINT "{CLR/HOME}" 30 FOR R = 1 TO 4 40 PRINT "QUESTION # :"; R 50 PRINT "1-YES 2-NO 3-UNDECIDED" 60 PRINT "WHAT WAS THE RESPONSE : "; 61 GET C: IF C < 1 OR C > 3 THEN 61 65 PRINT C: PRINT 70 A(R,C) = A(R,C) + 1: REM UPDATE ELEMENT 80 NEXT R 85 PRINT 90 PRINT "DO YOU WANT TO ENTER ANOTHER": PRINT "RESPONSE (Y/N) ?"; 100 GET A$ : IF A$ = "" THEN 100 110 IF A$ = "Y" THEN 20 120 IF A$ <> "N" THEN 100 130 PRINT "{CLR/HOME}"; "THE TOTAL RESPONSES WERE:": PRINT 140 PRINT SPC(18); "RESPONSE" 141 PRINT "QUESTION", "YES", "NO", "UNDECIDED" 142 PRINT "-------- -----------------------------" 150 FOR R = 1 TO 4 160 PRINT R, A(R,1), A(R,2), A(R,3) 170 NEXT R RUN QUESTION # : 1 1-YES 2-NO 3-UNDECIDED WHAT WAS THE RESPONSE : 1 QUESTION # : 2 1-YES 2-NO 3-UNDECIDED WHAT WAS THE RESPONSE : 1 And so on... DO YOU WANT TO ENTER ANOTHER RESPONSE (Y/N) ? THE TOTAL RESPONSES WERE: RESPONSE QUESTION YES NO UNDECIDED -------- ----------------------------- 1 6 1 0 2 5 2 0 3 7 0 0 4 2 4 1 APPENDICES INTRODUCTION Now that you've become more intimately involved with your Commodore 64, we want you to know that our customer support does not stop here. You may not know it, but Commodore has been in business for over 23 years. In the 1970's we introduced the first self-contained personal computer (the PET). We have since become the leading computer company in many countries of the world. Our ability to design and manufacture our own computer chips allows us to bring you new and better personal computers at prices way below what you'd expect for this level of technical excellence. Commodore is committed to supporting not only you, the end user, but also the dealer you bought your computer from, magazines which publish how-to articles showing you new applications or techniques, and ... importantly ... software developers who produce programs on cartridge, disk ond tape for use with your computer. We encourage you to establish or join a Commodore "user club" where you can learn new techniques, exchange ideas and share discoveries. We publish two separate magazines which contain programming tips, information on new products and ideas for computer applications. (See Appendix N). In North America, Commodore provides a "Commodore Information Network" on the CompuServe Information Service ... to access this network, all you need is your Commodore 64 computer and our low cost VICMODEM telephone interface cartridge (or other compatible modem). The following APPENDICES contain charts, tables, and other information which help you program your Commodore 64 faster and more efficiently. They also include important information on the wide variety of Commodore products you may be interested in, and a bibliography listing of over 20 books and magazines which can help you develop your programming skills and keep you current on the latest information concerning your computer and peripherals. APPENDIX A EXPANDING YOUR COMMODORE 64 COMPUTER SYSTEM The 64 is an extremely powerful computer and one that can be used in a wide variety of applications from word-processing to data base management. The basic 64 computer system consists of the computer, a suitable television set or monitor and a cassette unit on which to store your programs. For some applications, the cassette unit can be somewhat slow. This limitation can be overcome by using a disk unit to save and recall your programs. Why Use a Disk Drive? If your programs or data files are very small, storing information on cassette tape will not cause any great inconvenience. However, there will come a time when the effective use of your system is restricted by the time it takes to load from and/or save to tape. This is when you should be thinking about using a Commodore disk unit. THE VIC 1541 DISK DRIVE The VIC 1541 disk drive allows you to store up to 144 programs or data files on a standard 5-1/4 inch diskette. When using a disk drive, you no longer have to think about re-winding tapes or worry about overwriting existing information. The 1541 disk unit is an 'intelligent device', i.e. it does its own processing without having to use any of the memory resources of the COMMODORE 64. Over 174000 characters of information can be stored on each diskette -- the size of an average Dicken's novel! The main advantage of a disk drive over a cassette unit is speed. An operation on a disk drive is typically up to 40 times faster than the same operation on cassette. The VIC 1541 disk unit requires no special interface -- it plugs directly to your COMMODORE 64. You are not restricted to using one disk drive. By connecting the units together (called 'daisy-chaining') as many as five disk drives can be used with one COMMODORE 64 so that you can load and save programs and files without having to change diskettes. VIC 1525 DOT MATRIX PRINTER A printer adds a great deal of versatility to your computer system. No computer system is complete without one. It allows you to produce invoices, send letters, or print out program listings so that you can examine your code away from the computer. The VIC 1525 is a 'dot matrix' printer. This means that each character is made up from a pattern of dots in a grid. You can print all the characters on your COMMODORE 64 keyboard or print characters you have designed yourself. The VIC 1525 prints at a speed of 30 characters/second at 12 characters/inch on plain tractor-feed paper up to 10 inches wide. The printer plugs directly into your COMMODORE 64 and requires no additional interface. VIC 1526 BI-DIRECTIONAL DOT MATRIX PRINTER The VIC 1526 printer differs from the VIC 1525 in two important respects. First, it is a bi-directional printer. This means that the machine prints from right to left as well as the conventional left to right. This means that the machine doesn't waste time sending the printer head to the left edge of the paper every time a new line of text is to be printed. The second main difference between the 1526 and 1525 is in speed of operation. The time taken to print each line is directly proportional to the width of page you have set up. On an 80 column wide print out, the speed is 45 lines/minute; on 40 columns, 78 lines/minute, and on 20 column wide paper, 124 lines/minute. The 1526 allows you to print up to 3 copies of your output including the original. It has a cartridge ribbon for ease of interchange and accepts paper up to 10 inches wide. The 1526 plugs directly to your COMMODORE 64 -- no special interface is required. VIC 1520 PRINTER/PLOTTER The VIC 1520 can be used both as a standard printer or as a plotter to allow you to design and draw graphs, histograms, pie charts -- in fact any shape you like in a combination of four colors. You can print upper case/lower case letters and graphics symbols. A further facility offered by the printer allows you to define the size of each character you display. The printer prints at 14 characters/second. Depending on the size of character selected, between 10 and 40 characters can be printed on each line of the paper. Characters can even be printed 'sideways' by rotating them 90 degrees. Shapes are drawn by simply telling the printer/ plotter where the start and end co-ordinates or the shape are to be on the paper and what type of line you wish to use. These range from solid lines to coarse, broken lines. The plotter is accurate to 0.2 of a mm and has a plotting speed of 60 mm/sec. The plotter uses small ball-point pens each of which is user-selectable when plotting. The printer/plotter plugs directly into your COMMODORE 64 and requires no additional interface. 1701 COLOR MONITOR A computer with the versatility of the COMMODORE 64 needs a medium on which to demonstrate its capabilities to the full. The 1701 color monitor has been designed specifically for this purpose. The monitor has a 14 inch screen with outstanding resolution. Sound can be generated either from the monitor's internal speaker or, via a simple connection, from your Hi-Fi system. 1311 JOYSTICK A joystick can be used not only as a games controller but also, with suitable software, as a tool for drawing and plotting. The COMMODORE 64 Programmer's Reference Guide gives detailed information on how to incorporate the use of a joystick in your programs. SOFTWARE A wide variety of software is available for the COMMODORE 64 covering applications in the home, at work, entertainment and aids for the programmer. Software for Business and the Home EASYFILE EFI 6440 (diskette) EASYFILE is a comprehensive data-base system for the COMMODORE 64. It includes all the features of similar, highly-priced packages at a fraction of the cost. The user decides how he wishes his information to appear when it is printed out either on the screen or the printer. This means that EASYFILE can be tailored to suit the needs of a wide variety of applications either in business or in the home. CLUB MANAGER CMG 6440 (diskette) CLUB MANAGER has been designed to aid in the smooth running of sports clubs, social clubs, associations -- in fact any organization that needs to maintain accurate membership records. The package allows you to record the details of all the members of your club on diskette, much as records are stored within a filing cabinet. Membership details can be amended where necessary and records can be added to or deleted from the membership file. CLUB MANAGER enables you to produce membership lists, subscription reminders, address labels, and, because the package can be linked to the EASY SCRIPT word processor, personalized copies of standard letters. CLUB MANAGER also has a booking facility allowing you to enter details of when members wish to use squash courts, tennis courts, snooker tables, restaurant tables, dance tickets or any similar club facility or activity. Overbooking is now a thing of the past. CLUB MANAGER allows you to maintain a diary and use it to record/amend details of appointments, meetings, etc. CLUB MANAGER is an ideal tool for the club owner or club secretary and will greatly reduce the amount of time spent on maintaining membership records and booking club facilities. FUTURE FINANCE FFI 6440 (diskette) FUTURE FINANCE is a low-cost, financial planning package. It enables you to predict your company's profit and cash-flow position based on expected production, sales and costs. Details can be altered to view the effect of these changes on the company's overall performance. Reports can be produced showing the contribution to profits made by each product and the cash-flow position at the end of each user-defined period. EASYCALC ECL 6440 (diskette) EASYCALC is an electronic spreadsheet package. It contains all the traditional spreadsheet features -- user-defined sheet size, replication of information from one area of the sheet to the other etc. Allied to these facilities, EASYCALC includes many other features including a library of trigonometrical, statistical and other advanced mathematical functions, the ability to draw graphs in a specific area of the sheet, data protection via a password option and much, much more. EASY STOCK EST 6440 (diskette) EASY STOCK is a powerful inventory system containing a wide range of stock-recording and reporting features. The details of each stock item are entered directly from the keyboard onto the screen and then stored on diskette. EASY STOCK also allows you to change the price of an individual item or a range of products on the stock file. Each stock record is accessed by simply typing in the reference/part number of that item. Records can be amended, added to your stock file or deleted from it. If the amount of stock on hand falls below your specified minimum level, the stock figure is highlighted when the record is accessed. EASY STOCK allows you to produce a wide range of reports including stock levels, analysis of stock movements, sales/stock valuation analyses and much more. EASY SCRIPT ESC 6440 (diskette) EASY SCRIPT is a professional, low cost, word-processing package. It enables you to create, modify and print text quickly and easily. EASY SCRIPT can be used for writing letters, reports, memos, book manuscripts -- in fact any kind of document. Text can be stored on diskette or cassette so that it may be printed or modified as required. EASY SPELL ESP 6440 (diskette) EASY SPELL is a spelling checker for files produced by the EASY SCRIPT word processing package. It can be used to check text in individual EASY SCRIPT files or text that is spread over files that have been linked together. The EASY SPELL package comes complete with a dictionary diskette against which the spelling of text is checked. Aids for the Programmer To assist in the development of your own software, Commodore has introduced a range of programming utilities. These will help speed the entry and debugging of BASIC and machine code programs. SIMON'S BASIC SIB 6410 (cartridge) SIMON'S BASIC has been designed to enable programmers of all levels to easily utilize the potential of their COMMODORE 64. The SIMON'S BASIC cartridge is really three packages in one. It contains a Toolkit to remove the tedious aspects of computer programming, a vast range of commands to facilitate the use of graphics and sound on the 64 and Structured Programming commands to help the programmer write more meaningful code. The package is supplied in cartridge form which means that you can use all its features by simply inserting it into the slot at the rear of the COMMODORE 64 and turning the computer on -- it's as simple as that. You then use the additional SIMON'S BASIC commands just as you would any other BASIC commands. Toolkit commands include: o AUTO - for automatic line numbering o RENUMBER - for automatic program re-numbering o KEY - to assign commands to the function keys and many more. Graphics commands include: o HIRES - to put the screen into high-resolution mode o REC - to draw a rectangular shape o CIRCLE - to draw a circular shape o PAINT - to fill a shape with color plus commands for creating sprites and user-defined graphics: o DESIGN - to set up a design grid for a sprite or user-defined character o MMOB - to move a sprite o DETECT - to detect sprite collision and much, much more. The Structured-Programming commands supplied by the SIMON'S BASIC cartridge are a boon to programmers of all levels of ability. It is now possible to label BASIC routines and call these routines by name. Other structured-programming commands include: o PROC - to label BASIC routines o CALL - to pass execution to a routine o EXEC - to pass execution to a routine and return from it when the routine has been completed o REPEAT...UNTIL - to repeat a loop dependent on a condition test and many others. SIMON'S BASIC also includes commands for screen formatting, scrolling the screen, input validation, character string manipulation, hexadecimal to decimal and binary to decimal conversion, integer division and much, much more. The cartridge also has a group of commands which allow you to trap certain BASIC errors. You can even generate your own error messages! The range of commands supplied by the SIMON'S BASIC cartridge make it an essential tool for any programmer who wants to easily utilize the special features of his COMMODORE 64. Works with cassette or diskette. ASSEMBLER TUTOR AST 6440 (diskette) AST 6420 (cassette) The ASSEMBLER TUTOR package is a must for all would-be machine code programmers. It can also be valuable to those programmers who already know something about assembly language programming but wish to expand their knowledge of 6502 machine code. The ASSEMBLER TUTOR is divided into three modules. Each module covers one aspect of assembly-language programming and contains an introduction, a self-test and discussion of various aspects of assembly-language programming. ASSEMBLER DEVELOPMENT ASM 6440 (diskette) The ASSEMBLER DEVELOPMENT package allows you to program in assembler directly onto your COMMODORE 64. It provides all the tools the assembler programmer needs to create, assemble load and execute 6510 assembly language code. PROGRAMMER'S UTILITIES UTL 6440 (diskette) The PROGRAMMER'S UTILITIES package contains many useful routines to help both the new and experienced programmer to get the most from his COMMODORE 64. These include Disk-Handling routines for changing the device number of a disk drive and copying disks using a single disk drive, graphics utilities such as a sprite and character editor, sound commands and BASIC programming aids for easier screen formatting and control operations. ENTERTAINMENT As well as a wide range of top quality arcade-style games for the COMMODORE 64, Commodore have also produced a range of Business Simulation programs for those who prefer to exercise their brain rather than their joystick fire button finger. In these games, time is no restriction, only your capabilities to work out complex scenarios. LABYRINTH LBY 6420 (cassette) Dare you enter the twisting Elizabethan maze? Will you ever get out, or will you be trapped forever? LOST? Well you can take a quick peek at where you are but remember that this reduces your score. Certainly a game to lose yourself in. HIGH FLYER HFL 6440 (diskette) It's 1945. The War has just ended and you have decided to run your own airline. By making careful management decisions, you have to guide the enterprise from 1945 up to the present day. The decisions are all yours -- plane schedules and routes; what is the best cargo/passenger ratio to maximize profit; when is the best time to extend your fleet, make improvements to existing stock, enhance support services; whether or not you need to borrow money from the hank and which banks can offer you the best deal etc. You can save the position you have reached until the next time you wish to join the high-flyers. Available on diskette only. RAIL BOSS RBO 6440 (diskette) You are a pioneer railwayman in charge of building a line in the American West between Base City and Junction City. It's your job to hire and fire surveyors, workers and guards to protect you and your workforce against marauding bandits. By building stations along the route, you can generate income to pay your workforce and buy additional stock should you require it. To thwart your efforts, warlike Indians try to disrupt your work by killing members of the workforce and ripping up the track. Your only hope is that the cavalry from Fort Commodore can get to the Indians before they get to you. A game for budding pioneersmen everywhere. OCEAN RACER OCR 6440 (diskette) You have entered the round-the-world yacht race. The race starts from Portsmouth and goes via Cape Town South Africa, Auckland New Zealand, Rio de Janeiro in Brazil and, finally, back to Portsmouth. You choose the type of ship you wish to captain: a single-masted cutter/sloop; a twin- masted ketch or a single-masted multi-hull boat. The race is in four stages, each of which contains various hazards ranging from icebergs to boat damage caused by passing whales! You decide which route to sail and how much sail to select for the prevailing wind conditions. A game for old salts and aspiring mariners alike. These are just the first of a series of thinking games especially designed for the COMMODORE 64. More are being developed all the time. For details of release dates, please keep in close touch with your local Commodore stockist. APPENDIX B DESCRIPTION OF DOS ERROR MESSAGES NOTE: Error message numbers less than 20 should be ignored with the exception of 01 which gives information about the number of files scratched with the SCRATCH command. 20: READ ERROR (block header not found) The disk controller is unable to locate the header of the requested data block. Caused by an illegal sector number, or the header has been destroyed. 21: READ ERROR (no sync character) The disk controller is unable to detect a sync mark on the desired track. Caused by misalignment of the read/writer head, no diskette is present, or unformatted or improperly seated diskette. Can also indicate a hardware failure. 22: READ ERROR (data block not present) The disk controller has been requested to read or verify a data block that was not properly written. This error message occurs in conjunction with the BLOCK commands and indicates an illegal track and/or block request. 23: READ ERROR (checksum error in data block) This error message indicates that there is an error in one or more of the data bytes. The data has been read into the DOS memory, but the checksum over the data is in error. This message may also indicate grounding problems. 24: READ ERROR (byte decoding error) The data or header has been read into the DOS memory, but a hardware error has been created due to an invalid bit pattern in the data byte. This message may also indicate grounding problems. 25: WRITE ERROR (write-verify error) This message is generated if the controller detects a mismatch between the written data and the data in the DOS memory. 26: WRITE PROTECT ON This message is generated when the controller has been requested to write a data block while the write protect switch is depressed. Typically, this is caused by using a diskette with a write a protect tab over the notch. 27: READ ERROR (checksum error in header) The controller has detected an error in the header of the requested data block. The block has not been read into the DOS memory. This message may also indicate grounding problems. 28: WRITE ERROR (long data block) The controller attempts to detect the sync mark of the next header after writing a data block. If the sync mark does not appear within a predetermined time, the error message is generated. The error is caused by a bad diskette format (the data extends into the next block), or by hardware failure. 29: DISK ID MISMATCH This message is generated when the controller has been requested to access a diskette which has not been initialized. The message can also occur if a diskette has a bad header. 30: SYNTAX ERROR (general syntax) The DOS cannot interpret the command sent to the command channel. Typically, this is caused by an illegal number of file names, or patterns are illegally used. For example, two file names may appear on the left side of the COPY command. 31: SYNTAX ERROR (invalid command) The DOS does not recognize the command. The command must start in the first position. 32: SYNTAX ERROR (invalid command) The command sent is longer than 58 characters. 33: SYNTAX ERROR (invalid file name) Pattern matching is invalidly used in the OPEN or SAVE command. 34: SYNTAX ERROR (no file given) The file name was left out of a command or the DOS does not recognize it as such. Typically, a colon (:) has been left out of the command. 39: SYNTAX ERROR (invalid command) This error may result if the command sent to command channel (secondary address 15) is unrecognized by the DOS. 50: RECORD NOT PRESENT Result of disk reading past the last record through INPUT#, or GET# commands. This message will also occur after positioning to a record beyond end of file in a relative file. If the intent is to expand the file by adding the new record (with a PRINT# command), the error message may be ignored. INPUT or GET should not be attempted after this error is detected without first repositioning. 51: OVERFLOW IN RECORD PRINT# statement exceeds record boundary. Information is truncated. Since the carriage return which is sent as a record terminator is counted in the record size, this message will occur if the total characters in the record (including the final carriage return) exceeds the defined size. 52: FILE TOO LARGE Record position within a relative file indicates that disk overflow will result. 60: WRITE FILE OPEN This message is generated when a write file that has not been closed is being opened for reading. 61: FILE NOT OPEN This message is generated when a file is being accessed that has not been opened in the DOS. Sometimes, in this case, a message is not generated; the request is simply ignored. 62: FILE NOT FOUND The requested file does not exist on the indicated drive. 63: FILE EXISTS The file name of the file being created already exists on the diskette. 64: FILE TYPE MISMATCH The file type does not match the file type in the directory entry for the requested file. 65: NO BLOCK This message occurs in conjunction with the B-A command. It indicates that the block to be allocated has been previously allocated. The parameters indicate the track and sector available with the next highest number. If the parameters are zero (0), then all blocks higher in number are in use. 66: ILLEGAL TRACK AND SECTOR The DOS has attempted to access a track or block which does not exist in the format being used. This may indicate a problem reading the pointer to the next block. 67: ILLEGAL SYSTEM T OR S This special error message indicates an illegal system track or block. 70: NO CHANNEL (available) The requested channel is not available, or all channels are in use. A maximum of five sequential files may be opened at one time to the DOS. Direct access channels may have six opened files. 71: DIRECTORY ERROR The BAM does not match the internal count. There is a problem in the BAM allocation or the BAM has been overwritten in DOS memory. To correct this problem, reinitialize the diskette to restore the BAM in memory. Some active files may be terminated by the corrective action. NOTE: BAM = Block Availability Map. 72: DISK FULL Either the blocks on the diskette are used or the directory is at its entry limit. DISK FULL is sent when two blocks are available on the 1541 to allow the current file to be closed. 73: DOS MISMATCH (73, CBM DOS V2.6 1541) DOS 1 and 2 are read compatible but not write compatible. Disks may be interchangeably read with either DOS, but a disk formatted on one version cannot be written upon with the other version because the format is different. This error is displayed whenever an attempt is made to write upon a disk which has been formatted in a non- compatible format. (A utility routine is available to assist in converting from one format to another.) This message may also appear after power up. 74: DRIVE NOT READY An attempt has been made to access the 1541 single Drive Floppy Disk without any diskettes present in either drive. APPENDIX C COMMODORE 64 BASIC This manual has given you an introduction to the BASIC language -- enough for you to get a feel for computer programming and some of the vocabulary involved. This appendix gives a complete list of the rules (SYNTAX) of 64 BASIC, along with concise descriptions. Please experiment with these commands. Remember, you can't damage the computer by just typing in programs, and the best way to learn computing is by experimenting. This appendix is divided into sections according to the different types of operations in BASIC. These include: 1. Variables and Operators: describes the different type of variables, legal variable names, and arithmetic and logical operators. 2. Commands: describes the commands used to work with programs, such as editing, storing and erasing. 3. Statements: describes the BASIC program statements used in numbered lines of programs. 4. Functions: describes the string, numeric, and print functions. VARIABLES The Commodore 64 uses three types of variables in BASIC. These are real numeric, integer numeric, and string (alphanumeric) variables. Variable names may consist of a single letter, a letter followed by a number, or two letters. An integer variable is specified by using the percent (%) sign after the variable name. String variable have the dollar sign ($) after their name. Examples Real Variable Names: A, A5, BZ Integer Variable Names: A%, A5%, BZ% String Variable Names: A$, A5$, BZ$ Arrays are lists of variables with the same name, using numbers called subscripts to specify the element of the array. Arrays are defined using the DIM statement, and may contain floating point, integer, or string variables. The array variable name is followed by a set of parentheses ( ) enclosing the number of variables in the list. A(7), BZ%(11), A$(50), PT(20,20) NOTE: There are three variable names which are reserved for use by the 64, and may not be defined by you. These variables are: ST, TI and TI$. ST is a status variable which relates to input/output operations. The value of ST will change if there is a problem loading a program from disk or tape. TI and TI$ are variables which relate to the real-time clock built into the 64. The variable TI is updated every 1/60th of a second. It starts at 0 when the computer is turned on, and is reset only by changing the value of TI$. TI$ is a string which is constantly updated by the system. The first two characters contain the number of hours, the 3rd and 4th characters the number of minutes, and the 5th and 6th characters are the number of seconds. This variable can be given any numeric value, and will be updated from that point. TI$ = "101530" sets the clock to 10:15 and 30 seconds AM. This clock is erased when the computer is turned off, and starts at zero when the system is turned back on. OPERATORS The arithmetic operators include the following signs: + Addition - Subtraction * Multiplication / Division ^ Raising to a power (exponentiation) On a line containing more than one operator, there is a set order in which operations always occur. If several operations are used together on the same line, the computer assigns priorities as follows: First, exponentiation. Next, multiplication and division, and last, addition and subtraction. You can change the order of operations by enclosing within parentheses the calculation to be performed first. Operations enclosed in parentheses will take place before other operations. There are also operations for equalities and inequalities: = Equal To < Less Than > Greater Than <= Less Than or Equal To >= Greater Than or Equal To <> Not Equal To Finally, there are three logical operators: AND OR NOT These are used most often to join multiple formulas in IF...THEN statements. For example: IF A=B AND C=D THEN 100 (Requires both parts to be true) IF A=B OR C=D THEN 100 (Allows either part to be true) COMMANDS CONT (Continue) This command is used to restart the execution of a program which has been stopped by either using the key (but not & ), a STOP statement, or an END statement within the program. The program will restart at the exact place from where it left off. CONT will not work if you have changed or added lines to the program, or if the program halted due to an error, or if you caused an error before trying to restart the program. In these cases you will get a CAN'T CONTINUE ERROR. LIST The LIST command allows you to look at lines of a BASIC program in memory. You can ask for the entire program to be displayed, or only certain line numbers. LIST Shows entire program LIST 10- Shows only from line 10 until end LIST 10 Shows only line 10 LIST -10 Shows lines from beginning until 10 LIST 10-20 Shows line from 10 to 20, inclusive LOAD This command is used to transfer a program from tape or disk into memory so the program can be used. If you just type LOAD and hit , the first program found on the cassette unit will be placed in memory. The command may be followed by a program name enclosed within quotes. The name may then be followed by a comma and a number or numeric variable, which acts as a device number to indicate where the program is coming from. If no device number is given, the COMMODORE 64 assumes device #1, which is the cassette unit. The other device commonly used with the LOAD command is the disk device, which is device #8. LOAD Reads in the next program on tape LOAD "HELLO" Searches tape for program called HELLO, and loads program if found LOAD A$ Looks for program whose name is in the variable A$ LOAD "HELLO",8 Looks for program called HELLO on the disk drive LOAD "*",8 Looks for first program on disk A secondary address of 1 must be specified if you want to load a machine code program without relocating it. LOAD "M/C PROGRAM",1,1 Loads machine code from tape without relocating NEW This command erases the entire program in memory, and also clears out any variables that may have been used. Unless the program was SAVEd, it is lost. BE CAREFUL WHEN YOU USE THIS COMMAND. The NEW command can also be used as a BASIC program statement. When the program reaches this line, the program is erased. This is useful if you want to leave everything neat when the program is done. RUN This command causes execution of a program, once the program is loaded into memory. If there is no line number following RUN, the computer will start with the lowest line number. If a line number is designated, the program will start executing from the specified line. RUN Starts program at lowest line number RUN 100 Starts execution at line 100 RUN X UNDEFINED STATEMENT ERROR. You must always specify an actual line number, not a variable representation SAVE This command will store the program currently in memory on cassette or disk. If you just type SAVE and , the program will be SAVEd on cassette. The computer has no way of knowing if there is a program already on that tape, so be careful with your tapes or you may erase a valuable program. If you type SAVE followed by a name in quotes or a string variable, the computer will give the program that name, so it can be more easily located and retrieved in the future. The name may also be followed by a device number. After the device number, there can be a comma and a second number, either 0 or 1. If the second number is 1, the COMMODORE 64 will put an END-OF-TAPE marker after your program. This signals the computer not to look any further on the tape if you were to give an additional LOAD command. If you try to LOAD a program and the computer finds one of these markers, you will get a FILE NOT FOUND ERROR. SAVE Stores program to tape without name SAVE "HELLO" Stores on tape with name HELLO SAVE A$ Stores on tape with name A$ SAVE "HELLO",8 Stores on disk with name HELLO SAVE "HELLO",1,1 Stores on tape with name HELLO and reloads in same position of memory SAVE "HELLO",1,2 Stores on tape with name HELLO and follows program with END-OF-TAPE marker SAVE "HELLO",1,3 As above but reloads in same position of memory VERIFY This command causes the computer to check the program on disk or tape against the one in memory. This is proof that the program is actually SAVEd, in case the tape or disk is bad, or something went wrong during the SAVE. VERIFY without anything after the command causes the COMMODORE 64 to check the next program on tape, regardless of name, against the program in memory. VERIFY followed by a program name, or a string variable, will search for that program and then check. Device numbers can also be included with the verify command. VERIFY Checks the next program on tape VERIFY "HELLO" Searches for HELLO, checks against memory VERIFY "HELLO",8 Searches for HELLO on disk, then checks To check if a program is already on a tape, just VERIFY and the computer will say which program it has found (if any). STATEMENTS CLOSE This command completes and closes any files used by OPEN statements. The number following CLOSE is the file number to be closed. CLOSE 2 Only file #2 is closed CLR This command will erase any variables in memory, but leaves the program itself intact. This command is automatically executed when a RUN command is given. CMD CMD sends the output which normally would go to the screen (i.e., PRINT statements, LISTs, but not POKEs onto the screen) to another device instead. This could be a printer, or a data file on disk. This device or file must be OPENed first. The CMD command must be followed by a number or numeric variable referring to the file. OPEN 1,4 OPENs device #4, which is the printer CMD 1 All normal output now goes to printer LIST The program listing now goes to the printer, not the screen To send output back to the screen, CLOSE the file with CLOSE 1. DATA This statement is followed by a list of items to be used by READ statements. Items may be numeric values or text strings, and items are separated by commas. String items need not be inside quote marks unless they contain space, colon, or comma. If two commas have nothing between them, the value will be READ as a zero for a number, or an empty string. DATA 12, 14.5, "HELLO, MOM", 3.14, PART1 DEF FN This command allows you to define a complex calculation as a function with a short name. In the case of a long formula that is used many times within the program, this can save time and space. This function name will be FN and any legal variable name (1 or 2 characters long). First you must define the function using the statement DEF followed by the function name. Following the name is a set of parentheses enclosing a numeric variable. Then follows the actual formula that you want to define, with the variable in the proper spot. You can then "call" the formula, substituting any number for the variable. 10 DEF FN A(X) = 12 * ( 34.75 - X / .3 ) 20 PRINT FN A(7) ^ ^ | | | 7 is inserted where +-----------------+ X is in the formula For this example, the result would be 137. DIM When you use more than 11 elements of an array, you must execute a DIM statement for the array. Keep in mind that the whole array takes up room in memory, so don't create an array much larger than you'll need. To figure the number of variables created with DIM, multiply the total number of elements plus one in each dimension of the array. 10 DIM A$(40), B7(15), CC%(4,4,4) ^ ^ ^ | | | 41 elements 16 elements 125 elements You can dimension more than one array in a DIM statement. However, be careful not to dimension an array more than once. END When a program encounters an END statement, the program halts, as if it ran out of lines. You may use CONT to restart the program. FOR ... TO ... STEP This statement works with the NEXT statement to repeat a section of the program a set number of times. The format is: FOR (Var. Name)=(Start of Count) TO (End of Count) STEP (Count By) The loop variable will be added to or subtracted from during the program. Without any STEP specified, STEP is assumed to be 1. The start count and end count are the limits to the value of the loop variable. 10 FOR L = 1 TO 10 STEP .1 20 PRINT L 30 NEXT L The end of the loop value may be followed by the word STEP and another number or variable. In this case, the value following STEP is added each time instead of 1. This allows you to count backwards, or by fractions. GET The GET statement allows you to get data from the keyboard, one character at a time. When GET is executed, the character that is typed is assigned to the variable. If no character is typed, then a null (empty) character is assigned. GET is followed by a variable name, usually a string variable. If a numeric variable was used and a nonnumeric key depressed, the program would halt with an error message. The GET statement may be placed into a loop, checking for any empty result. This loop will continue until a key is hit. 10 GET A$: IF A$ = "" THEN 10 GET# The GET# statement is used with a previously OPENed device or file, to input one character at a time from that device or file. GET#1,A$ This would input one character from a data file. GOSUB This statement is similar to GOTO, except the computer remembers which program line it last executed before the GOSUB. When a line with a RETURN statement is encountered, the program jumps back to the statement immediately following the GOSUB. This is useful if there is a routine in your program that occurs in several parts of the program. Instead of typing the routine over and over, execute GOSUBs each time the routine is needed. 20 GOSUB 800 GOTO or GO TO When a statement with the GOTO command is reached, the next line to be executed will be the one with the line number following the word GOTO. IF ... THEN IF ... THEN lets the computer analyze a situation and take two possible courses of action, depending on the outcome. If the expression is true, the statement following THEN is executed. This may be any BASIC statement. If the expression is false, the program goes directly to the next line. The expression being evaluated may be a variable or formula, in which case it is considered true if nonzero, and false if zero. In most cases, there is an expression involving relational operators (=, <, >, <=, >=, <>, AND, OR, NOT). 10 IF X > 10 THEN END INPUT The INPUT statement allows the program to get data from the user, assigning that data to a variable. The program will stop, print a question mark (?) on the screen, and wait for the user to type in the answer and hit . INPUT is followed by a variable name, or a list of variable names, separated by commas. A message may be placed within quote marks, before the list of variable names to be INPUT. If more than one variable is to be INPUT, they must be separated by commas when typed. 10 INPUT "PLEASE ENTER YOUR FIRST NAME";A$ 20 PRINT "ENTER YOUR CODE NUMBER";: INPUT B INPUT# INPUT# is similar to INPUT, but takes data from a previously OPENed file. 10 INPUT#1, A LET LET is hardly ever used in programs, since it is optional, but the statement is the heart of all BASIC programs. The variable name which is to be assigned the result of a calculation is on the left side of the equal sign, and the formula on the right. 10 LET A = 5 20 LET D$ = "HELLO" NEXT NEXT is always used in conjunction with the FOR statement. When the program reaches a NEXT statement, it checks the FOR statement to see if the limit of the loop has been reached. If the loop is not finished, the loop variable is increased by the specified STEP value. If the loop is finished, execution proceeds with the statement following NEXT. NEXT may be followed by a variable name, or list of variable names, separated by commas. If there are no names listed, the last loop started is the one being completed. If variables are given, they are completed in order from left to right. 10 FOR X = 1 TO 100: NEXT ON This command turns the GOTO and GOSUB commands into special versions of the IF statement. ON is followed by a formula, which is evaluated. If the result of the calculation is one, the first line on the list is executed; if the result is 2, the second line is executed, and so on. If the result is 0, negative, or larger than the list of numbers, the next line executed will be the statement following the ON statement. 10 INPUT X 20 ON X GOTO 10,20,30,40,50 OPEN Then OPEN statement allows the COMMODORE 64 to access devices such as the disk for data, a printer, or even the screen. OPEN is followed by a number (0-255), to which all following statements will refer. There is usually a second number after the first, which is the device number. The device numbers are: 0 Screen 1 Cassette 4 Printer 8 Disk Following the device number may be a third number, separated again by a a comma, which is the secondary address. In the case of the disk, the number refers to the buffer, or channel, number. In the printer, the secondary address controls features like expanded printing. See the Commodore 64 Programmer's Reference Manual for more details. OPEN 1,0 OPENs the SCREEN as a device OPEN 2,8,8,"D" OPENs the disk for reading, file to be searched for is D OPEN 3,4 OPENs the printer OPEN 4,8,15 OPENs the data channel on the disk Also see: CLOSE, CMD, GET#, INPUT#, and PRINT#, system variable ST, and Appendix B. POKE POKE is always followed by two numbers, or formulas. The first location is a memory location; the second number is a decimal value from 0 to 255, which will be placed in the memory location, replacing any previously stored value. 10 POKE 53281,0 20 S = 4096 * 13 30 POKE S + 29,8 PRINT The PRINT statement is the first one most people learn to use, but there are a number of variations to be aware of. PRINT can be followed by: Text String with quotes Variable names Functions Punctuation marks Punctuation marks are used to help format the data on the screen. The comma divides the screen into four columns, while the semicolon suppresses all spacing. Either mark can be the last symbol on a line. This results in the next thing PRINTed acting as if it were a continuation of the same PRINT statement. 10 PRINT "HELLO" 20 PRINT "HELLO", A$ 30 PRINT A + B 40 PRINT J; 50 PRINT A,B,C,D Also see: POS, SPC and TAB functions. PRINT# There are a few differences between this statement and PRINT. PRINT# is followed by a number, which refers to the device or data file previously OPENed. This number is followed by a comma and a list to be printed. The comma and semicolon have the same effect as they do in PRINT. Please note that some devices may not work with TAB and SPC. 100 PRINT#1, "DATA VALUES"; A%, B1, C$ READ READ is used to assign information from DATA statements to variables, so the information may be put to use. Care must be taken to avoid READing strings where READ is expecting a number, which will give a TYPE MISMATCH ERROR. REM (Remark) REMark is a note to whomever is reading a LIST of the program. It may explain a section of the program, or give additional instructions. REM statements in no way affect the operation of the program, except to add to its length. REM may be followed by any text. RESTORE When executed in a program, the pointer to which an item in a DATA statement will be READ next is reset to the first item in the list. This gives you the ability to re-READ the information. RESTORE stands by itself on a line. RETURN This statement is always used in conjunction with GOSUB. When the program encounters a RETURN, it will go to the statement immediately following the GOSUB command. If no GOSUB was previously issued, a RETURN WITHOUT GOSUB ERROR will occur. STOP This statement will halt program execution. The message, BREAK IN xxx will be displayed, where xxx is the line number containing STOP. The program may be restarted by using the CONT command. STOP is normally used in debugging a program. SYS SYS is followed by a decimal number or numeric value in the range 0-65535. The program will then begin executing the machine language program starting at that memory location. This is similar to the USR function, but does not allow parameter passing. WAIT WAIT is used to halt the program until the contents of a memory location changes in a specific way. WAIT is followed by a memory location (X) and up to two variables. The format is: WAIT X,Y,Z The contents of the memory location are first exclusive-ORed with the third number, if present, and then logically ANDed with the second number. If the result is zero, the program goes back to that memory location and checks again. When the result is nonzero, the program continues with the next statement. NUMERIC FUNCTIONS ABS(X) (absolute value) ABS returns the absolute value of the number, without its sign (+ or -). The answer is always positive. ATN(X) (arctangent) Returns the angle, measured in radians, whose tangent is X. COS(X) (cosine) Returns the value of the cosine of X, where X is an angle measured in radians. EXP(X) Returns the value of the mathematical constant e (2.71828183) raised to the power of X. FN xx(X) Returns the value of the user-defined function xx created in a DEF FN xx(X) statement. INT(X) Returns the truncated value of X, that is, with all the decimal places to the right of the decimal point removed. The result will always be less than, or equal to, X. Thus, any negative numbers with decimal places will become the integer less than their current value. LOG(X) (logarithm) Will return the natural log of X. The natural log to the base e (see EXP(X)). To convert to log base 10, simply divide by LOG(10). PEEK(X) Used to find out contents of memory location X, in the range 0-65535, giving a result from 0-255. PEEK is often used in conjunction with the POKE statement. RND(X) (random number) RND(X) returns a random number in the range 0-1. The first random number should be generated by the formula RND(-TI) to start things off differently every time. After this, X should be a 1 or any positive number. If X is zero, the result will be the same random number as the last one. A negative value for X will reseed the generator. The use of the same negative number for X will result in the same sequence of "random" numbers. The formula for generating a number between X and Y is: N = RND(1) * (Y-X) + X where, Y is the upper limit, X is the lower range of numbers desired. SGN(X) (sign) This function returns the sign (positive, negative, or zero) of X. The result will be +1 if positive, 0 if zero, and -1 if negative. SIN(X) (sine) SIN(X) is the trigonometric sine function. The result will be the sine of X, where X is an angle in radians. SQR(X) (square root) This function will return the square root of X, where X is a positive number or 0. If X is negative, an ILLEGAL QUANTITY ERROR results. TAN(X) (tangent) The result will be the tangent of X, where X is an angle in radians. USR(X) When this function is used, the program jumps to a machine language program whose starting point is contained in memory locations. The parameter X is passed to the machine language program, which will return another value back to the BASIC program. Refer to the Commodore 64 Programmer's Reference Manual for more details on this function and machine language programming. STRING FUNCTIONS ASC(X$) This function will return the ASCII code of the first character of X$. CHR$(X) This is the opposite of ASC, and returns a string character whose ASCII code is X. LEFT$(X$,X) Returns a string containing the leftmost X characters of X$. LEN(X$) Returned will be the number of characters (including spaces and other symbols) in the string X$. MID$(X$,S,X) This will return a string containing X characters starting from the Sth character in X$. RIGHT$(X$,X) Returns the rightmost X characters in X$. STR$(X) This will return a string which is identical to the PRINTed version of X. VAL(X$) This function converts X$ into a number, and is essentially the inverse operation from STR$. The string is examined from the leftmost character to the right, for as many characters as are in recognizable number format. 10 X = VAL("123.456") X = 123.456 10 X = VAL("12A13B") X = 12 10 X = VAL("RIU017") X = 0 10 X = VAL("-1.23.45.67") X = -1.23 OTHER FUNCTIONS FRE(X) This function returns the number of unused bytes available in memory, regardless of the value of X. Note that FRE(X) will read out in negative numbers if the number of unused bytes is over 32K. POS(X) This function returns the number of the column (0-39) at which the next PRINT statement will begin on the screen. X may have any value and is not used. SPC(X) This is used in a PRINT statement to skip X spaces forward. TAB(X) TAB is also used in a PRINT statement; the next item to be PRINTed will be in column X. APPENDIX D ABBREVIATIONS FOR BASIC KEYWORDS As a time-saver when typing in programs and commands, Commodore 64 BASIC allows the user to abbreviate most keywords. The abbreviation for PRINT is a question mark. The abbreviations for other words are made by typing the first one or two letters of the word, followed by the SHIFTed next letter of the word. If the abbreviations are used in a program line, the keyword will LIST in the full form. Com- Abbrevi- Looks like | Com- Abbrevi- Looks like mand ation this on | mand ation this on screen | screen ------------------------------------+------------------------------------ ABS A | NOT N AND A | ON NONE ON ASC A | OPEN O ATN A | OR NONE OR CHR$ C | PEEK P CLOSE CL | POKE P CLR C | POS NONE POS CMD C | PRINT ? ? CONT C | PRINT# P COS NONE COS | READ R DATA D | REM NONE REM DEF D | RESTORE RE DIM D | RETURN RE END E | RIGHT$ R EXP E | RND R FN NONE FN | RUN R FOR F | SAVE S FRE F | SGN S GET G | SIN S GET# NONE GET# | SPC( S GOSUB GO | SQR S GOTO G | STATUS ST ST IF NONE IF | STEP ST INPUT NONE INPUT | STOP S INPUT# I | STR$ ST INT NONE INT | SYS S LEFT$ LE | TAB( T LEN NONE LEN | TAN NONE TAN LET L | THEN T LIST L SAVE | TIME TI TI LOAD L | TIME$ TI$ TI$ LOG NONE LOG | USR U MID$ M | VAL V NEW NONE NEW | VERIFY V NEXT N | WAIT W APPENDIX E SCREEN DISPLAY CODES The following chart lists all of the characters built into the Commodore 64 character sets. It shows which numbers should be POKED into screen memory (locations 1024-2023) to get a desired character. Also shown is which character corresponds to a number PEEKed from the screen. Two character sets are available, but only one set at a time. This means that you cannot have characters from one set on the screen at the same time you have characters from the other set displayed. The sets are switched by holding down the and keys simultaneously. From BASIC, POKE 53272,21 will switch to upper case mode and POKE 53272,23 switches to lower case. Any number on the chart may also be displayed in REVERSE. The reverse character code may be obtained by adding 128 to the values shown. If you want to display a solid circle at location 1504, POKE the code for the circle (81) into location 1504: POKE 1504,81. There is a corresponding memory location to control the color of each character displayed on the screen (locations 55296-56295). To change the color of the circle to yellow (color code 7) you would POKE the corresponding memory location (55776) with the character color: POKE 55776,7. Refer to Appendix G for the complete screen and color memory maps, along with color codes. SCREEN CODES SET 1 SET 2 POKE | SET 1 SET 2 POKE | SET 1 SET 2 POKE ------------------------+------------------------+----------------------- @ 0 | + 43 | V 86 A a 1 | , 44 | W 87 B b 2 | - 45 | X 88 C c 3 | . 46 | Y 89 D d 4 | / 47 | Z 90 E e 5 | 0 48 | 91 F f 6 | 1 49 | 92 G g 7 | 2 50 | 93 H h 8 | 3 51 | 94 I i 9 | 4 52 | 95 J j 10 | 5 53 | SPACE 96 K k 11 | 6 54 | 97 L l 12 | 7 55 | 98 M m 13 | 8 56 | 99 N n 14 | 9 57 | 100 O o 15 | : 58 | 101 P p 16 | ; 59 | 102 Q q 17 | < 60 | 103 R r 18 | = 61 | 104 S s 19 | > 62 | 105 T t 20 | ? 63 | 106 U u 21 | 64 | 107 V v 22 | A 65 | 108 W w 23 | B 66 | 109 X x 24 | C 67 | 110 Y y 25 | D 68 | 111 Z z 26 | E 69 | 112 [ 27 | F 70 | 113 pound 28 | G 71 | 114 ] 29 | H 72 | 115 ^ 30 | I 73 | 116 <- 31 | J 74 | 117 SPACE 32 | K 75 | 118 ! 33 | L 76 | 119 " 34 | M 77 | 120 # 35 | N 78 | 121 $ 36 | O 79 | 122 % 37 | P 80 | 123 & 38 | Q 81 | 124 ' 39 | R 82 | 125 ( 40 | S 83 | 126 ) 41 | T 84 | 127 * 42 | U 85 | ------------------------+------------------------+----------------------- Codes from 128-255 are reversed images of codes 0-127. APPENDIX F ASCII AND CHR$ CODES This appendix shows you what characters will appear if you PRINT CHR$(X), for all possible values of X. It will also show the values obtained by typing PRINT ASC("x"), where x is any character you can type. This is useful in evaluating the character received in a GET statement, converting upper/lower case, and printing character based commands (like switch to upper/lower case) that could not be enclosed in quotes. +-----------------+-----------------+-----------------+-----------------+ | PRINTS CHR$ | PRINTS CHR$ | PRINTS CHR$ | PRINTS CHR$ | +-----------------+-----------------+-----------------+-----------------+ | 0 | 0 48 | 96 | {black} 144 | | 1 | 1 49 | 97 | {up} 145 | | 2 | 2 50 | 98 | {rvs off} 146 | | 3 | 3 51 | 99 | {clear} 147 | | 4 | 4 52 | 100 | {inst} 148 | | {white} 5 | 5 53 | 101 | {brown} 149 | | 6 | 6 54 | 102 | {lt. red} 150 | | 7 | 7 55 | 103 | {grey 1} 151 | | disSHIFT+C= 8 | 8 56 | 104 | {grey 2} 152 | | enaSHIFT+C= 9 | 9 57 | 105 | {lt.green}153 | | 10 | : 58 | 106 | {lt.blue} 154 | | 11 | ; 59 | 107 | {grey 3} 155 | | 12 | < 60 | 108 | {purple} 156 | | return 13 | = 61 | 109 | {left} 157 | | lower case 14 | > 62 | 110 | {yellow} 158 | | 15 | ? 63 | 111 | {cyan} 159 | | 16 | @ 64 | 112 | SPACE 160 | | {down} 17 | A 65 | 113 | 161 | | {rvs on} 18 | B 66 | 114 | 162 | | {home} 19 | C 67 | 115 | 163 | | {del} 20 | D 68 | 116 | 164 | | 21 | E 69 | 117 | 165 | | 22 | F 70 | 118 | 166 | | 23 | G 71 | 119 | 167 | | 24 | H 72 | 120 | 168 | | 25 | I 73 | 121 | 169 | | 26 | J 74 | 122 | 170 | | 27 | K 75 | 123 | 171 | | {red} 28 | L 76 | 124 | 172 | | {right} 29 | M 77 | 125 | 173 | | {green} 30 | N 78 | 126 | 174 | | {blue} 31 | O 79 | 127 | 175 | | SPACE 32 | P 80 | 128 | 176 | | ! 33 | Q 81 | {orange} 129 | 177 | | " 34 | R 82 | 130 | 178 | | # 35 | S 83 | 131 | 179 | | $ 36 | T 84 | 132 | 180 | | % 37 | U 85 | f1 133 | 181 | | & 38 | V 86 | f3 134 | 182 | | ' 39 | W 87 | f5 135 | 183 | | ( 40 | X 88 | f7 136 | 184 | | ) 41 | Y 89 | f2 137 | 185 | | * 42 | Z 90 | f4 138 | 186 | | + 43 | [ 91 | f6 139 | 187 | | , 44 | pound 92 | f8 140 | 188 | | - 45 | ] 93 |shift+ret. 141 | 189 | | . 46 | ^ 94 |upper case 142 | 190 | | / 47 |{arrow left}95 | 143 | 191 | +-----------------+-----------------+-----------------+-----------------+ CODES 192-223 SAME AS 96-127 CODES 224-254 SAME AS 160-190 CODE 255 SAME AS 126 APPENDIX G SCREEN AND COLOR MEMORY MAPS The following charts list which memory locations control placing characters on the screen, and the locations used to change individual character colors, as well as showing character color codes. SCREEN MEMORY MAP COLUMN 1063 0 10 20 30 39 / +------------------------------------------------------------/ 1024 | | 0 1064 | | 1104 | | 1144 | | 1184 | | 1224 | | 1264 | | 1304 | | 1344 | | 1384 | | 1424 | | 10 1464 | | 1504 | | ROW 1544 | | 1584 | | 1624 | | 1664 | | 1704 | | 1744 | | 1784 | | 1824 | | 20 1864 | | 1904 | | 1944 | | 1984 | | 24 +------------------------------------------------------------\ \ 2023 The actual values to POKE into a color memory location to change a character's color are: 0 BLACK 8 ORANGE 1 WHITE 9 BROWN 2 RED 10 Light RED 3 CYAN 11 GRAY 1 4 PURPLE 12 GRAY 2 5 GREEN 13 Light GREEN 6 BLUE 14 Light BLUE 7 YELLOW 15 GRAY 3 For example, to change the color of a character located at the upper left-hand corner of the screen to red, type: POKE 55296,2. COLOR MEMORY MAP COLUMN 55335 0 10 20 30 39 / +------------------------------------------------------------/ 55296| | 0 55336| | 55376| | 55416| | 55456| | 55496| | 55536| | 55576| | 55616| | 55656| | 55696| | 10 55736| | 55776| | ROW 55816| | 55856| | 55896| | 55936| | 55976| | 56016| | 56056| | 56096| | 20 56136| | 56176| | 56216| | 56256| | 24 +------------------------------------------------------------\ 56295 APPENDIX H DERIVING MATHEMATICAL FUNCTIONS Functions that are not intrinsic to Commodore 64 BASIC may be calculated as follows: +-------------------------------+---------------------------------------+ | FUNCTION | BASIC EQUIVALENT | +-------------------------------+---------------------------------------+ | SECANT | SEC(X)=1/COS(X) | | COSECANT | CSC(X)=1/SIN(X) | | COTANGENT | COT(X)=1/TAN(X) | | INVERSE SINE | ARCSIN(X)=ATN(X/SQR(-X*X+1)) | | INVERSE COSINE | ARCCOS(X)=-ATN(X/SQR(-X*X+1))+{pi}/2 | | INVERSE SECANT | ARCSEC(X)=ATN(X/SQR(X*X-1)) | | INVERSE COSECANT | ARCCSC(X)=ATN(X/SQR(X*X-1)) | | | +(SGN(X)-1*{pi}/2 | | INVERSE COTANGENT | ARCOT(X)=ATN(X)+{pi}/2 | | HYPERBOLIC SINE | SINH(X)=(EXP(X)-EXP(-X))/2 | | HYPERBOLIC COSINE | COSH(X)=(EXP(X)+EXP(-X))/2 | | HYPERBOLIC TANGENT | TANH(X)=EXP(-X)/(EXP(X)+EXP(-X))*2+1 | | HYPERBOLIC SECANT | SECH(X)=2/(EXP(X)+EXP(-X)) | | HYPERBOLIC COSECANT | CSCH(X)=2/(EXP(X)-EXP(-X)) | | HYPERBOLIC COTANGENT | COTH(X)=EXP(-X)/(EXP(X)-EXP(-X))*2+1 | | INVERSE HYPERBOLIC SINE | ARCSINH(X)=LOG(X+SQR(X*X+1)) | | INVERSE HYPERBOLIC COSINE | ARCCOSH(X)=LOG(X+SQR(X*X-1)) | | INVERSE HYPERBOLIC TANGENT | ARCTANH(X)=LOG((1+X)/(1-X))/2 | | INVERSE HYPERBOLIC SECANT | ARCSECH(X)=LOG((SQR(-X*X+1)+1/X) | | INVERSE HYPERBOLIC COSECANT | ARCCSCH(X)=LOG((SGN(X)*SQR(X*X+1/X) | | INVERSE HYPERBOLIC COTANGENT | ARCCOTH(X)=LOG((X+1)/(X-1))/2 | +-------------------------------+---------------------------------------+ APPENDIX I PINOUTS FOR INPUT/OUTPUT DEVICES This appendix is designed to show you what connections may be made to the Commodore 64. 1) Game I/O 4) Serial I/O (Disk/Printer) 2) Cartridge Slot 5) Modulator Output 3) Audio/Video 6) Cassette 7) User Port Control Port 1 +---------+-------------------+---------------------------------------+ | Pin | Type | Note | +---------+-------------------+---------------------------------------+ | 1 | JOYA0 | | | 2 | JOYA1 | | | 3 | JOYA2 | | | 4 | JOYA3 | | | 5 | POT AY | | | 6 | BUTTON A/LP | | | 7 | +5V | MAX. 100mA | | 8 | GND | | | 9 | POT AX | | +---------+-------------------+---------------------------------------+ /---------------------\ | 1 2 3 4 5 | | O O O O O | | | | O O O O | | 6 7 8 9 | \_______________/ Control Port 2 +---------+-------------------+---------------------------------------+ | Pin | Type | Note | +---------+-------------------+---------------------------------------+ | 1 | JOYB0 | | | 2 | JOYB1 | | | 3 | JOYB2 | | | 4 | JOYB3 | | | 5 | POT BY | | | 6 | BUTTON B | | | 7 | +5V | MAX. 100mA | | 8 | GND | | | 9 | POT BX | | +---------+-------------------+---------------------------------------+ Cartridge Expansion Slot +-----------+------------------+ +-----------+------------------+ | Pin | Type | | Pin | Type | +-----------+------------------+ +-----------+------------------+ | 1 | GND | | 12 | BA | | 2 | +5V | | 13 | /DMA | | 3 | +5V | | 14 | D7 | | 4 | /IRQ | | 15 | D6 | | 5 | R/W | | 16 | D5 | | 6 | Dot Clock | | 17 | D4 | | 7 | I/O1 | | 18 | D3 | | 8 | /GAME | | 19 | D2 | | 9 | /EXROM | | 20 | D1 | | 10 | I/O2 | | 21 | D0 | | 11 | /ROML | | 22 | GND | +-----------+------------------+ +-----------+------------------+ +-----------+------------------+ +-----------+------------------+ | Pin | Type | | Pin | Type | +-----------+------------------+ +-----------+------------------+ | A | GND | | N | A9 | | B | /ROMH | | P | A8 | | C | /RESET | | R | A7 | | D | /NMI | | S | A6 | | E | 02 | | T | A5 | | F | A15 | | U | A4 | | H | A14 | | V | A3 | | J | A13 | | W | A2 | | K | A12 | | X | A1 | | L | A11 | | Y | A0 | | M | A10 | | Z | GND | +-----------+------------------+ +-----------+------------------+ 2 2 2 1 1 1 1 1 1 1 1 1 1 2 1 0 9 8 7 6 5 4 3 2 1 0 9 8 7 6 5 4 3 2 1 +---@-@-@-@-@-@-@-@-@-@-@-@-@-@-@-@-@-@-@-@-@-@---+ | | +---@-@-@-@-@-@-@-@-@-@-@-@-@-@-@-@-@-@-@-@-@-@---+ Z Y X W V U T S R P N M L K J H F E D C B A Audio/Video ++ ++ +--------------------------+------------------+ / +-+ \ | Pin | Type | Note | / \ +--------+-----------------+------------------+ + + | 1 | LUMINANCE | | |3O O1| | 2 | GND | | | | | 3 | AUDIO OUT | | + O O + | 4 | VIDEO OUT | | \5 O 4/ | 5 | AUDIO IN | | \ 2 / +--------+-----------------+------------------+ +---+ Cassette +-------+-------------------------------------+ | Pin | Type | +-------+-------------------------------------+ | A-1 | GND | 1 2 3 4 5 6 | B-2 | +5V | +---@-@-@-@-@-@---+ | C-3 | CASSETTE MOTOR | | | | D-4 | CASSETTE READ | +---@-@-@-@-@-@---+ | E-5 | CASSETTE WRITE | A B C D E F | F-6 | CASSETTE SENSE | +-------+-------------------------------------+ Serial I/O ++ ++ +---------------------------------------------+ / +-+ \ | Pin | Type | /5 1\ +--------+------------------------------------+ + O O + | 1 | SERIAL /SRQIN | | 6 | | 2 | GND | | O | | 3 | SERIAL ATN OUT | | | | 4 | SERIAL CLK IN/OUT | + O O + | 5 | SERIAL DATA IN/OUT | \4 O 2/ | 6 | /RESET | \ 3 / +--------+------------------------------------+ +---+ User I/O +-----------+--------------------+------------------------------------+ | Pin | Type | Note | +-----------+--------------------+------------------------------------+ | 1 | GND | | | 2 | +5V | MAX. 100 mA | | 3 | /RESET | | | 4 | CNT1 | | | 5 | SP1 | | | 6 | CNT2 | | | 7 | SP2 | | | 8 | /PC2 | | | 9 | SER. ATN OUT | | | 10 | 9 VAC | MAX. 100 mA | | 11 | 9 VAC | MAX. 100 mA | | 12 | GND | | +-----------+--------------------+------------------------------------+ +-----------+--------------------+------------------------------------+ | Pin | Type | Note | +-----------+--------------------+------------------------------------+ | A | GND | | | B | /FLAG2 | | | C | PB0 | | | D | PB1 | | | E | PB2 | | | F | PB3 | | | H | PB4 | | | I | PB5 | | | K | PB6 | | | L | PB7 | | | M | PA2 | | | N | GND | | +-----------+--------------------+------------------------------------+ 1 1 1 1 2 3 4 5 6 7 8 9 0 1 2 +--@-@-@-@-@-@-@-@-@-@-@-@--+ | | +--@-@-@-@-@-@-@-@-@-@-@-@--+ A B C D E F H J K L M N APPENDIX J PROGRAMS TO TRY We've included a number of useful programs for you to try with your Commodore 64. These programs will prove both entertaining and useful. start tok64 jotto.prg 100 print "{down}jotto{space*7}jim butterfield" 120 input "{down}want instructions";z$:if asc(z$)=78 goto 250 130 print "{down}try to guess the mystery 5-letter word" 140 print "{down}you must guess only legal 5-letter" 150 print "words, too..." 160 print "you will be told the number of matches" 170 print "(or 'jots') of your guess." 180 print "{down}hint: the trick is to vary slightly" 190 print " from one guess to the next; so that" 200 print " if you guess 'batch' and get 2 jots" 210 print " you might try 'botch' or 'chart'" 220 print " for the next guess..." 250 data bxbsf,ipccz,dbdif,esfbe,pggbm 260 data hpshf,ibudi,djwjm,kpmmz,lbzbl 270 data sbkbi,mfwfm,njnjd,boofy,qjqfs 280 data rvftu,sjwfs,qsftt,puufs,fwfou 290 data xfbwf,fyupm,nvtiz,afcsb,gjaaz 300 data uijdl,esvol,gmppe,ujhfs,gblfs 310 data cppui,mzjoh,trvbu,hbvaf,pxjoh 320 data uisff,tjhiu,bymft,hsvnq,bsfob 330 data rvbsu,dsffq,cfmdi,qsftt,tqbsl 340 data sbebs,svsbm,tnfmm,gspxo,esjgu 400 n=50 410 dim n$(n),z(5),y(5) 420 for j=1 to n: read n$(j): next j 430 t=ti 440 t=t/1000:if t>=1 then goto 440 450 z=rnd(-t) 500 g=0: n$=n$(rnd(1)*n+1) 510 print "{down}i have a five letter word:": if r>0 then 560 520 print "guess (with legal words)" 530 print "and i'll tell you how many" 540 print "'jots', or matching letters," 550 print "you have...." 560 g=g+1: input "your word";z$ 570 if len(z$)<>5 then print "you must guess a 5-letter word!": goto 560 580 v=0: h=0: m=0 590 for j=1 to 5 600 z=asc(mid$(z$,j,1)): y=asc(mid$(n$,j,1))-1: if y=64 then y=90 610 if z<65 or z>90 then print "that's not a word!": goto 560 620 if z=65 or z=69 or z=73 or z=79 or z=85 or z=89 then v=v+1 630 if z=y then m=m+1 640 z(j)=z: y(j)=y: next j 650 if m=5 goto 800 660 if v=0 or v=5 then print "come on..what kind of a word is that?":\ goto 560 670 for j=1 to 5: y=y(j) 680 for k=1 to 5: if y=z(k) then h=h+1:z(k)=0:goto 700 690 next k 700 next j 710 print"{up}{right*19}";h;"jots" 720 if g<30 goto 560 730 print "i'd better tell you.. word was '"; 740 for j=1 to 5: print chr$(y(j));: next j 750 print"'": goto 810 800 print "you got it in only";g;"guesses." 810 input "{down}another word";z$ 820 r=1: if asc(z$)<>78 goto 500 stop tok64 begin 644 jotto.prg M`0@F"&0`F2`B$4I/5%1/("`@("`@($I)32!"551415)&245,1"(`50AX`(4@ M(A%704Y4($E.4U1254-424].4R([6B0ZBR#&*%HD*;(W."")(#(U,`"%"((` MF2`B$51262!43R!'54534R!42$4@35E35$5262`U+4Q%5%1%4B!73U)$(@"Q M"(P`F2`B$5E/52!-55-4($=515-3($].3%D@3$5'04P@-2U,151415(B`,<( ME@"9(")73U)$4RP@5$]/+BXN(@#V"*``F2`B64]5(%=)3$P@0D4@5$],1"!4 M2$4@3E5-0D52($]&($U!5$-(15,B`!D)J@"9("(H3U(@)TI/5%,G*2!/1B!9 M3U52($=515-3+B(`1@FT`)D@(A%(24Y4.B!42$4@5%))0TL@25,@5$\@5D%2 M62!33$E'2%1,62(`=`F^`)D@(B`@1E)/32!/3D4@1U5%4U,@5$\@5$A%($Y% M6%0[(%-/(%1(050B`*()R`"9("(@($E&(%E/52!'54534R`G0D%40T@G($%. M1"!'150@,B!*3U13(@#-"=(`F2`B("!93U4@34E'2%0@5%)9("="3U1#2"<@ M3U(@)T-(05)4)R(`[0G<`)D@(B`@1D]2(%1(12!.15A4($=515-3+BXN(@`1 M"OH`@R!"6$)31BQ)4$-#6BQ$0D1)1BQ%4T9"12Q01T="30`U"@0!@R!(4%-( M1BQ)0E5$22Q$2E=*32Q+4$U-6BQ,0EI"3`!9"@X!@R!30DM"22Q-1E=&32Q. M2DY*1"Q"3T]&62Q12E%&4P!]"A@!@R!25D9452Q32E=&4RQ14T945"Q0555& M4RQ&5T9/50"A"B(!@R!81D)71BQ&655032Q.5E1)6BQ!1D-30BQ'2D%!6@#% M"BP!@R!524I$3"Q%4U9/3"Q'35!012Q52DA&4RQ'0DQ&4P#I"C8!@R!#4%!5 M22Q-6DI/2"Q44E9"52Q(0E9!1BQ06$I/2``-"T`!@R!525-&1BQ42DA)52Q" M64U&5"Q(4U9.42Q"4T9/0@`Q"TH!@R!25D)352Q$4T9&42Q#1DU$22Q14T94 M5"Q444)33`!5"U0!@R!30D5"4RQ35E-"32Q43D9-32Q'4U!83RQ%4TI'50!> M"Y`!3K(U,`!T"YH!AB!.)"A.*2Q:*#4I+%DH-2D`D`ND`8$@2K(Q(*0@3CH@ MAR!.)"A**3H@@B!*`)D+K@%4LE1)`+4+N`%4LE2M,3`P,#J+(%2QLC$@IR") M(#0T,`#!"\(!6K*[**M4*0#:"_0!1[(P.B!.)+).)"B[*#$IK$ZJ,2D`"PS^ M`9D@(A%)($A!5D4@02!&259%($Q%5%1%4B!73U)$.B(Z((L@4K$P(*<@-38P M`"P,"`*9(")'54534R`H5TE42"!,14=!3"!73U)$4RDB`$\,$@*9(")!3D0@ M22=,3"!414Q,(%E/52!(3U<@34%.62(`=`P<`ID@(B=*3U13)RP@3U(@34%4 M0TA)3D<@3$545$524RPB`(D,)@*9(")93U4@2$%612XN+BXB`*4,,`)'LD>J M,3H@A2`B64]54B!73U)$(CM:)`#A##H"BR##*%HD*;.Q-2"G()D@(EE/52!- M55-4($=515-3($$@-2U,151415(@5T]21"$B.B")(#4V,`#S#$0"5K(P.B!( MLC`Z($VR,``!#4X"@2!*LC$@I"`U`#4-6`):LL8HRBA:)"Q*+#$I*3H@6;+& M*,HH3B0L2BPQ*2FK,3H@BR!9LC8T(*<@6;(Y,`!G#6("BR!:LS8U(+`@6K$Y M,""G()D@(E1(050G4R!.3U0@02!73U)$(2(Z((D@-38P`)T-;`*+(%JR-C4@ ML"!:LC8Y(+`@6K(W,R"P(%JR-SD@L"!:LC@U(+`@6K(X.2"G(%:R5JHQ`*\- M=@*+(%JR62"G($VR3:HQ`,<-@`):*$HILEHZ(%DH2BFR63H@@B!*`-<-B@*+ M($VR-2")(#@P,``:#I0"BR!6LC`@L"!6LC4@IR"9(")#3TU%($].+BY72$%4 M($M)3D0@3T8@02!73U)$($E3(%1(050_(CH@B2`U-C``,`Z>`H$@2K(Q(*0@ M-3H@6;)9*$HI`%T.J`*!($NR,2"D(#4Z((L@6;):*$LI(*<@2+)(JC$Z6BA+ M*;(P.HD@-S`P`&4.L@*"($L`;0Z\`H(@2@"2#L8"F2*1'1T='1T='1T='1T= M'1T='1T='2([2#LB2D]44R(`HP[0`HL@1[,S,"")(#4V,`#-#MH"F2`B22=$ M($)%5%1%4B!414Q,(%E/52XN(%=/4D0@5T%3("26 then 200 240 s=s% 300 for i=1 to s 310 a$(i)=mid$(z$,i,1) 320 next i 400 rem randomize string 420 for i=1 to s 430 k=int(rnd(1)*s+1) 440 t$=a$(i) 450 a$(i)=a$(k) 460 a$(k)=t$ 470 next i 480 gosub 950 595 t=0 600 rem rverse substring 605 t=t+1 610 input "how many to reverse ";r% 620 if r%=0 goto 900 630 if r%>0 and r%<=s goto 650 640 print "must be between 1 and ";s: goto 610 650 r=int(r%/2) 660 for i=1 to r 670 t$=a$(i) 680 a$(i)=a$(r%-i+1) 690 a$(r%-i+1)=t$ 700 next i 750 gosub 950 800 c=1: for i=2 to s 810 if a$(i)>a$(i+1) goto 830 820 c=0 830 next i 840 if c=0 goto 600 850 print "{down}you did it in ";t;" tries" 900 rem check for another game 910 input "{down}want to play again ";y$ 920 if left$(y$,1)="y" or y$="ok" or y$="1" goto 200 930 end 950 print 960 print left$(z1$,s) 970 for i=1 to s: print a$(i);: next i 980 print "{down}" 990 return stop tok64 begin 644 sequence.prg M`0@4"`$`CR`J*BH@4T51545.0T4`&@@"`(\`.`@#`(\@*BHJ($923TT@4$54 M(%5315(@1U)/55``5`@$`(\@*BHJ(%-/1E1705)%($580TA!3D=%`&D(!0"/ M("HJ*B!03R!"3U@@,S`E0DLD$D*$DI`-D*J`)!)"A)*;)! M)"A2):M)JC$I`.L*L@)!)"A2):M)JC$ILE0D`/,*O`*"($D`_0KN`HT@.34P M`!`+(`-#LC$Z(($@2;(R(*0@4P`J"RH#BR!!)"A)*;%!)"A)JC$I((D@.#,P M`#(+-`-#LC``.@L^`X(@20!*"T@#BR!#LC`@B2`V,#``;0M2`YD@(A%93U4@ M1$E$($E4($E.("([5#LB(%122453(@"*"X0#CR!#2$5#2R!&3U(@04Y/5$A% M4B!'04U%`*H+C@.%("(15T%.5"!43R!03$%9($%'04E.("([620`U0N8`XL@ MR"A9)"PQ*;(B62(@L"!9)+(B3TLB(+`@622R(C$B((D@,C`P`-L+H@.``.$+ MM@.9`/`+P`.9(,@H6C$D+%,I``T,R@.!($FR,2"D(%,Z()D@020H22D[.B"" 5($D`%PS4`YD@(A$B`!T,W@..```` ` end start tok64 pianokey.prg 90 REM piano keyboard 100 PRINT"{CLEAR} {REVERSE ON} {RIGHT} {RIGHT} {194} {RIGHT} {RIGHT} \ {RIGHT} {194} {RIGHT} {RIGHT} {194} {RIGHT} {RIGHT} " 110 PRINT" {REVERSE ON} {RIGHT} {RIGHT} {194} {RIGHT} {RIGHT} {RIGHT} \ {194} {RIGHT} {RIGHT} {194} {RIGHT} {RIGHT} " 120 PRINT" {REVERSE ON} {RIGHT} {RIGHT} {194} {RIGHT} {RIGHT} {RIGHT} \ {194} {RIGHT} {RIGHT} {194} {RIGHT} {RIGHT} " 130 PRINT" {REVERSE ON} {194} {194} {194} {194} {194} {194} {194} \ {194} {194} {194} {194} {194} " 140 PRINT" {REVERSE ON}q{194}w{194}e{194}r{194}t{194}y{194}u{194} \ i{194}o{194}p{194}@{194}*{194}^" 150 PRINT"{DOWN}'space' for solo or polyphonic" 160 PRINT"{DOWN}'f1,f3,f5,f7' octave selection" 170 PRINT"{DOWN}'f2,f4,f6,f8' waveform{DOWN}" 180 PRINT"hang on, setting up frequency table..." 190 S=13*4096+1024: DIM F(26): DIM K(255) 200 FOR I=0 TO 28: POKE S+I,0: NEXT 210 F1=7040: FOR I=1 TO 26: F(27-I)=F1*5.8+30: F1=F1/2^(1/12): NEXT 220 K$="q2w3er5t6y7ui9o0p@-*\^" 230 FOR I=1 TO LEN(K$): K(ASC(MID$(K$,I)))=I: NEXT 240 PRINT "{UP}{SPACE*38}" 250 AT=0:DE=0:SU=15:RE=9:SV=SU*16+RE:AV=AT*16+DE:WV=16:W=0:M=1:OC=4:\ HB=256:Z=0 260 FOR I=0 TO 2: POKE S+5+I*7,AT*16+DE: POKES+6+I*7,SU*16+RE 270 POKE S+2+I*7,4000 AND 255: POKE S+3+I*7,4000/256: NEXT 280 POKE S+24,15: REM+16+64:poke s+23,7 300 GET A$:IF A$="" THEN 300 310 FR=F(K(ASC(A$)))/M: T=V*7: CR=S+T+4: IF FR=Z THEN 500 320 POKE S+6+T,Z: REM finish dec/sus 325 POKE S+5+T,Z: REM finish att/rel 330 POKE CR,8: POKE CR,0: REM fix off 340 POKE S+T,FR-HB*INT(FR/HB): REM set lo 350 POKE S+1+T,FR/HB: REM set hi 360 POKE S+6+T,SV: REM set dec/sus 365 POKE S+5+T,AV: REM set att/rel 370 POKE CR,WV+1: FOR I=1 TO 50*AT: NEXT 375 POKE CR,WV: REM pulse 380 IF P=1 THEN V=V+1: IF V=3 THEN V=0 400 GOTO 300 500 IF A$="{F1}" THEN M=1: OC=4: GOTO 300 510 IF A$="{F3}" THEN M=2: OC=3: GOTO 300 520 IF A$="{F5}" THEN M=4: OC=2: GOTO 300 530 IF A$="{F7}" THEN M=8: OC=1: GOTO 300 540 IF A$="{F2}" THEN W=0: WV=16: GOTO 300 550 IF A$="{F4}" THEN W=1: WV=32: GOTO 300 560 IF A$="{F6}" THEN W=2: WV=64: GOTO300 570 IF A$="{F8}" THEN W=3: WV=128: GOTO300 580 IF A$=" " THEN P=1-P: GOTO 300 590 IF A$="{CLEAR}" THEN 200 600 GOTO 300 800 PRINT"hit a key" 810 GET A$: IF A$="" THEN 810: WAIT FOR A KEY 820 PRINT A$: RETURN stop tok64 begin 644 pianokey.prg M`0@6"%H`CR!024%.3R!+15E"3T%21``Z"&0`F2*3(!(@'2`=(,(@'2`=(!T@ MPB`=(!T@PB`=(!T@(@!="&X`F2(@$B`=(!T@PB`=(!T@'2#"(!T@'2#"(!T@ M'2`B`(`(>`"9(B`2(!T@'2#"(!T@'2`=(,(@'2`=(,(@'2`=("(`HPB"`)DB M(!(@PB#"(,(@PB#"(,(@PB#"(,(@PB#"(,(@(@#&"(P`F2(@$E'"5\)%PE+" M5,)9PE7"2<)/PE#"0,(JPEXB`.T(E@"9(A$G4U!!0T4G($9/4B!33TQ/($]2 M(%!/3%E02$].24,B`!0)H`"9(A$G1C$L1C,L1C4L1CK M22FR1C&L-2XXJC,P.B!&,;)&,:TRKB@QK3$R*3H@@@`!"MP`2R2R(E$R5S-% M4C54-EDW54DY3S!00"TJ7%XB`"<*Y@"!($FR,2"D(,,H2R0I.B!+*,8HRBA+ M)"Q)*2DILDDZ(((`5PKP`)D@(I$@("`@("`@("`@("`@("`@("`@("`@("`@ M("`@("`@("`@("`@("(`I@KZ`$%4LC`Z1$6R,#I35;(Q-3I21;(Y.E-6LE-5 MK#$VJE)%.D%6LD%4K#$VJD1%.E=6LC$V.E>R,#I-LC$Z3T.R-#I(0K(R-38Z M6K(P`-L*!`&!($FR,""D(#(Z()<@4ZHUJDFL-RQ!5*PQ-JI$13H@EU.J-JI) MK# key. CAN'T CONTINUE The CONT command will not work, either because the program was never RUN, there has been an error, or a line has been edited. DEVICE NOT PRESENT The required I/O device was not available for an OPEN, CLOSE, CMD, PRINT#, INPUT#, or GET#. DIVISION BY ZERO Division by zero is a mathematical oddity and not allowed. EXTRA IGNORED Too many items of data were typed in response to an INPUT statement. Only the first few items were accepted. FILE NOT FOUND If you were looking for a file on tape, and END-OF- TAPE marker was found. If you were looking on disk, no file with that name exists. FILE NOT OPEN The file specified in a CLOSE, CMD, PRINT#, INPUT#, or GET#, must first be OPENed. FILE OPEN An attempt was made to open a file using the number of an already open file. FORMULA TOO COMPLEX The string expression being evaluated should be split into at least two parts for the system to work with, or a formula has too many parentheses. ILLEGAL DIRECT The INPUT statement can only be used within a program, and not in direct mode. ILLEGAL QUANTITY A number used as the argument of a function or statement is out of the allowable range. LOAD There is a problem with the program on tape. NEXT WITHOUT FOR This is caused by either incorrectly nesting loops or having a variable name in a NEXT statement that doesn't correspond with one in a FOR statement. NOT INPUT FILE An attempt was made to INPUT or GET data from a file which was specified to be for output only. NOT OUTPUT FILE An attempt was mode to PRINT data to a file which was specified as input only. OUT OF DATA A READ statement was executed but there is no data left unREAD in a DATA statement. OUT OF MEMORY There is no more RAM available for program or variables. This may also occur when too many FOR loops have been nested, or when there are too many GOSUBs in effect. OVERFLOW The result of a computation is larger than the largest number allowed, which is 1.70141884E+38. REDIM'D ARRAY An array may only be DIMensioned once. If an array variable is used before that array is DIM'd, an automatic DIM operation is performed on that array setting the number of elements to ten, and any subsequent DIMs will cause this error. REDO FROM START Character data was typed in during an INPUT statement when numeric data was expected. Just re- type the entry so that it is correct, and the program will continue by itself. RETURN WITHOUT GOSUB A RETURN statement was encountered, and no GOSUB command has been issued. STRING TOO LONG A string can contain up to 255 characters. SYNTAX ERROR A statement is unrecognizable by the Commodore 64. A missing or extra parenthesis, misspelled keywords, etc. TYPE MISMATCH This error occurs when a number is used in place of a string, or vice-versa. UNDEF'D FUNCTION A user defined function was referenced, but it has never been defined using the DEF FN statement. UNDEF'D STATEMENT An attempt was made to GOTO or GOSUB or RUN a line number that doesn't exist. VERIFY The program on tape or disk does not match the program currently in memory. VERIFY The program on tape or disk does not match the program currently in memory. APPENDIX M MUSIC NOTE VALUES This appendix contains a complete list of Note#, actual note, and the values to be POKED into the HI FREQ and LOW FREQ registers of the sound chip to produce the indicated note. +-----------------------------+-----------------------------------------+ | MUSICAL NOTE | OSCILLATOR FREQ | +-------------+---------------+-------------+-------------+-------------+ | NOTE | OCTAVE | CYCLES/SEC. | HI | LOW | +-------------+---------------+-------------+-------------+-------------+ | 0 | C-0 | 268 | 1 | 12 | | 1 | C#-0 | 284 | 1 | 28 | | 2 | D-0 | 301 | 1 | 45 | | 3 | D#-0 | 318 | 1 | 62 | | 4 | E-0 | 337 | 1 | 81 | | 5 | F-0 | 358 | 1 | 102 | | 6 | F#-0 | 379 | 1 | 123 | | 7 | G-0 | 401 | 1 | 145 | | 8 | G#-0 | 425 | 1 | 169 | | 9 | A-0 | 451 | 1 | 195 | | 10 | A#-0 | 477 | 1 | 221 | | 11 | B-0 | 506 | 1 | 250 | | 16 | C-1 | 536 | 2 | 24 | | 17 | C#-1 | 568 | 2 | 56 | | 18 | D-1 | 602 | 2 | 90 | | 19 | D#-1 | 637 | 2 | 125 | | 20 | E-1 | 675 | 2 | 163 | | 21 | F-1 | 716 | 2 | 204 | | 22 | F#-1 | 758 | 2 | 246 | | 23 | G-1 | 803 | 3 | 35 | | 24 | G#-1 | 851 | 3 | 83 | | 25 | A-1 | 902 | 3 | 134 | | 26 | A#-1 | 955 | 3 | 187 | | 27 | B-1 | 1012 | 3 | 244 | | 32 | C-2 | 1072 | 4 | 48 | | 33 | C#-2 | 1136 | 4 | 112 | | 34 | D-2 | 1204 | 4 | 180 | | 35 | D#-2 | 1275 | 4 | 251 | | 36 | E-2 | 1351 | 5 | 71 | | 37 | F-2 | 1432 | 5 | 152 | | 38 | F#-2 | 1517 | 5 | 237 | | 39 | G-2 | 1607 | 6 | 71 | | 40 | G#-2 | 1703 | 6 | 167 | | 41 | A-2 | 1804 | 7 | 12 | | 42 | A#-2 | 1911 | 7 | 119 | | 43 | B-2 | 2025 | 7 | 233 | | 48 | C-3 | 2145 | 8 | 97 | | 49 | C#-3 | 2273 | 8 | 225 | | 50 | D-3 | 2408 | 9 | 104 | | 51 | D#-3 | 2551 | 9 | 247 | | 52 | E-3 | 2703 | 10 | 143 | | 53 | F-3 | 2864 | 11 | 48 | | 54 | F#-3 | 3034 | 11 | 218 | | 55 | G-3 | 3215 | 12 | 143 | | 56 | G#-3 | 3406 | 13 | 78 | | 57 | A-3 | 3608 | 14 | 24 | | 58 | A#-3 | 3823 | 14 | 239 | | 59 | B-3 | 4050 | 15 | 210 | | 64 | C-4 | 4291 | 16 | 195 | | 65 | C#-4 | 4547 | 17 | 195 | | 66 | D-4 | 4817 | 18 | 209 | | 67 | D#-4 | 5103 | 19 | 239 | | 68 | E-4 | 5407 | 21 | 31 | | 69 | F-4 | 5728 | 22 | 96 | | 70 | F#-4 | 6069 | 23 | 181 | | 71 | G-4 | 6430 | 25 | 30 | | 72 | G#-4 | 6812 | 26 | 156 | | 73 | A-4 | 7217 | 28 | 49 | | 74 | A#-4 | 7647 | 29 | 223 | | 75 | B-4 | 8101 | 31 | 165 | | 80 | C-5 | 8583 | 33 | 135 | | 81 | C#-5 | 9094 | 35 | 134 | | 82 | D-5 | 9634 | 37 | 162 | | 83 | D#-5 | 10207 | 39 | 223 | | 84 | E-5 | 10814 | 42 | 62 | | 85 | F-5 | 11457 | 44 | 193 | | 86 | F#-5 | 12139 | 47 | 107 | | 87 | G-5 | 12860 | 50 | 60 | | 88 | G#-5 | 13625 | 53 | 57 | | 89 | A-5 | 14435 | 56 | 99 | | 90 | A#-5 | 15294 | 59 | 190 | | 91 | B-5 | 16203 | 63 | 75 | | 96 | C-6 | 17167 | 67 | 15 | | 97 | C#-6 | 18188 | 71 | 12 | | 98 | D-6 | 19269 | 75 | 69 | | 99 | D#-6 | 20415 | 79 | 191 | | 100 | E-6 | 21629 | 84 | 125 | | 101 | F-6 | 22915 | 89 | 131 | | 102 | F#-6 | 24278 | 94 | 214 | | 103 | G-6 | 25721 | 100 | 121 | | 104 | G#-6 | 27251 | 106 | 115 | | 105 | A-6 | 28871 | 112 | 199 | | 106 | A#-6 | 30588 | 119 | 124 | | 107 | B-6 | 32407 | 126 | 151 | | 112 | C-7 | 34334 | 134 | 30 | | 113 | C#-7 | 36376 | 142 | 24 | | 114 | D-7 | 38539 | 150 | 139 | | 115 | D#-7 | 40830 | 159 | 126 | | 116 | E-7 | 43258 | 168 | 250 | | 117 | F-7 | 45830 | 179 | 6 | | 118 | F#-7 | 48556 | 189 | 172 | | 119 | G-7 | 51443 | 200 | 243 | | 120 | G#-7 | 54502 | 212 | 230 | | 121 | A-7 | 57743 | 225 | 143 | | 122 | A#-7 | 61176 | 238 | 248 | | 123 | B-7 | 64814 | 253 | 46 | +-------------+---------------+-------------+-------------+-------------+ FILTER SETTINGS +------------+--------------------------------+ | Location | Contents | +------------+--------------------------------+ | 54293 | Low cutoff frequency (0-7) | | 54294 | High cutoff frequency (0-255) | | 54295 | Resonance (bits 4-7) | | | Filter voice 3 (bit 2) | | | Filter voice 2 (bit 1) | | | Filter voice 1 (bit 0) | | 54296 | High pass (bit 6) | | | Bandpass (bit 5) | | | Low pass (bit 4) | | | Volume (bits 0-3) | +------------+--------------------------------+ APPENDIX N BIBLIOGRAPHY Addison-Wesley "BASIC and the Personal Computer", Dwyer and Critchfield Compute "Compute's First Book of PET/CBM" Cowbay Computing "Feed Me, I'm Your PET Computer", Carol Alexander "Looking Good with Your PET", Carol Alexander "Teacher's PET -- Plans, Quizzes, and Answers" Creative Computing "Getting Acquainted With Your VIC 20", T. Hartnell Dilithium Press "BASIC Basic-English Dictionary for the PET", Lorry Noonan "PET BASIC", Tom Rugg and Phil Feldman Faulk Baker Associates "MOS Programming Manual", MOS Technology Hoyden Book Co. "BASIC From the Ground Up", David E. Simon "I Speak BASIC to My PET", Aubrey Jones, Jr. "Library of PET Subroutines',', Nick Hampshire "PET Graphics", Nick Hampshire "BASIC Conversions Handbook, Apple, TRS-80, and PET", David A. Brain, Phillip R. Oviatt, Paul J. Paquin, and Chandler P. Stone Howard W. Sams "The Howard W. Sams Crash Course in Microcomputers", Louis E. Frenzel, Jr. "Mostly BASIC: Applications for Your PET", Howard Berenbon "PET Interfacing", James M. Downey and Steven M. Rogers "VIC 20 Programmer's Reference Guide", A. Finkel, P. Higginbottom, N. Harris, and M. Tomczyk Level Ltd. "Programming the PET/CBM", Raeto West. Little, Brown & Co. "Computer Games for Businesses, Schools, and Homes", J. Victor Nagigian, and William S. Hodges "The Computer Tutor: Learning Activities for Homes and Schools", Gary W. Orwig, University of Central Florida, and William S. Hodges McGraw-Hill "Hands-On BASIC With a PET", Herbert D. Peckman "Home and Office Use of VisiCalc", D. Castlewitz, and L. Chisauki Osborne/McGraw-Hill "PET/CBM Personal Computer Guide", Carroll S. Donahue "PET Fun and Games", R. Jeffries and G. Fisher "PET and the IEEE", A. Osborne and C. Donahue "Some Common BASIC Programs for the PET", L. Poole, M. Borchers, and C. Donahue "Osborne CP/M User Guide", Thorn Hogan "CBM Professional Computer Guide" "The PET Personal Guide" "The 8086 Book", Russell Rector and George Alexy P. C. Publications "Beginning Self-Teaching Computer Lessons" Prentice-Hall "The PET Personal Computer for Beginners", S. Dunn and V. Morgan Reston Publishing Co. "PET and the IEEE 488 Bus (GPIB)", Eugene Fisher and C. W. Jensen "PET BASIC -- Training Your PET Computer", Roman Zamora, Wm. F. Carrie, and B. Allbrecht "PET Games and Recreation", M. Ogelsby, L. Lindsey, and D. Kunkin "PET BASIC", Richard Huskell "VIC Games and Recreation" Telmas Courseware "BASIC and the Personal Computer", T. A. Dwyer, Ratings and M. Critchfield Total Information "Understanding Your PET/CBM, Vol. 1, BASIC Services Programming" "Understanding Your VIC", David Schultz Commodore Magazines provide you with the most up-to-date information for your Commodore 64. Two of the most popular publications that you should seriously consider subscribing to are: COMMODORE -- The Microcomputer Magazine is published bimonthly and is available by subscription ($15.00 per year, U.S., and $25.00 per year, worldwide). POWER/PLAY -- The Home Computer Magazine is, published quarterly and is available by subscription ($10.00 per year, U.S., and $15.00 per year worldwide). APPENDIX O SPRITE REGISTER MAP +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ |Register#| | | | | | | | | | | Dec Hex | DB7 | DB6 | DB5 | DB4 | DB3 | DB2 | DB1 | DB0 | | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 0 0 |S0X7 | | | | | | |S0X0 |SPRITE 0 X | | | | | | | | | | |Component | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 1 1 |S0Y7 | | | | | | |S0Y0 |SPRITE 0 Y | | | | | | | | | | |Component | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 2 2 |S1X7 | | | | | | |S1X0 |SPRITE 1 X | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 3 3 |S1Y7 | | | | | | |S1Y0 |SPRITE 1 Y | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 4 4 |S2X7 | | | | | | |S2X0 |SPRITE 2 X | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 5 5 |S2Y7 | | | | | | |S2Y0 |SPRITE 2 Y | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 6 6 |S3X7 | | | | | | |S3X0 |SPRITE 3 X | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 7 7 |S3Y7 | | | | | | |S3Y0 |SPRITE 3 Y | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 8 8 |S4X7 | | | | | | |S4X0 |SPRITE 4 X | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 9 9 |S4Y7 | | | | | | |S4Y0 |SPRITE 4 Y | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 10 A |S5X7 | | | | | | |S5X0 |SPRITE 5 X | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 11 B |S5Y7 | | | | | | |S5Y0 |SPRITE 5 Y | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 12 C |S6X7 | | | | | | |S6X0 |SPRITE 6 X | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 13 D |S6Y7 | | | | | | |S6Y0 |SPRITE 6 Y | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 14 E |S7X7 | | | | | | |S7X0 |SPRITE 7 X | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 15 F |S7Y7 | | | | | | |S7Y0 |SPRITE 7 Y | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 16 10 |S7X8 |S6X8 |S5X8 |S4X8 |S3X8 |S2X8 |S1X8 |S0X8 |MSB of X | | | | | | | | | | |COORD. | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 17 11 | RC8 | ECM | BMM |BLNK |RSEL |YSCL2|YSCL1|YSCL0|Y SCROLL | | | | | | | | | | |Mode | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 18 12 | RC7 | RC6 | RC5 | RC4 | RC3 | RC2 | RC1 | RC0 |RASTER | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 19 13 |LPX7 | | | | | | |LPX0 |LIGHT PEN X | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 20 14 |LPY7 | | | | | | |LPY0 |LIGHT PEN Y | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 21 15 | SE7 | | | | | | | SE0 |SPRITE | | | | | | | | | | |ENABLE | | | | | | | | | | |(ON/OFF) | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 22 16 |N.C. |N.C. | RST | MCM |CSEL |XSCL2|XSCL1|XSCL0|X SCROLL | | | | | | | | | | |MODE | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 23 17 |SEX7 | | | | | | |SEX0 |SPRITE | | | | | | | | | | |EXPAND Y | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 24 18 |VS13 |VS12 |VS11 |VS10 |CB13 |CB12 |CB11 |N.C. |SCREEN | | | | | | | | | | |Character | | | | | | | | | | |Memory | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 25 19 |IRQ |N.C. |N.C. |N.C. |LPIRQ|ISSC |ISBC |RIRIQ|Interrupt | | | | | | | | | | |Request's | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 26 1A |N.C. |N.C. |N.C. |N.C. |MLPI |MISSC|MISBC|MRIRQ|Interrupt | | | | | | | | | | |Request | | | | | | | | | | |MASKS | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 27 1B |BSP7 | | | | | | |BSP0 |Background | | | | | | | | | | |Sprite | | | | | | | | | | |PRIORITY | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 28 1C |SCM7 | | | | | | |SCM0 |MULTICOLOR | | | | | | | | | | |SPRITE | | | | | | | | | | |SELECT | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 29 1D |SEXX7| | | | | | |SEXX0|SPRITE | | | | | | | | | | |EXPAND X | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 30 1E |SSC7 | | | | | | |SSC0 |Sprite-Sprite| | | | | | | | | | |COLLISION | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ | 31 1F |SBC7 | | | | | | |SBC0 |Sprite- | | | | | | | | | | |Background | | | | | | | | | | |COLLISION | +---------+-----+-----+-----+-----+-----+-----+-----+-----+-------------+ +-----------+---------------------+ +------------+--------------------+ | Register# | | | Register# | | | Dec Hex | Color | | Dec Hex | Color | +-----------+---------------------+ +------------+--------------------+ | 32 20 | BORDER COLOR | | 39 27 | SPRITE 0 COLOR | +-----------+---------------------+ +------------+--------------------+ | 33 21 | BACKGROUND COLOR 0 | | 40 28 | SPRITE 1 COLOR | +-----------+---------------------+ +------------+--------------------+ | 34 22 | BACKGROUND COLOR 1 | | 41 29 | SPRITE 2 COLOR | +-----------+---------------------+ +------------+--------------------+ | 35 23 | BACKGROUND COLOR 2 | | 42 2A | SPRITE 3 COLOR | +-----------+---------------------+ +------------+--------------------+ | 36 24 | BACKGROUND COLOR 3 | | 43 2B | SPRITE 4 COLOR | +-----------+---------------------+ +------------+--------------------+ | 37 25 | SPRITE MULTICOLOR 0 | | 44 2C | SPRITE 5 COLOR | +-----------+---------------------+ +------------+--------------------+ | 38 26 | SPRITE MULTICOLOR 1 | | 45 2D | SPRITE 6 COLOR | +-----------+---------------------+ +------------+--------------------+ | 46 2E | SPRITE 7 COLOR | +------------+--------------------+ COLOR CODES +-----------------+---------------+ +-----------------+---------------+ | Dec Hex | Color | | Dec Hex | Color | +-----------------+---------------+ +-----------------+---------------+ | 0 0 | BLACK | | 8 8 | ORANGE | +-----------------+---------------+ +-----------------+---------------+ | 1 1 | WHITE | | 9 9 | BROWN | +-----------------+---------------+ +-----------------+---------------+ | 2 2 | RED | | 10 A | LT RED | +-----------------+---------------+ +-----------------+---------------+ | 3 3 | CYAN | | 11 B | GRAY 1 | +-----------------+---------------+ +-----------------+---------------+ | 4 4 | PURPLE | | 12 C | GRAY 2 | +-----------------+---------------+ +-----------------+---------------+ | 5 5 | GREEN | | 13 D | LT GREEN | +-----------------+---------------+ +-----------------+---------------+ | 6 6 | BLUE | | 14 E | LT BLUE | +-----------------+---------------+ +-----------------+---------------+ | 7 7 | YELLOW | | 15 F | GRAY 3 | +-----------------+---------------+ +-----------------+---------------+ LEGEND: ONLY COLORS 0-7 MAY BE USED IN MULTICOLOR CHARACTER MODE. APPENDIX P 6566/6567 (VIC-II) CHIP REGISTER MAP The 6566/6567 are multi-purpose color video controller devices for use in both computer video terminals and video game applications. Both devices contain 47 control registers which are accessed via a standard 8-bit microprocessor bus (65XX) and will access up to 16K of memory for display information. The various operating modes and options within each mode are described. REGISTER MAP +----------+------------------------------------------------------------+ | ADDRESS | DB7 DB6 DB5 DB4 DB3 DB2 DB1 DB0 DESCRIPTION | +----------+------------------------------------------------------------+ | 00 ($00) | M0X7 M0X6 M0X5 M0X4 M0X3 M0X2 M0X1 M0X0 MOB 0 X-position | | 01 ($01) | M0Y7 M0Y6 M0Y5 M0Y4 M0Y3 M0Y2 M0Y1 M0Y0 MOB 0 Y-position | | 02 ($02) | M1X7 M1X6 M1X5 M1X4 M1X3 M1X2 M1Xl M1X0 MOB 1 X-position | | 03 ($03) | M1Y7 M1Y6 M1Y5 M1Y4 M1Y3 M1Y2 M1Y1 M1Y0 MOB 1 Y-position | | 04 ($04) | M2X7 M2X6 M2X5 M2X4 M2X3 M2X2 M2X1 M2X0 MOB 2 X-position | | 05 ($05) | M2Y7 M2Y6 M2Y5 M2Y4 M2Y3 M2Y2 M2Y1 M2Y0 MOB 2 Y-position | | 06 ($06) | M3X7 M3X6 M3X5 M3X4 M3X3 M3X2 M3X1 M3X0 MOB 3 X-position | | 07 ($07) | M3Y7 M3Y6 M3Y5 M3Y4 M3Y3 M3Y2 M3Y1 M3Y0 MOB 3 Y-position | | 08 ($08) | M4X7 M4X6 M4X5 M4X4 M4X3 M4X2 M4X1 M4X0 MOB 4 X-position | | 09 ($09) | M4Y7 M4Y6 M4Y5 M4Y4 M4Y3 M4Y2 M4Y1 M4Y0 MOB 4 Y-position | | 10 ($0A) | M5X7 M5X6 M5X5 M5X4 M5X3 M5X2 M5X1 M5X0 MOB 5 X-position | | 11 ($0B) | M5Y7 M5Y6 M5Y5 M5Y4 M5Y3 M5Y2 M5Y1 M5Y0 MOB 5 Y-position | | 12 ($0C) | M6X7 M6X6 M6X5 M6X4 M6X3 M6X2 M6X1 M6X0 MOB 6 X-position | | 13 ($0D) | M6Y7 M6Y6 M6Y5 M6Y4 M6Y3 M6Y2 M6Y1 M6Y0 MOB 6 Y-position | | 14 ($0E) | M7X7 M7X6 M7X5 M7X4 M7X3 M7X2 M7Xl M7X0 MOB 7 X-position | | 15 ($0F) | M7Y7 M7Y6 M7Y5 M7Y4 M7Y3 M7Y2 M7Y1 M6Y0 MOB 7 Y-position | | 16 ($10) | M7X8 M6X8 M5X8 M4X8 M3X8 M2X8 M1X8 M0X8 MSB of X-position | | 17 ($11) | RC8 ECM BMM DEN RSEL Y2 Y1 Y0 See text | | 18 ($12) | RC7 RC6 RC5 RC4 RC3 RC2 RC1 RC0 Raster register | | 19 ($13) | LPX8 LPX7 LPX6 LPX5 LPX4 LPX3 LPX2 LPX1 Light Pen X | | 20 ($14) | LPY7 LPY6 LPY5 LPY4 LPY3 LPY2 LPY1 LPY0 Light Pen Y | | 21 ($15) | M7E M6E M5E M4E M3E M2E M1E M0E MOB Enable | | 22 ($16) | - - RES MCM CSEL X2 X1 X0 See text | | 23 ($17) | M7YE M6YE M5YE M4YE M3YE M2YE M1YE M0YE MOB Y-expand | | 24 ($18) | VM13 VM12 VM11 VM10 CB13 CB12 CB11 - Memory Pointers | | 25 ($19) | IRQ - - - ILP IMMC IMBC IRST Interrupt Register| | 26 ($1A) | - - - - ELP EMMC EMBC ERST Enable Interrupt | | 27 ($1B) | M7DP M6DP M5DP M4DP M3DP M2DP M1DP M0DP MOB-DATA Priority | | 28 ($1C) | M7MC M6MC M5MC M4MC M3MC M2MC M1MC M0MC MOB Multicolor Sel| | 29 ($1D) | M7XE M6XE M5XE M4XE M3XE M2XE M1XE M0XE MOB X-expand | | 30 ($1E) | M7M M6M M5M M4M M3M M2M M1M M0M MOB-MOB Collision | | 31 ($1F) | M7D M6D M5D M4D M3D M2D M1D M0D MOB-DATA Collision| | 32 ($20) | - - - - EC3 EC2 EC1 EC0 Exterior Color | | 33 ($21) | - - - - B0C3 B0C2 B0C1 B0C0 Bkgd #0 Color | | 34 ($22) | - - - - B1C3 B1C2 B1C1 B1C0 Bkgd #1 Color | | 35 ($23) | - - - - B2C3 B2C2 B2C1 B2C0 Bkgd #2 Color | | 36 ($24) | - - - - B3C3 B3C2 B3C1 B3C0 Bkgd #3 Color | | 37 ($25) | - - - - MM03 MM02 MM01 MM00 MOB Multicolor #0 | | 38 ($26) | - - - - MM13 MM12 MM11 MM10 MOB Multicolor #1 | | 39 ($27) | - - - - M0C3 M0C2 M0C1 M0C0 MOB 0 Color | | 40 ($28) | - - - - M1C3 M1C2 M1C1 M1C0 MOB 1 Color | | 41 ($29) | - - - - M2C3 M2C2 M2C1 M2C0 MOB 2 Color | | 42 ($2A) | - - - - M3C3 M3C2 M3C1 M3C0 MOB 3 Color | | 43 ($2B) | - - - - M4C3 M4C2 M4C1 M4C0 MOB 4 Color | | 44 ($2C) | - - - - M5C3 M5C2 M5C1 M5C0 MOB 5 Color | | 45 ($2D) | - - - - M6C3 M6C2 M6C1 M6C0 MOB 6 Color | | 46 ($2E) | - - - - M7C3 M7C2 M7C1 M7C0 MOB 7 Color | +----------+------------------------------------------------------------+ +-----------------------------------------------------------------------+ |NOTE: A dash indicates a no connect. All no connects are read as a "1".| +-----------------------------------------------------------------------+ APPENDIX Q COMMODORE 64 SOUND CONTROL SETTINGS This handy table gives you the key numbers you need to use in your sound programs, according to which of the Commodore 64's 3 voices you want to use. To set or adjust a sound control in your BASIC program, just POKE the number from the second column, followed by a comma (,) and a number from the chart ... like this: POKE 54276,17 (Selects a Triangle Waveform for VOICE 1). Remember that you must set the VOLUME before you can generate sound. POKE 54296 followed by a number from 0 to 15 sets the volume for all 3 voices. It takes 2 separate POKEs to generate each musical note ... for example POKE 54273,34: POKE 54272,75 designates low C in the sample scale bellow. Also ... you aren't limited to the numbers shown in the tables. If 34 doesn't sound "right" for a low C, try 35. To provide a higher SUSTAIN or ATTACK rate than those shown, add two or more SUSTAIN numbers together. (Examples: POKE 54277,96 combines two attack rates (32 and 64) for a combined higher attack rate ... but ... POKE 54277,20 provides a low attack rate (16) and a medium decay rate (4). +----------------------------------------------------------------------------+ |SETTING VOLUME -- SAME FOR ALL 3 VOICES | +--------------+---------+---------------------------------------------------+ |VOLUME CONTROL|POKE54296| Settings from 0 (off) to 15 (loudest) | +--------------+---------+---------------------------------------------------+ VOICE NUMBER 1 +--------------+---------+---------------------------------------------------+ |TO CONTROL |POKE THIS| FOLLOWED BY ONE OF THESE NUMBERS | |THIS SETTING: |NUMBER: | (0 to 15 ... or ... 0 to 255 depending on range) | +--------------+---------+---------------------------------------------------+ |TO PLAY A NOTE| C | C#| D | D#| E | F | F#| G | G#| A | A#| B | C | C#| |HIGH FREQUENCY|54273 34 | 36| 38| 40| 43| 45| 48| 51| 54| 57| 61| 64| 68| 72| |LOW FREQUENCY |54272 75 | 85|126|200| 52|198|127| 97|111|172|126|188|149|169| +--------------+---------+------------+------------+------------+------------+ |WAVEFORM | POKE | TRIANGLE | SAWTOOTH | PULSE | NOISE | | | 54276 | 17 | 33 | 65 | 129 | +--------------+---------+------------+------------+------------+------------+ |PULSE RATE (Pulse Waveform) | |HI POLSE | 54275 | A value of 0 to 15 (for Pulse waveform only) | |LO POLSE | 54274 | A value of 0 to 255 (for Pulse waveform only) | +--------------+---------+------+------+------+------+-----+-----+-----+-----+ |ATTACK/ | POKE | ATK4 | ATK3 | ATK2 | ATK1 | DEC4| DEC3| DEC2| DEC1| | DECAY | 54277 | 128 | 64 | 32 | 16 | 8 | 4 | 2 | 1 | +--------------+---------+------+------+------+------+-----+-----+-----+-----+ |SUSTAIN/ | POKE | SUS4 | SUS3 | SUS2 | SUS1 | REL4| REL3| REL2| REL1| | RELEASE| 54278 | 128 | 64 | 32 | 16 | 8 | 4 | 2 | 1 | +--------------+---------+------+------+------+------+-----+-----+-----+-----+ VOICE NUMBER 2 +--------------+---------+---------------------------------------------------+ |TO CONTROL |POKE THIS| FOLLOWED BY ONE OF THESE NUMBERS | |THIS SETTING: |NUMBER: | (0 to 15 ... or ... 0 to 255 depending on range) | +--------------+---------+---------------------------------------------------+ |TO PLAY A NOTE| C | C#| D | D#| E | F | F#| G | G#| A | A#| B | C | C#| |HIGH FREQUENCY|54280 34 | 36| 38| 40| 43| 45| 48| 51| 54| 57| 61| 64| 68| 72| |LOW FREQUENCY |54279 75 | 85|126|200| 52|198|127| 97|111|172|126|188|149|169| +--------------+---------+------------+------------+------------+------------+ |WAVEFORM | POKE | TRIANGLE | SAWTOOTH | PULSE | NOISE | | | 54283 | 17 | 33 | 65 | 129 | +--------------+---------+------------+------------+------------+------------+ |PULSE RATE (Pulse Waveform) | |HI POLSE | 54282 | A value of 0 to 15 (for Pulse waveform only) | |LO POLSE | 54281 | A value of 0 to 255 (for Pulse waveform only) | +--------------+---------+------+------+------+------+-----+-----+-----+-----+ |ATTACK/ | POKE | ATK4 | ATK3 | ATK2 | ATK1 | DEC4| DEC3| DEC2| DEC1| | DECAY | 54284 | 128 | 64 | 32 | 16 | 8 | 4 | 2 | 1 | +--------------+---------+------+------+------+------+-----+-----+-----+-----+ |SUSTAIN/ | POKE | SUS4 | SUS3 | SUS2 | SUS1 | REL4| REL3| REL2| REL1| | RELEASE| 54285 | 128 | 64 | 32 | 16 | 8 | 4 | 2 | 1 | +--------------+---------+------+------+------+------+-----+-----+-----+-----+ VOICE NUMBER 3 +--------------+---------+---------------------------------------------------+ |TO CONTROL |POKE THIS| FOLLOWED BY ONE OF THESE NUMBERS | |THIS SETTING: |NUMBER: | (0 to 15 ... or ... 0 to 255 depending on range) | +--------------+---------+---------------------------------------------------+ |TO PLAY A NOTE| C | C#| D | D#| E | F | F#| G | G#| A | A#| B | C | C#| |HIGH FREQUENCY|54287 34 | 36| 38| 40| 43| 45| 48| 51| 54| 57| 61| 64| 68| 72| |LOW FREQUENCY |54286 75 | 85|126|200| 52|198|127| 97|111|172|126|188|149|169| +--------------+---------+------------+------------+------------+------------+ |WAVEFORM | POKE | TRIANGLE | SAWTOOTH | PULSE | NOISE | | | 54290 | 17 | 33 | 65 | 129 | +--------------+---------+------------+------------+------------+------------+ |PULSE RATE (Pulse Waveform) | |HI POLSE | 54289 | A value of 0 to 15 (for Pulse waveform only) | |LO POLSE | 54288 | A value of 0 to 255 (for Pulse waveform only) | +--------------+---------+------+------+------+------+-----+-----+-----+-----+ |ATTACK/ | POKE | ATK4 | ATK3 | ATK2 | ATK1 | DEC4| DEC3| DEC2| DEC1| | DECAY | 54291 | 128 | 64 | 32 | 16 | 8 | 4 | 2 | 1 | +--------------+---------+------+------+------+------+-----+-----+-----+-----+ |SUSTAIN/ | POKE | SUS4 | SUS3 | SUS2 | SUS1 | REL4| REL3| REL2| REL1| | RELEASE| 54292 | 128 | 64 | 32 | 16 | 8 | 4 | 2 | 1 | +--------------+---------+------+------+------+------+-----+-----+-----+-----+ TRY THESE SETTINGS TO SIMULATE DIFFERENT INSTRUMENTS +------------+----------+--------------+---------------+----------------+ | Instrument | Waveform | Attack/Decay |Sustain/Release| Pulse Rate | +------------+----------+--------------+---------------+----------------+ | Piano | Pulse | 9 | 0 | Hi-0, Lo-255 | | Flute | Triangle | 96 | 0 | Not applicable | | Harpsichord| Sawtooth | 9 | 0 | Not applicable | | Xylophone | Triangle | 9 | 0 | Not applicable | | Organ | Triangle | 0 | 240 | Not applicable | | Colliape | Triangle | 0 | 240 | Not applicable | | Accordian | Triangle | 102 | 0 | Not applicable | | Trumpet | Sawtooth | 96 | 0 | Not applicable | +------------+----------+--------------+---------------+----------------+ MEANINGS OF SOUND TERMS ADSR -- Attack/Decay/Sustain/Release Attack -- Rate sound rises to peak volume Decay -- Rate sound falls from peak volume to Sustain level Sustain -- Prolong rate at certain volume Release -- Rate at which volume falls from Sustain level Waveform -- "Shape" of sound wave Pulse -- Tone quality of Pulse Waveform NOTE: Attack/Decay and Sustain/Release settings should always be POKEd in your program BEFORE the Waveform is POKEd. APPENDIX R 6581 SOUND INTERFACE DEVICE (SID) CHIP SPECIFICATIONS CONCEPT The 6581 Sound Interface Device (SID) is a single-chip, 3-voice electronic music synthesizer/sound effects generator compatible with the 6510 and similar microprocessor families. SID provides wide-range, high- resolution control of pitch (frequency), tone color (harmonic content), and dynamics (volume). Specialized control circuitry minimizes software overhead, facilitating use in arcade/home video games and low-cost musical instruments. FEATURES o 3 TONE OSCILLATORS Range: 0 - 4 kHz o 4 WAVEFORMS PER OSCILLATOR Triangle, Sawtooth, Variable Pulse, Noise o 3 AMPLITUDE MODULATORS Range: 48 dB o 3 ENVELOPE GENERATORS Exponential response Attack Rate: 2 ms - 8 s Decay Rate: 6 ms - 24 s Sustain Level: 0 - peak volume Release Rate: 6 ms - 24 s o OSCILLATOR SYNCHRONIZATION o RING MODULATION DESCRIPTION The 6581 consists of three synthesizer "voices" which can be used independently or in conjunction with each other (or external audio sources) to create complex sounds. Each voice consists of a Tone Oscillator/Waveform Generator, an Envelope Generator and an Amplitude Modulator. The Tone Oscillator controls the pitch of the voice over a wide range. The Oscillator produces four waveforms at the selected frequency, with the unique harmonic content of each waveform providing simple control of tone color. The volume dynamics of the oscillator are controlled by the Amplitude Modulator under the direction of the Envelope Generator. When triggered, the Envelope Generator creates an amplitude envelope with programmable rates of increasing and decreasing volume. In addition to the three voices, a programmable Filter is provided for generating complex, dynamic tone colors via subtractive synthesis. SID allows the microprocessor to read the changing output of the third Oscillator and third Envelope Generator. These outputs can be used as a source of modulation information for creating vibrato, frequency/filter sweeps and similar effects. The third oscillator can also act as a random number generator for games. Two A/D converters are provided for interfacing SID with potentiometers. These can be used for "paddles" in a game environment or as front panel controls in a music synthesizer. SID can process external audio signals, allowing multiple SID chips to be daisy-chained or mixed in complex polyphonic systems. SID CONTROL REGISTERS There are 29 eight-bit registers in SID which control the generation of sound. These registers are either WRITE-only or READ-only and are listed below in Table 1. Table 1. SID Register Map WO=WRITE-ONLY RO=READ-ONLY REG# DATA (HEX) D7 D6 D5 D4 D3 D2 D1 D0 REG NAME REG Voice 1 TYPE 0 00 F7 F6 F5 F4 F3 F2 F1 F0 FREQ LO WO 1 01 F15 F14 F13 F12 F11 F10 F9 F8 FREQ HI WO 2 02 PW7 PW6 PW5 PW4 PW3 PW2 PW1 PW0 PW LO WO 3 03 - - - - PW11 PW10 PW9 PW8 PW HI WO 4 04 NOISE PULSE SAW TRIANG TEST RING SYNC GATE CONTROL REG WO 5 05 ATK3 ATK2 ATK1 ATK0 DCY3 DCY2 DCY1 DCY0 ATTACK/DECAY WO 6 06 STN3 STN2 STN1 STN0 RLS3 RLS2 RLS1 RLS0 SUSTAIN/RELEASE WO Voice 2 7 07 F7 F6 F5 F4 F3 F2 F1 F0 FREQ LO WO 8 08 F15 F14 F13 F12 F11 F10 F9 F8 FREQ HI WO 9 09 PW7 PW6 PW5 PW4 PW3 PW2 PW1 PW0 PW LO WO 10 0A - - - - PW11 PW10 PW9 PW8 PW HI WO 11 0B NOISE PULSE SAW TRIANG TEST RING SYNC GATE CONTROL REG WO 12 0C ATK3 ATK2 ATK1 ATK0 DCY3 DCY2 DCY1 DCY0 ATTACK/DECAY WO 13 0D STN3 STN2 STN1 STN0 RLS3 RLS2 RLS1 RLS0 SUSTAIN/RELEASE WO Voice 3 14 0E F7 F6 F5 F4 F3 F2 F2 F1 FREQ LO WO 15 0F F15 F14 F13 F12 F11 F10 F9 F8 FREQ HI WO 16 10 PW7 PW6 PW5 PW4 PW3 PW2 PW1 PW0 PW LO WO 17 11 - - - - PW11 PW10 PW9 PW8 PW HI WO 18 12 NOISE PULSE SAW TRIANG TEST RING SYNC GATE CONTROL REG WO 19 13 ATK3 ATK2 ATK1 ATK0 DCY3 DCY2 DCY1 DCY0 ATTACK/DECAY WO 20 14 STN3 STN2 STN1 STN0 RLS3 RLS2 RLS1 RLS0 SUSTAIN/RELEASE WO Filter 21 15 - - - - - FC2 FC1 FC0 FC LO WO 22 16 FC10 FC9 FC8 FC7 FC6 FC5 FC4 FC3 FC HI WO 23 17 RES3 RES2 RES1 RES0 FILTEX FILT3 FILT2 FILT1 RES/FILT WO 24 18 3OFF HP BP LP VOL3 VOL2 VOL1 VOL0 MODE/VOL WO Misc. 25 19 PX7 PX6 PX5 PX4 PX3 PX2 PX1 PX0 POT X RO 26 1A PY7 PY6 PY5 PY4 PY3 PY2 PY1 PY0 POT Y RO 27 1B O7 O6 O5 O4 O3 O2 O1 O0 OSC3/RANDOM RO 28 1C E7 E6 E5 E4 E3 E2 E1 E0 ENV3 RO APPENDIX S DISK and PRINTER COMMANDS and STATEMENTS The following BASIC commands and statements let you perform a variety of operations on disk drives and any compatible Commodore printer. CLOSE TYPE: I/O Statement FORMAT: CLOSE Action: This statement shuts off any data file or channel to a device. The file number is the same as when the file or device was OPENed (see OPEN statement and the section on INPUT/OUTPUT programming). When working with storage devices like disks, the CLOSE operation stores any incomplete buffers to the device. When this is not performed, the file will be unreadable on the disk. The CLOSE operation isn't as necessary with other devices, but it does free up memory for other files. See your external device manual for more details. EXAMPLES of CLOSE Statement: 10 CLOSE 1 20 CLOSE X 30 CLOSE 9 * (1 + J) CMD TYPE: I/O Statement FORMAT: CMD [,string] Action: This statement switches the primary output device from the TV screen to the file specified. This file could be on disk, printer, or an I/O device like the modem. The file number must be specified in a prior OPEN statement. The string, when specified, is sent to the file. This is handy for titling printouts, etc. When this command is in effect, any PRINT statements and LIST commands will not display on the screen, but will send the text in the same format to the file. To re-direct the output back to the screen, the PRINT# command should send a blank line to the CMD device before CLOSEing, so it will stop expecting data (called "un-listening" the device). Any system error (like ?SYNTAX ERROR) will cause output to return to the screen. Devices aren't un-listened by this, so you should send a blank line after an error condition. (See your printer or disk manual for more details.) EXAMPLES of CMD Statement: OPEN 4,4: CMD 4,"TITLE": LIST: REM LISTS PROGRAM ON PRINTER PRINT#4: CLOSE 4: REM UN-LISTENS AND CLOSES PRINTER 10 OPEN 1, 8 ,4, "TEST": REM CREATE SEQ FILE 20 CMD 8: REM OUTPUT TO SEQ FILE, NOT SCREEN 30 FOR L = 1 TO 100 40 PRINT L: REM PUTS NUMBER IN DISK BUFFER 50 NEXT 60 PRINT# 1: REM UNLISTEN 70 CLOSE 1: REM WRITE UNFINISHED BUFFER, PROPERLY FINISH GET# TYPE: I/O Statement FORMAT: GET# , Action: This statement reads characters one-at-a-time from the device or file specified. It works the same as the GET statement, except that the data comes from a different place than the keyboard. If no character is received, the variable is set to an empty string (equal to "") or to 0 for numeric variables. Characters used to separate data in files, like the comma (,) or key code (ASC code of 13), are received like any other character. When used with device #3 (TV screen), this statement will read characters one by one from the screen. Each use of GET# moves the cursor 1 position to the right. The character at the end of the logical line is changed to a CHR$(13), the key code. EXAMPLES of GET# Statement: 5 GET# 1, A$ 10 OPEN 1, 3: GET# 1, Z7$ 20 GET# 1, A, B, C$, D$ INPUT# TYPE: I/O Statement FORMAT: INPUT# , Action: This is usually the fastest and easiest way to retrieve data stored in a file on disk. The data is in the form of whole variables of up to 80 characters in length, as opposed to the one-at-a-time method of GET#. First, the file must have been OPENed, then INPUT# can fill the variables. The INPUT# command assumes a variable is finished when it reads a code (CHR$(13)), a comma (,), semicolon (;), or colon(:). Quote marks can be used to enclose these characters when writing if they are needed (See PRINT# statement). If the variable type used is numeric, and non-numeric characters are received, a BAD DATA error results. INPUT# can read strings up to 80 characters long, beyond which a STRING TOO LONG error results. When used with device #3 (the screen), this statement will read an entire logical line and move the cursor down to the next line. EXAMPLES of INPUT# Statement: 10 INPUT# 1, A 20 INPUT# 2, A$, B$ LOAD TYPE: Command FORMAT: LOAD "",[,
] Action: The LOAD statement reads the contents of a program file from disk into memory. That way you can use the information LOADed or change the information in some way. The disk unit is normally device number 8. The LOAD closes all open files and, if it is used in direct mode, it performs a CLR (clear) before reading the program. If LOAD is executed from within a program, the program is RUN. This means that you can use LOAD to "chain" several programs together. None of the variables are cleared during a chain operation. If you are using file-name pattern matching, the first file which matches the pattern is loaded. The asterisk in quotes by itself ("*") causes the first file-name in the disk directory to be loaded. If the file-name used does not exist or if it is not a program file, the BASIC error message ?FILE NOT FOUND occurs. If you use the secondary address of 1 this will cause the program to LOAD to the memory location from which it was saved. EXAMPLES of LOAD Command: LOAD A$,8 (Uses the name in A$ to search) LOAD "*",8 (LOADs first program from disk) LOAD "$",8 (LOADs disk directory) LOAD "FUN",8 (LOAD a file from disk) SEARCHING FOR FUN LOADING READY. LOAD "GAME ONE",8,1 (LOAD a file to the specific memory SEARCHING FOR GAME ONE location from which the program was LOADING saved on the disk) READY. OPEN TYPE: I/O Statement FORMAT: OPEN ,[,
][,"[,] [,]"] Action: This statement OPENs a channel for input and/or output to a peripheral device. However, you may NOT need all those parts for every OPEN statement. Some OPEN statements require only 2 codes: 1) LOGICAL FILE NUMBER 2) DEVICE NUMBER The is the logical file number, which relates the OPEN, CLOSE, CMD, GET#, INPUT#, and PRINT# statements to each other and associates them with the file-name and the piece of equipment being used. The logical file number can range from 1 to 255 and you can assign it any number you want in that range. +-----------------------------------------------------------------------+ | NOTE: File numbers over 128 were really designed for other uses so | | it's good practice to use only numbers below 127 for file numbers. | +-----------------------------------------------------------------------+ Each peripheral device (printer, disk drive) in the system has its own number which it answers to. The number is used with OPEN to specify on which device the data file exists. Peripherals like disk drives or printers also answer to several secondary addresses. Think of these as codes which tell each device what operation to perform. The device logical file number is used with every GET#, INPUT#, and PRINT#. The file-name can also be left out, but later on in your program you can NOT call the file by name if you have not already given it one. For disk files, the secondary addresses 1 thru 14 are available for data-files, but other numbers have special meanings in DOS commands. You must use a secondary address when using your disk drive(s). (See your disk drive manual for DOS command details.) The is a string of 1-16 characters and is optional for printer files. If the file is left out the type of file will automatically default to the Program file unless the is given. Sequential files are OPENed for reading =R unless you specify that files should be OPENed for writing =W is specified. A file can be used to OPEN an existing Relative file. Use REL for with Relative files. Relative and Sequential files are for disk only. If you try to access a file before it is OPENed the BASIC error message ?FILE NOT OPEN will occur. If you try to OPEN a file for reading which does not exist the BASIC error message ?FILE NOT FOUND will occur. If a file is OPENed to disk for writing and the file-name already exists, the DOS error message FILE EXISTS occurs. If a file is OPENed that is already OPEN, the BASIC error message FILE OPEN occurs. (See Printer Manual for further details.) EXAMPLES of OPEN Statements: 10 OPEN 2,8,4,"DISK-OUTPUT, (Opens sequential file on disk) -- SEQ,W" For Write 10 OPEN 50,0 (Keyboard input) 10 OPEN 12,3 (Screen output) 10 OPEN 130,4 (Printer output) 10 OPEN 1,2,0,CHR$(10) (Open channel to RS 232 device) 10 OPEN 1,4,0,"STRING" (Send upper case/graphics to the printer) 10 OPEN 1,4,7,"STRING" (Send upper/lower case to printer) 10 OPEN 1,5,7,"STRING" (Send upper/lower case to printer with device #5) 10 OPEN 1,8,15,"COMMAND" (Send a command to disk) 10 OPEN 1,8,1,"NAME,L"+ (Relative file OPEN (1st time) where CHR$(X) X is the length of the relative record) 10 OPEN 1,8,1,"NAME" (Relative or sequential read) PRINT# TYPE: I/O Statement FORMAT: PRINT# [,][<,/;>]... Actions: The PRINT# statement is used to write data items to a logical file. It must use the same number used to OPEN the file. Output goes to the device-number used in the OPEN statement. The expressions in the output-list can be of any type. The punctuation characters between items are the same as with the PRINT statement and they can be used in the same way. The effects of punctuation are different in two significant respects. If no punctuation finishes the list, a carriage-return and a line-feed are written at the end of the data. If a comma or semicolon terminates the output-list, the carriage-return and line-feed are suppressed. Regardless of the punctuation, the next PRINT# statement begins output in the next available character position. The line-feed will act as a stop when using the INPUT# statement; leaving an empty variable when the next INPUT# is executed. The line-feed can be suppressed of compensated for as shown in the examples below. The easiest way to write more than one variable to a file on disk is to set a string variable to CHR$(13), and use that string in between all the other variables when writing the file. EXAMPLES of PRINT# Statement: 1) 10 OPEN 1,8,4, "MY FILE" 20 R$=CHR$(18) (By Changing the CHR$(13) to 30 PRINT#1,1;R$;2;R$;3;R$;4;R$;5 CHR$(44) you put a "," between each 40 PRINT#1,6 variable. CHR$(59) would put a ";" 50 PRINT#1,7 between each variable.) 2) 10 CO$=CHR$(44): CR$=CHR$(13) 20 PRINT#1, "AAA"CO$"BBB", AAA,BBB CCCDDDEEE "CCC";"DDD";"EEE"CR$ (carriage return) "FFF"CR$; FFF(carriage return) 30 INPUT#1, A$,BCDE$,F$ 3) 5 CR$=CHR$(13) 10 PRINT#2, "AAA";CR$;"BBB" (10 blanks) AAA 20 PRINT#2, "CCC"; BBB (10 blanks) CCC 30 INPUT#2, A$,B$,DUMMY$,C$ SAVE TYPE: Command FORMAT: SAVE "",[,
] Action: The SAVE command is used to store the program that is currently in memory onto a diskette file. The program being SAVEd is only affected by the command while the SAVE is happening. The program remains in the current computer memory even after the SAVE operation is completed until you put something else there by using another command. The file type will be "prg" (program). The SAVE statement can be used in your programs and execution will continue with the next statement after the SAVE is completed. When saving programs onto a disk, the must be present. EXAMPLES of SAVE Command: SAVE "FUN DISK",8 (SAVES on disk (device 8 is the disk)) SAVE A$,8 (Store on disk with the name A$) SAVE and REPLACE TYPE: Command FORMAT: SAVE "@0:", Action: This version of the SAVE command is used to overwrite an existing file or program on disk. Saving a program with the normal version of the SAVE command will not store the program if the name used already exists, although no disk error is indicated. EXAMPLE of SAVE and REPLACE: SAVE "@0:ME",8 (Overwrites "ME" on disk with update version) VERIFY TYPE: Command FORMAT: VERIFY "", Action: The VERIFY command is used, in direct or program mode, to compare the contents of a BASIC program file on disk with the program currently in memory. VERIFY is normally used right after a SAVE, to make sure that the program was stored correctly on tape or disk. For disk files (device number 8), the file-name must be present. If any difference in program text are found, the BASIC error message ?VERIFY ERROR is displayed. A program name can be given either in quotes ("") or as a string variable. EXAMPLE of VERIFY Command: 9000 SAVE "ME",8 9010 VERIFY "ME",8 (Looks at device 8 for the program) INDEX A Abbreviations, BASIC commands, 3.2, D Accessories, 1.7 Addition, 3.2 AND operator, C Animation, 5.1, 6.8 Arithmetic, Operators, 3.2, C Arithmetic, Formulas, H Arrays, 9.3 ASC function, C ASCII character codes, F B BASIC abbreviations, 3.2, D commands, C numeric functions, 3.2-3.3, C operators, C other functions, C string functions, C variables, 4.4, C Bibliography, N Binary arithmetic, 7.1 Bit, 7.1 Business aids, A Byte, 7.1 C Calculations, 3.2-3.5 Cartridge slot, 1.1 Cassette unit , 1.1, 2.3 Cassette port, INTRODUCTION CHR$ codes, 6.3, F CHR$ function, C CLR statement, C CLR/HOME key, 2.1 Clock, C CLOSE statement, 2.3, C, S Color adjustment, 1.6 keys, 2.1 memory map, 6.7, G PEEKS and POKES, 6.7 screen and border, 6.4 Commands, BASIC, C Commodore key (see graphic keys), 2.1 Connections optional, 1.3 rear, 1.1 side panel, 1.1 TV/Monitor, 1.1-1.2 CONT command, C ConTRoL key, 2.1 COSine function, C CuRSoR keys, 2.1 Correcting errors, 2.1 Cursor, 1.6 D Data, loading and saving (disk), 2.2, 2.4 DATA statement, 9.1, C Decay, 8.1 DEFine statement, C DELete key, 2.1 DIMension statement, 9.4, C Directory, 2.5 Disk drives commands, 2.2-2.5, S error messages, L Division, 3.2 Duration (see FOR ... NEXT), 4.5 E Editing program, 2.1, 4.3, 6.3 END statement, C Equal, not-equal-to, signs, C Equations, 3.4-3.5 Error messages, L EXPonent function, C Exponentiation, 3.2 F Files, (disk), 2.2-2.5 FOR statement, 4.5 FRE function, C Function keys, 2.1, 5.4 Functions, C G Game controls and ports, 1.1 GET statement, 5.3-5.4, C GET# statement, C, S Getting started, 2.1-2.5 GOSUB statement, C GOTO (GO TO) statement, 4.2, C Graphic keys, 2.1 Graphic symbols (see graphic keys), 2.1, 6.5, E Greater than, C H Headering disks, 2.3 Hyperbolic functions, H I IEEE-488 Interface, 1.7 IF ... THEN statement, C INPUT statement, 5.2, C INPUT# statement, C, S INSerT key, 2.1 INTeger function, 5.5, C Integer variable, 4.4, C I/O pinouts, I J Joysticks, 1.1, I K Keyboard, 2.1 L LEFT$ function, C LENgth function, C Less than, C LET statement, C LIST command, 4.3, C LOAD command, 2.2, C LOGarithm, C Loops, 4.2, 4.5 Lower case characters, 2.1 M Mathematics, 3.2-3.3 formulas, H function table, H symbols, 3.2-3.4, C Memory maps, G MID$ function, C Multiplication, 3.2 Music, 8.1-8.6 N Names program, 2.2, C variable, 4.4-4.5, C NEW command, 2.3, C NEXT statement, 4.5, C NOT operator, C Numeric variables, 4.4, C Numeric functions, C O ON statement, C OPEN statement, 2.3, C, S Operators arithmetic, 3.2-3.4, C logical, C relational, 3.4, C P Parentheses, 3.4 PEEK function, 6.4, C Peripherals, 1.3, 1.7, A POKE statement, 6.4, C POS function, C PRINT statement, 3.1-3.5, C PRINT# statement, C, S Printer commands, S Programs editing, 2.1, 4.3, 6.3 line numbering, 4.1 loading/saving (disk), 2.2-2.5, C, S loading/saving (cassette), 2.2-2.5, C Prompt, 5.2 Q Quotation marks, 3.1, 3.5 R RaNDom function, 5.5, C Random numbers, 5.5 READ statement, 9.1, C REMark statement, C Reserved words (see Command statements), C RESTORE key, 2.1 RESTORE statement, C RETURN key, 2.1 RETURN statement, C RIGHT$ function, C RUN command, C RUN/STOP key, 2.1 S SAVE command, 2.4, C, S Saving programs, 2.4 Screen memory maps, 6.6-6.7 SGN function, C SHIFT key, 2.1 SINe function, C Sound effects, 8.4-8.5 SPC function, C SPRITE EDITOR, A SPRITE graphics, 7.1-7.11 SQuaRe function, C STOP command, C STOP key, 2.1 String variables, 4.4, C STR$ function, C Subscripted variables, 9.3 Subtraction, 3.2, C SYNTAX ERROR, 3.1, L SYS statement, C T TAB function, C TAN function, C TI variable, C TI$ variable, C Time clock, C TV connections, 1.2 U Upper/Lower Case mode, 2.1 USR function, C User defined function (see DEF), C V VALue function, C Variables, 4.4, C array, 9.3-9.5, C dimensions, 9.4 floating point, 4.4, C integer, 4.4, C numeric, 4.4, C string ($), 4.4, C VERIFY command, C, S Voice, 8.1-8.6 W WAIT command, C COMMODORE 64 QUICK REFERENCE CARD SIMPLE VARIABLES TYPE NAME RANGE Real XY +/-1.70141183E+38 +/-2.93873588E-39 Integer XY% +32767...-32768 String XY$ 0 to 255 characters X is a letter (A-Z), Y is a letter or number (0-9). Variable names can be more than 2 characters, but only the first two are recognized. ARRAY VARIABLES TYPE NAME Single Dimension XY(5) Two-Dimension XY(5,5) Three-Dimension XY(5,5,5) Arrays of up to eleven elements (subscripts 0-10) can be used where needed. Arrays with more than eleven elements need to be DIMensioned. ALGEBRAIC OPERATIONS = Assigns value to variable - Negation ^ Exponentiation * Multiplication / Division + Addition - Subtraction RELATION AND LOGICAL OPERATORS = Equal <> Not Equal To < Less Than > Greater Than <= Less Than or Equal To >= Greater Than or Equal To NOT Logical "Not" AND Logical "And" OR Logical "Or" Expressions equals -1 if true, 0 if false. SYSTEM COMMANDS LOAD "NAME" Loads a program from tape SAVE "NAME" Saves a program on tape LOAD "NAME",8 Loads a program from disk SAVE "NAME",8 Saves a program to disk VERIFY "NAME" Verifies that program was SAVEd without errors RUN Executes a program RUN xxx Executes program starting at line xxx STOP Halts execution END Ends execution CONT Continues program execution from line where program was halted PEEK(X) Returns contents of memory location X POKE X,Y Changes contents of location X to value Y SYS xxxxx Jumps to execute a machine language program, starting at xxxxx WAIT X,Y,Z Program waits until contents of location X, when EORed with Z and ANDed with Y, is nonzero. USR(X) Passes value of X to a machine language subroutine EDITING AND FORMATTING COMMANDS LIST Lists entire program LIST A-B Lists from line A to line B REM Message Comment message can be listed but is ignored during program execution TAB(X) Used in PRINT statements. Spaces X positions on screen SPC(X) PRINTs X blanks on line POS(X) Returns current cursor position CLR/HOME Positions cursor to upper left corner of screen SHIFT CLR/HOME Clears screen and places cursor in "Home" position SHIFT INS/DEL Inserts space at current cursor position INST/DEL Deletes character at current cursor position CTRL When used with numeric color key, selects text color. May be used in PRINT statement. CRSR Keys Moves cursor up, down, left right on screen Commodore Key When used with SHIFT selects between upper/lower case and graphic display mode. When used with numeric color key, selects optional text color ARRAYS AND STRINGS DIM A(X,Y,Z) Sets maximum subscripts for A; reserves space for (X+1)*(Y+1)*(Z+1) elements starting at A(0,0,0) LEN(X$) Returns number of characters in X$ STR$(X) Returns numeric value of X, converted to a string VAL(X$) Returns numeric value of X$, up to first nonnumeric character CHR$(X) Returns ASCII character whose code is X ASC(X$) Returns ASCII code for first character of X$ LEFT$(A$,X) Returns leftmost X characters of A$ RIGHT$(A$,X) Returns rightmost X characters of A$ MID$(A$,X,Y) Returns Y characters of A$ starting at character X INPUT/OUTPUT COMMANDS INPUT A$ or A PRINTs '?' on screen and waits for user to enter a string or value INPUT "ABC";A PRINTs message and waits for user to enter value. Can also INPUT A$ GET A$ or A Waits for user type one-character value; no needed DATA A,"B",C Initializes a set of values that can be used by READ statement READ A$ or A Assigns next DATA value to A$ or A RESTORE Resets data pointer to start READing the DATA list again PRINT "A=";A PRINTs string 'A=' and value of A; ';' suppresses spaces; ',' tabs data to next field PROGRAM FLOW GOTO X Branches to line X IF A=3 THEN 10 IF assertion is true THEN execute following part of statement. IF false, execute next line number FOR A=1 to 10 Executes all statements between FOR and corresponding STEP 2: NEXT NEXT, with A, going from 1 to 10 by 2. Step size is 1 unless specified NEXT A Defines end of loop. A is optional GOSUB 2000 Branches to subroutine starting at line 2000 RETURN Marks end of subroutine. Returns to statement following most recent GOSUB ON X GOTO A,B Branches to Xth line number on list. If X=1 branches to A, etc. ON X GOSUB A,B Branches to subroutine at Xth line number in list ABOUT THE COMMODORE 64 USERS GUIDE... Outstanding color ... sound synthesis ... graphics ... computing capabilities ... the synergistic marriage of state-of-the-art technologies. These features make the Commodore 64 the most advanced personal computer in its class. The COMMODORE 64 User's Guide helps you get started in computing, even if you're never used a computer before. Through clear, step-by-step instructions, you are given an insight into the BASIC language and how the Commodore 64 can be put to a myriad of uses. For those already familiar with microcomputers, the advanced programming sections and appendices explain the enhanced features of the Commodore 64 and how to get the most of these expanded capabilities. _____ / ___|___ | / |__/ c o m m o d o r e | \___|__\ C O M P U T E R \_____| PRINTED IN HONG-KONG ********* End of the Project 64 etext of the Commodore 64 MicroComputer User Manual (2d ed) *********