Jump to content
IGNORED

Shooting Sprites


orion1052003

Recommended Posts

The Millers Graphics Sprite Book talks about a sprite shooting down letters of the alphabet and never missing. How would one take a JOYST controlled sprite and make it shoot a bullet? I know you would redefine a character or two to make a bullet. But how would that "bullet" appear to be coming from another sprite?

 

James

Link to comment
Share on other sites

Basically you set up things and go into a game loop. The secret to the bullet appearing to come from another sprite, is simply reading and using the position of the ship when the bullet is fired. Stripped down the game loop could look something like this.

 

1. Read joystick

2. Move ship

3. Read fire button

4. If fire, read position of ship and release bullet from that position

5. If bullet active move bullet

6. Loop

Edited by sometimes99er
Link to comment
Share on other sites

In "Riding for the Brand", here is how I tackled it...

 

REM HERO SHOOT

6000 CALL POSITION(#1,Y,X)

6010 CALL SPRITE(#2,136,2,Y-10,X,-20,0)

6020 RETURN

 

It checks the position of the "ship" (in your case), then creates a new SPRITE which is slightly above the "ship"... this is because I was firing "upward" onscreen. The reason I did not start the SPRITE at the exact location is that I'm doing a coincidence check on all SPRITEs... In other words, I'd be blowing myself up. =) If you were firing from left to right (like Parsec) you could just use (Y,X+10) instead of the example above. =) Hope this helps.

Link to comment
Share on other sites

Part one.

 

100 CALL CLEAR::CALL SCREEN(2)::CALL MAGNIFY(3)
110 CALL CHAR(64,"010307000D1B376F006A3F0F000502018040A0007068B4BA00AAFCF000E0C08")
130 SHIP=192/2::CALL SPRITE(#1,64,16,180,SHIP)
140 CALL JOYST(1,X,Y)::SHIP=((SHIP+X) AND 255)::CALL LOCATE(#1,180,SHIP+1)::GOTO 140

Line 100-130 is setting up things.

 

Line 140 does the following:

 

1. Read the joystick. X returns the values -4, 0 or 4 (that's left, no and right movement).

2. Adjust the ship position. The "AND 255" adjust the value into the range 0-255.

3. Adjust the sprite position. The X position can be a value in the range 1-256.

4. Loop.

Edited by sometimes99er
Link to comment
Share on other sites

Part two.

 

100 CALL CLEAR::CALL SCREEN(2)::CALL MAGNIFY(3)
110 CALL CHAR(64,"010307000D1B376F006A3F0F000502018040A0007068B4BA00AAFCF000E0C08")
120 CALL CHAR(68,"0103030301010101010100010100000180C0C0C08080800080808080008")
130 SHIP=192/2::CALL SPRITE(#1,64,16,180,SHIP)
135 BULLET=200::CALL SPRITE(#2,68,9,BULLET,SHIP)
140 CALL JOYST(1,X,Y)::SHIP=((SHIP+X) AND 255)::CALL LOCATE(#1,180,SHIP+1)
150 IF BULLET<200 THEN BULLET=BULLET-4::IF BULLET<1 THEN BULLET=200
160 CALL LOCATE(#2,BULLET,SHIP+1)::CALL KEY(1,K,S)::IF K<>18 OR S<>1 THEN 140
170 BULLET=170::GOTO 140

Line 120 adds the pattern of the bullet.

Line 135 adds the bullet to the screen using a sprite and setting it outside the visible area.

Line 140 still controls the ship.

Line 150 controls position of the bullet. Only moves if visible.

Line 160 repositions the bullet and if no fire button then loop.

Line 170 activate bullet.

 

Just a quick one. I know it could/should be more "clean" in its logic approach. ;)

Edited by sometimes99er
Link to comment
Share on other sites

I did similar to Somtimes99'ers solution in Inaccurate Invaders.

 

I had the bullet created and in motion off screen. I would then just LOCATE it to the ships location upon firing and relocate it offscreen when it's expended. Much quicker than creating a sprite. And, it retains the motion. I think the locate math to keep the bullet in motion during game play would really make a game unplayable - that's expensive work. Of course then your collision checking won't miss since there's no motion. But then you unfortunately lose game plot enhancing explanations like "the missiles in your submarine are old and unreliable." I made such an explanation in my Piranha game when i was a kid.

 

-H

Link to comment
Share on other sites

  • 3 weeks later...

I did similar to Somtimes99'ers solution in Inaccurate Invaders.

 

I had the bullet created and in motion off screen. I would then just LOCATE it to the ships location upon firing and relocate it offscreen when it's expended. Much quicker than creating a sprite. And, it retains the motion.

 

Nice trick.

 

I guess that means hiding it along the right side of the screen. And ensuring no pixels turned on in left most column of the bullet's pattern.

 

:thumbsup:

Edited by sometimes99er
Link to comment
Share on other sites

How would you do an "enemy" controlled bullet? I was trying to make a space invader near the top of the screen go across from left to right and shoot down at the hero. The hero is on the ground below or jumping in the air at any given moment. This is what I got, doesn't work yet, might be incorrect.

 

 

320 A$="08040F1B3F2F280600000000000000002040E0B0F8E828C00000000000000000"!ALIEN

330 B$="0000001818000000"!ALIENS BULLET

 

 

1081 SUB ALIEN

1082 AR,AC=1

1083 CALL LOCATE(#4,AR,AC) :: CALL MOTION(#4,0,10)!ALIEN

1084 CALL LOCATE(#5,AR+10,AC) :: CALL MOTION(#5,20,0)!BULLET

1086 !ALL SOUND(XX,XX,XX)!FILL IN

1087 CALL POSITION(#4,AR,AC)

1097 CALL COINC(#4,#1,10,A) :: CALL COINC(#5,#1,10,B)!B=BULLET

1098 IF A OR B THEN CALL SOUND(XX,XX,XX) :: CALL DELSPRITE(#1,#5)

1099 SUBEND

Link to comment
Share on other sites

I know you don't want to share your unfinished code, but this isn't really much to work with.

 

In any event, if you want your alien to shoot - you CALL POSITION to find out it's (it looks like you are doing CALL LOCATE - does does placement) location and then generate your downward bullet at that location... You'll need to monitor it until a collision or it goes off screen.

Edited by unhuman
Link to comment
Share on other sites

I put the code in the CALL COINC thread...but here's the latest version. I think the only thing pertaining to the shooting part was the CALL ALIEN part. First game, practically first program, getting really confused but still trying.

 

170 DIM E$(13)
180 CALL CHARSET :: CALL CLEAR :: CALL SCREEN(2)
200 L$="00233123213F0303033F20202020E0000080808080F888889888808080FC0404"
210 L2$="0003010B09090F010101011F10101070008080808080F8888880808080FC0404"
220 R$="000303037F43434303030202023E303000880888F880808080F8080808080E0E"
230 R2$="00030303070F172747070707FCFCC0C0008000808080FC000000E0E060607878"
280 C$="000302030F0B1B03030302020202060600808080E0A0B080808080808080C0C0"
290 C2$="000302030F0B1B03030302020202060600808080E0A0B080808080808080C0C0"
300 !ENEMY ANIMATIONS
305 D$="00003C3C3C3C0000"!DOT
310 M$="00000000000F10204980A0829041221C0000000000C020A02020204080000000"!METEOR
320 A$="08040F1B3F2F280600000000000000002040E0B0F8E828C00000000000000000"!ALIEN
330 B$="0000001818000000"!ALIENS BULLET
340 P$="804020100F080B0A0A0B080F1020408001020408F010D05050D010F008040201"!PULSAR
350 R$=""!SUNRAY
360 !ALL CHAR(124,D$,128,M$,136,A$,140,B$,72,P$,76,R$)!ENEMIES
365 CALL CHAR(128,M$,136,A$,140,B$,72,P$,76,R$)!ENEMIESTEST
380 CALL CHAR(64,RPT$("F",16))!GREY FLOOR
390 CALL HCHAR(21,1,64,128)!GREY FLOOR
400 !CLR CENTER LEFT RIGHT
410 !CENTER 96 LEFT 100 RIGHT 116 CENTER B 112 LEFT B 104 RIGHT B 120
420 CALL CHAR(96,C$,100,L$,104,L2$)! 96-120 CHARSETS 9-12
440 CALL CHAR(112,C2$,116,R$,120,R2$)
450 !DRAW EARTH 645-760,970-1010
460 CALL COLOR(2,6,1,3,6,1,4,3,6,5,15,2)
465 RESTORE 500
470 FOR I=6 TO 14 :: CALL COLOR(I,16,2) :: NEXT I
480 FOR I=0 TO 13 :: READ E$(I) :: CALL CHAR(40+I,E$(I)) :: NEXT I
490 FOR I=0 TO 7 :: READ E$(I) :: CALL CHAR(I+56,E$(I)) :: NEXT I
500 DATA 0000000000000F7F,000000000000F0FE,01030F1F3F7FFFFF
510 DATA 80C0F0F8FCFEFFFF,0001010103030303,FFFFFFFFFFFFFFFF
520 DATA 00808080C0C0C0C0,0303030301010100,C0C0C0C080808000
530 DATA FF7F3F3F1F0F0703,FFFEFCFCF8F0E0C0,7F0F000000000000
540 DATA FEF0000000000000,0800667C18666810
550 DATA E0F07F7F7FFFFFFF,0818F8F8F0F8F0F0,7F7F7F3D1C0E0201
560 DATA F0F0908800180000,03070F0F0F070703,F0FFFFFEFCFCF8F0
570 DATA 0303010101010101,E0C0C0C080808000
580 DISPLAY AT(2,24):CHR$(40)&CHR$(41) :: DISPLAY AT(3,23):CHR$(42)&CHR$(56)&CHR$(57)&CHR$(43)
590 DISPLAY AT(4,22):CHR$(44)&CHR$(45)&CHR$(58)&CHR$(59)&CHR$(45)&CHR$(46)
600 DISPLAY AT(5,22):CHR$(47)&CHR$(45)&CHR$(60)&CHR$(61)&CHR$(45)&CHR$(48)
610 DISPLAY AT(6,23):CHR$(49)&CHR$(62)&CHR$(63)&CHR$(50)
620 DISPLAY AT(7,24):CHR$(51)&CHR$(52)
633 DR=130 :: DC=1 :: MEN=3 :: MDR=193 :: MDC=1
634 CALL SPRITE(#1,96,16,DR,DC) :: CALL MAGNIFY(4)
635 !ALL SPRITE(#2,124,6,193,1)!DOT
636 CALL SPRITE(#3,128,16,MDR,MDC)!METEOR 1,169,20,-20
637 CALL SPRITE(#4,136,4,193,1)!ALIEN 1,1,0,10
638 CALL SPRITE(#5,140,4,193,1)!BULLET AR+10,AC,20,0
639 CALL SPRITE(#6,72,6,193,1)!PULSAR 18,1,0,20
640 !ALL SPRITE(#7,76,?,193,1)!RAY
642 MDR=1 :: MDC=169
643 CALL LOCATE(#3,MDR,MDC) :: CALL MOTION(#3,10,-10)
645 !MAIN LOOP
650 CALL METEOR(MDR,MDC)
660 ANIM=ABS(ANIM-4) :: CALL JOYST(1,X,Y) :: DC=DC+X*4 :: CALL LOCATE(#1,(DR AND 255)+1,(DC AND 255)+1)
661 CALL COINC(#1,#3,10,HIT) :: IF HIT THEN CALL SOUND(300,-1,10) :: CALL DELSPRITE(#1)
663 CALL KEY(1,K,S) :: IF K=18 THEN CALL JUMP(DR,DC,DCD)
664 IF X<>0 THEN CALL PATTERN(#1,ANIM+X*2+108) :: FACE=SGN(X+4) :: DCD=SGN(X) :: GOTO 650
665 CALL PATTERN(#1,FACE*16+96) :: GOTO 650
770 !ENDOFMAINLOOP
775 !ENDING ROUTINE
780 CALL CLEAR :: CALL DELSPRITE(ALL) :: CALL CHARPAT :: CALL SCREEN(5)
785 CALL SOUND(300,-2,10) :: CALL SAY("PLAY AGAIN")
790 DISPLAY AT(12,16):"PLAY MOON MAN AGAIN? PRESS Y OR N"
800 ACCEPT AT(14,16)BEEPVALIDATE("YN"):Z$ :: IF Z$="Y" THEN 160 ELSE END
804 END
805 !///SUBPROGRAMS///
810 SUB JUMP(DR,DC,DCD)
840 SDR=DR :: A=1
844 DISPLAY AT(16,12):"DC= ";DC
850 CALL KEY(1,K,S) :: IF K=18 THEN DR=DR-4 :: DC=DC+(A*PI/45)*5*DCD :: IF DC>240 THEN DC=1 ELSE IF DCD<1 THEN DC=240
853 !F MEN=0 THEN 775
855 CALL COINC(#1,#2,10,CO) :: IF CO THEN CALL SOUND(150,-2,4) :: CALL DELSPRITE(#1) :: MEN=MEN-1
860 !DISPLAY AT(23,1):A;" ";SIN(A*PI/45)
870 IF DR<8 THEN 890
880 CALL LOCATE(#1,DR,DC) :: IF S<0 THEN A=A+1 :: GOTO 850
890 IF DR<SDR THEN DR=DR+4 :: DC=DC+1 :: CALL LOCATE(#1,DR,DC) :: IF DC>240 THEN DC=17
895 CALL COINC(#1,#2,10,CO) :: IF CO THEN CALL SOUND(150,-2,4) :: CALL DELSPRITE(#1) :: MEN=MEN-1
900 IF DR<SDR THEN 890
910 SUBEND
980 SUB DOT
1000 CALL COLOR(#2,12)
1030 DX=INT(RND*256)+1 :: DY=INT(RND*192)+1!DOT ROWS?
1050 CALL COINC(#1,#2,10,C)!TOUCH DOT
1060 COUNT=1
1065 IF C=0 THEN 1030
1067 IF C THEN CALL SOUND(500,110,15) :: CALL DELSPRITE(#2)
1069 !GOTO 1075 HOLD ON SCREEN
1070 SUBEND
1071 SUB METEOR(DR,DC)
1072 DR=1 :: DC=169
1075 CALL COINC(#1,#3,10,CO) :: IF CO THEN CALL SOUND(300,-2,10) :: CALL DELSPRITE(#1)
1076 CALL POSITION(#3,DR,DC) :: IF DR>130 THEN CALL DELSPRITE(#3)
1078 !HOWLONGSHOULDMETEORLAST?
1079 SUBEND
1081 SUB ALIEN
1082 AR,AC=1
1083 CALL LOCATE(#4,AR,AC) :: CALL MOTION(#4,0,10)!ALIEN
1084 CALL LOCATE(#5,AR+10,AC) :: CALL MOTION(#5,20,0)!BULLET
1086 !ALL SOUND(XX,XX,XX)!FILL IN
1087 CALL POSITION(#4,AR,AC)
1097 CALL COINC(#4,#1,10,A) :: CALL COINC(#5,#1,10,B)!B=BULLET
1098 IF A OR B THEN CALL SOUND(XX,XX,XX) :: CALL DELSPRITE(#1,#5)
1099 SUBEND
1100 SUB PULSAR
1120 CALL LOCATE(#6,18,1) :: CALL MOTION(#6,0,20)
1135 P1=6 :: P2=7
1165 FOR I=1 TO 100
1170 CALL COLOR(#6,P1) :: CALL COLOR(#6,P2)
1172 CALL SOUND(100,-1,10,200,5)
1180 CALL COINC(#1,#6,10,C) :: IF C THEN CALL SOUND(300,-1,10) :: CALL DELSPRITE(#1)
1185 NEXT I
1200 SUBEND

Link to comment
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Loading...
  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...