It is currently Sun Jul 05, 2020 6:49 pm

All times are UTC + 1 hour




Post new topic Reply to topic  [ 13 posts ] 
Author Message
 Post subject: Ms BlitzMan translated to PB
PostPosted: Wed Jan 17, 2018 4:50 pm 
Offline
Addict
Addict
User avatar

Joined: Wed Jun 11, 2003 9:33 pm
Posts: 4625
Location: Spa, relaxing and thinking, and learning...
Get the original Ms BlitzMan from:
http://www.incitti.com/Blitz/

Just put this code inside the same dir and run it.

To run windowed mode just create a direct access -W as program parameter (just the same as the blitz version).

Notice: not tested the joystick mode. Modify as your taste. Enjoy.

Code:
;AppTitle "Ms BlitzMan"
; Ms BlitzMan  Version 1.31
; Mark Incitti,  September 2000/June 2001
; mark@incitti.com
; June 11, 2001 - updated sound commands
; June 24, 2001 - more sound tweaks
; Dec  16, 2002 - bouncing pause letters
;             - line pause - L key to toggle
; Feb 23, 2004  - vwait and flip false added, windowed mode

;TRANSLATED TO PureBasic BY PSYCHOPHANTA (15 JANUARY 2018)

Enumeration
; you can change these
#invincible=0      ; 0 normal, change to 1 for invincible *cheat*
#numprizes=3      ; (1,2,3...) Usually 2 or 3
#prizeontime=511   ; (127,255,511, or 1023) -power of 2 -1, Usually 511
#MAXEXSPEED=198   ; (20-198) amount of zoom time
#PRIZEEXSPEED=75   ; (0-200) extra zoom time from eating prize
#speedkey=#PB_Key_Space      ; zoom key 57=SPACE
#speedkeyjoy=1      ; zoom key Button 1 on joypad
#pausekey=#PB_Key_Pause;25      ; pause key - 25=P
#skiplevkey=#PB_Key_F5      ; 0,63 to skip levels with F5 *cheat*
#eyespeed=32      ; (1-32) 32 is 2 pixels per frame (eyes move 2X per frame)
#prizespeed=15      ; (1-32)
#pointtime=110      ; Length of time(# of frames) points are displayed
#dtime=12         ; (8, 16, 32) 60 frames/second  = 1000/60  = ~16

; but don't change these
#gdsz=10      ; block spacing
#numbrds=100   ; number of boards/prizes
#mapwidth=23   ; number of tiles wide
#mapheight=21   ; number of tiles high
#cagex=11      ; location of cage gate x
#cagey=8      ; location of cage gate y
#screenw=320   ; screen width
#screenh=240   ; screen height
#M_XOFF=45      ; center the board horizontally

;game states
#dyingmode      =0
#getreadymode   =1
#playingmode   =2
#gameovermode   =3
#creditsmode   =4
#startmode      =5
#donemode      =6
#nextboardmode   =7
#pausemode      =8

;ghost states
#edible=1
#deadly=2
#eyes=3

;ghost anim frame offsets
#frmgb = 48   ; blue
#frmgw = 50   ; white
#frmge = 52   ; eyes
EndEnumeration
Global score.l,highscore.l,startinglevel.l
Global timer.l,board.l,gmode.l,keyorjoy.l,lastboard.l,sklevel.l=1
Global restorezoom.l    ;restore zoom after death, 1=true
Global freeman.l        ;every XXXXX points get a free pac

Structure ghost
   id.l       ; id number (0-5)
   act.l      ; activity - #edible, #deadly, or #eyes
   bx.l
   by.l       ; big x,y  32*screen pos
   sx.l
   sy.l       ; screen   bx/32, by/32
   x.l
   y.l        ; x,y map coords sx,sy/#gdsz
   vx.l
   vy.l       ; velocity  0-32? 
   gspeed.l   ; vel magnitude
   bluetimer.l; #edible time
   frm.l      ; anim frame
   frmcnt.l   ; anim frm counter
   cage.l     ; flag
   intunnel.l ; flag  0-not in, 1 = u/d, -1 = l/r
   cagetimer.l; time in cage
   changed.l  ; tics since last changed direction
EndStructure
Global NewList g.ghost()
Structure pacman
   bx.l
   by.l       ; big x,y  32*screen pos
   sx.l
   sy.l       ; screen   bx/32, by/32
   x.l
   y.l        ; x,y map coords sx,sy/#gdsz
   vx.l
   vy.l       ; velocity  0-32 ,0-32
   cx.l
   cy.l       ; character x y
   frm.l      ; anim frame
   frmcnt.l   ; frm counter
   intunnel.l ; flag 0,1,-1
EndStructure
Global NewList pac.pacman()
Structure prizetype
   bx.l
   by.l       ; big x,y  0-10230 ,0-6400
   sx.l
   sy.l       ; screen   bx/32, by/32
   x.l
   y.l        ; x,y map coords sx/16,sy/16
   vx.l
   vy.l       ; velocity  0-32 ,0-32
   cx.l
   cy.l       ; character x y
   cage.l     ; flag 0,1
   frm.l      ; anim frame - only 1 frame
   frmcnt.l   ; frm counter - not used
   intunnel.l ; flag 0,1,-1
   bouncedir.l; +/- 1
   bouncehgt.l; 0 to -8
   points.l   ; 100,200,...10000 
EndStructure
Global NewList prize.prizetype()
Structure pointstype
   v.l      ; time on screen counter
   x.l
   y.l
   frm.l
EndStructure
Global NewList pts.pointstype()
; color type for palette changes
Structure rgb
   col.l     ; color 0-7, 4-r, 2-g, 1-b
   x.l:y.l
EndStructure

Global Dim currentmap.a(#mapwidth,#mapheight)      ; the current map
Global Dim mapopen(#mapwidth,#mapheight)      ; bitsum of the u/d/l/r bits of the current map
Global Dim maps.a(#mapwidth,#mapheight,#numbrds)   ; all the maps
Global Dim prizepoints(#numbrds)      ; points awarded for each prize
Global Dim coltable(7,3,#numbrds)      ; 7 colors, r,g,orb, 100 palettes
Global Dim gkol(6,3)            ; 6 ghosts * rgb for each
Global NewList c.rgb   ()         ; for ploting the map blocks in new colors
Declare FlushKeys()
Declare GetPalettes()
Declare PaletteSwitch()
Declare Createghosts(num.l)
Restore points
For t = 0 To #numbrds-1
  Read.l p:prizepoints(t)=p*10
Next
DataSection
points:
Data.l 10  ,20  ,50  ,70  ,100
Data.l 200 ,500 ,300 ,200 ,100
Data.l 110 ,120 ,130 ,140 ,150
Data.l 160 ,170 ,180 ,190 ,200
Data.l 210 ,220 ,230 ,240 ,250
Data.l 260 ,270 ,280 ,290 ,300
Data.l 310 ,320 ,330 ,340 ,350
Data.l 360 ,370 ,380 ,390 ,400
Data.l 410 ,420 ,430 ,440 ,450
Data.l 460 ,470 ,480 ,490 ,500
Data.l 510 ,520 ,530 ,540 ,550
Data.l 560 ,570 ,580 ,590 ,600
Data.l 610 ,620 ,630 ,640 ,650
Data.l 660 ,670 ,680 ,690 ,700
Data.l 710 ,720 ,730 ,740 ,750
Data.l 760 ,770 ,780 ,790 ,800
Data.l 810 ,820 ,830 ,840 ,850
Data.l 860 ,870 ,880 ,890 ,900
Data.l 910 ,920 ,930 ,940 ,950
Data.l 960 ,970 ,980 ,990 ,1000
EndDataSection

RandomSeed(ElapsedMilliseconds())   ; reset the random number generator to random start

AddElement(pac())
AddElement(prize())

; set up the screen
Global windowed.b=0
InitSprite():InitKeyboard():InitSound()
If LCase(ProgramParameter())="-w"
  windowed.b=1:OpenWindowedScreen(OpenWindow(0,240,180,#screenw,#screenh,"Ms BlitzMan",#PB_Window_ScreenCentered|#PB_Window_MinimizeGadget|#PB_Window_SystemMenu|#PB_Window_TitleBar),0,0,#screenw,#screenh,1,0,0)
Else
  OpenScreen(#screenw,#screenh,32,"Ms BlitzMan")
EndIf

; display booting up message
LoadFont (0, "Courier",8)            ; Load Courrier Font, Size 15
StartDrawing(ScreenOutput())
FrontColor(RGB(255,200,200))
DrawingFont(FontID(0))
DrawText(40,100,"MsBlitzMan Version 1.31")
DrawText(40,115,"Programmed in BlitzBasicPC")
DrawText(40,130,"By Mark incitti (2001)")
StopDrawing()
FlipBuffers()
If windowed:For tt.i=1 To 100:If WindowEvent()=#PB_Event_CloseWindow:End:EndIf:Delay(20):Next
Else:Delay(2000)
EndIf
Macro LoadAnimImage(name,imagen,w,h,first,amount)
  Dim name#(amount#-1)
  preservescreen.i=GrabSprite(#PB_Any,0,0,#screenw,#screenh)
  ii.i=LoadSprite(#PB_Any,imagen#)
  DisplaySprite(ii,0,0)
  i.l=SpriteWidth(ii.i)/w#
  For tt=0 To amount#-1
    name#(tt)=GrabSprite(#PB_Any,(first#+tt)%i*w#,(first#+tt)/i*h#,w#,h#)
  Next
  DisplaySprite(preservescreen,0,0)
  FreeSprite(preservescreen)
  FreeSprite(ii.i)
EndMacro
Procedure.i miGrabimage(ima.i,x.u,y.u,w.u,h.u)
  Protected res.i,preservescreen.i=GrabSprite(#PB_Any,0,0,#screenw,#screenh)
  DisplaySprite(ima,0,0)
  res=GrabSprite(#PB_Any,x,y,w,h)
  DisplaySprite(preservescreen,0,0)
  FreeSprite(preservescreen)
  ProcedureReturn res
EndProcedure
; load in the graphics
Global LoadAnimImage(ghostimages,"images/ghosts.bmp",16,16,0,56)   ; rrlluudd*6, bbwwee
Global LoadAnimImage(pacimages,"images/pac.bmp",16,16,0,16)         ; rrrllluuudddxxxx
Global LoadAnimImage(prizeimages,"images/prizes.bmp",16,16,0,100)   ; cherries, strawberry,...
Global LoadAnimImage(blockimages,"images/blocks.bmp",16,16,0,5*13)   ; rgb version of blocks
Global LoadAnimImage(pointimages,"images/points.bmp",16,16,0,106)   ; 100,200,...9900,10000, 200,400,800,1600,3200,6400
Global miscimages=LoadSprite(#PB_Any,"images/misc.bmp")                  ; misc - game over, get ready, Ms.Blitzman, paused, zoom
Global LoadAnimImage(numberimages,"images/numbers.bmp",16,16,0,40)   ; 0,1,2..8,9 in 4 different colors
Global paletteimg=LoadSprite(#PB_Any,"images/palette.bmp")               ; 7 pixels(bg,dot,centre,,trim,,, )

; grab the individual images from the miscimage

Global gameoverimage=miGrabimage(miscimages,0,0,32,16)
Global getreadyimage=miGrabimage(miscimages,32,0,32,16)
Global mspacimage=miGrabimage(miscimages,0,64,96,48)
Global Dim pauseimage(5)
For tt=0 To 5
  pauseimage(tt)=miGrabimage(miscimages,2+tt*5,16,4,16)
Next
Global zoomimage=miGrabimage(miscimages,0,48,22,6)
Global bonusimage=miGrabimage(miscimages,32,16,32,16)
Global nobonusimage=miGrabimage(miscimages,64,0,32,16)
Global nopowerimage=miGrabimage(miscimages,0,32,32,16)
Global zoompowerimage=miGrabimage(miscimages,64,16,32,16)

; load in the sounds
Global sounddot = LoadSound(#PB_Any,"sounds/dot.wav" )
Global soundpower = LoadSound(#PB_Any,"sounds/pill.wav" )
Global soundprize = LoadSound(#PB_Any,"sounds/prize.wav" )
Global soundbounce = LoadSound(#PB_Any,"sounds/bounce.wav" )
Global sounddeath = LoadSound(#PB_Any,"sounds/death.wav" )
Global soundghost = LoadSound(#PB_Any,"sounds/ghost.wav" )
Global soundbonus = LoadSound(#PB_Any,"sounds/clap.wav" )
Global soundboarddone = LoadSound(#PB_Any,"sounds/clap.wav" )
Global soundgameover = LoadSound(#PB_Any,"sounds/over.wav" )
Global soundstartmusic = LoadSound(#PB_Any,"sounds/start.wav" )
Global sounddeadly = LoadSound(#PB_Any,"sounds/lp-hum.wav" )
Global soundeyes = LoadSound(#PB_Any,"sounds/lp-eyes.wav" )
Global soundblue = LoadSound(#PB_Any,"sounds/lp-blue.wav" )

Global chsounddeadly=PlaySound(sounddeadly,#PB_Sound_Loop|#PB_Sound_MultiChannel)
Global chsoundeyes=PlaySound(soundeyes,#PB_Sound_Loop|#PB_Sound_MultiChannel)
Global chsoundblue=PlaySound(soundblue,#PB_Sound_Loop|#PB_Sound_MultiChannel)

; load all the maps
Gosub loadmaps

; grab all the colored pixels from the block images
Gosub GetImageRGB

; fill coltable(7,3,100) with the color values from the palette image
GetPalettes()

bluesleft = 0
gmode = #creditsmode
keyorjoy = 0    ; keyboard=0, joystick=1
highscore = 0
lastboard = 24   ; start from level 1 to 25
timer=0
Global Dim pausex.f(10),Dim pausey.f(10),Dim driftx.f(10),Dim drifty.f(10)

innerloop:
  ExamineKeyboard()
  If KeyboardReleased(#PB_Key_Escape) Or (windowed And WindowEvent()=#PB_Event_CloseWindow):gmode=#creditsmode:EndIf   ; end with esc
  timer=timer+1
  If timer&16384=16384:timer = 0:EndIf
  If timer&2047=2047:Gosub reverse:EndIf
  If timer&15=15:flashpill=flashpill+1:If flashpill>1:flashpill=0:EndIf:EndIf
  If timer&#prizeontime=#prizeontime:Gosub prizeon:EndIf
  Select gmode
     Case #pausemode
       If SoundStatus(soundeyes,chsoundeyes)=#PB_Sound_Playing:PauseSound(soundeyes,chsoundeyes):psnde = 1:Else:psnde = 0:EndIf
        If SoundStatus(sounddeadly,chsounddeadly)=#PB_Sound_Playing:PauseSound(sounddeadly,chsounddeadly):psndd = 1:Else:psndd = 0:EndIf
        If SoundStatus(soundblue,chsoundblue)=#PB_Sound_Playing:PauseSound(soundblue,chsoundblue):psndb = 1:Else:psndb = 0:EndIf
        While KeyboardPushed(#pausekey)=0
          ExamineKeyboard()
          If linepause.b=0
              Gosub drawmap
              Gosub drawprize
              Gosub drawghosts
              Gosub drawpac
              Gosub drawpoints
              Gosub drawzoom
              Gosub drawscore
              Gosub drawpacsleft
              If nozoomflag > 0
                DisplayTransparentSprite(nopowerimage,#gdsz*#cagex-8+#M_XOFF,#gdsz*(#cagey+3))
              EndIf
              If zoompowerflag > 0
                 DisplayTransparentSprite(zoompowerimage,#gdsz*#cagex-8+#M_XOFF,#gdsz*(#cagey+3))
              EndIf
           Else
              ClearScreen(0)   
           EndIf
           Gosub drawpause
           FlipBuffers()
           Delay(30)
           ExamineKeyboard()
           If KeyboardPushed(#PB_Key_L):linepause!1:EndIf
        Wend
        If psnde = 1:ResumeSound(soundeyes,chsoundeyes):EndIf
        If psndd = 1:ResumeSound(sounddeadly,chsounddeadly):EndIf
        If psndb = 1:ResumeSound(soundblue,chsoundblue):EndIf
        gmode = oldmode
     Case #creditsmode
        Gosub soundoff
        Gosub credits
        gmode = #startmode
     Case #startmode
        ;new game
        Gosub setupgame
        gmode = #nextboardmode
     Case #nextboardmode
        ; get new map and reset variables each level
        Gosub setuplevel
        Gosub setpositions
        gmode = #getreadymode
     Case #getreadymode
        ;every level and every life
        zoompowerflag = 0
        nozoomflag = 0
        Gosub drawall
        Gosub drawgetready
        FlipBuffers()
        ExamineKeyboard()
        If KeyboardPushed(#skiplevkey)=0
           If board=0 And looped=0 And played=0
              PlaySound(soundstartmusic)
              Delay(3500)
           Else
              Delay(1500)
           EndIf
        EndIf
        played=1
        gmode = #playingmode
     Case #playingmode
       stime = ElapsedMilliseconds()
       ExamineKeyboard()
        Gosub moveall
        Gosub drawall
        FlipBuffers()
        ;Flip False
        etime = ElapsedMilliseconds() - stime
        ;delay if needed
        If etime < #dtime
           Delay(#dtime-etime)
        EndIf
        ExamineKeyboard()
        If KeyboardPushed(#skiplevkey):gmode = #nextboardmode:EndIf   ; skip boards with skipkey
        If KeyboardPushed(#pausekey)
           oldmode = gmode: gmode = #pausemode   ; pause, remember current mode
           For tt = 0 To 5
              pausex(tt) = #cagex*#gdsz-8+tt*5
              pausey(tt) = (#cagey+3)*#gdsz
              driftx(tt) = Random(1,-1)
              drifty(tt) = Random(1,-1)
           Next
           ; the P needs a boost
           driftx(0) = Random(3,-3)
           drifty(0) = Random(3,-3)
           For tt = 0 To 3
              If board+t-3 >= 0
                 If board < 4:xoff = board:Else:xoff = 3:EndIf
                 pausex(tt+6) = 264-(xoff+tt)*17
                 pausey(tt+6) = #gdsz*#mapheight
                 driftx(tt) = Random(1,-1)
                 drifty(tt) = Random(1,-1)
              EndIf
           Next
        EndIf         
     Case #donemode
       ; all the dots are eaten
        Gosub drawmap
        Gosub drawpac
        Gosub drawzoom
        Gosub drawscore
        Gosub drawpacsleft
        Gosub drawlevel
        Gosub boardclear
        boarddone=0
        gmode = #nextboardmode
     Case #dyingmode
        Gosub death
        Gosub setpositions
        If pacmen > 0:gmode = #getreadymode:EndIf
        If pacmen = 0:gmode = #gameovermode:EndIf
     Case #gameovermode
       Gosub soundoff
        Gosub drawmap
        Gosub drawpacsleft
        Gosub drawlevel
        Gosub drawscore
        Gosub drawzoom
        Gosub drawgameover
        FlipBuffers()
        PlaySound(soundgameover)
        Delay(3500)
        If score > highscore:highscore = score:EndIf
        If board > lastboard:lastboard = board:startinglevel=lastboard:EndIf
        gmode = #creditsmode
  EndSelect
  ExamineKeyboard()
  If KeyboardPushed(#PB_Key_L):linepause!1:EndIf
  ;If KeyboardPushed(#PB_Key_F12) SaveBuffer(FrontBuffer(),"SNAPHOT"+timer+".bmp")
  Goto innerloop
End  ;  mainloop

drawall:
  Gosub drawmap
  Gosub drawprize
  Gosub drawghosts
  Gosub drawpac
  Gosub drawpoints
  Gosub drawzoom
  Gosub drawscore
  Gosub drawlevel
  Gosub drawpacsleft
  If nozoomflag > 0
     DisplayTransparentSprite(nopowerimage,#gdsz*#cagex-8+#M_XOFF,#gdsz*(#cagey+3))
  EndIf
  If zoompowerflag > 0
     DisplayTransparentSprite(zoompowerimage,#gdsz*#cagex-8+#M_XOFF,#gdsz*(#cagey+3))
  EndIf
Return

moveall:
  slowdown = slowdown - 1: If slowdown <0:slowdown = 0:EndIf
  Select keyorjoy
   Case 0
      If KeyboardPushed(#speedkey)
         If exspeed>0
            Gosub movepac:Gosub gobble
            Gosub movepac:Gosub gobble
            exspeed=exspeed-1
         Else
            nozoomflag = 20
         EndIf
      EndIf
   Case 1
    ExamineJoystick(0)
      If JoystickButton(0,#speedkeyjoy)
         If exspeed>0
            Gosub movepac:Gosub gobble
            Gosub movepac:Gosub gobble
            exspeed=exspeed-1
         Else
            nozoomflag = 20
         EndIf
      EndIf
  EndSelect
  Gosub movepac
  Gosub gobble
  Gosub movepac
  Gosub gobble
  pass = 0 ; for regular ghosts
  Gosub moveghosts
  pass = 0 ; for regular ghosts
  Gosub moveghosts
  pass = 1 ; for eyes to give 50% more speed
  Gosub moveghosts
  Gosub moveprize
  Gosub checkcollisions
  If nozoomflag> 0:nozoomflag = nozoomflag - 1:EndIf
  If zoompowerflag> 0:zoompowerflag = zoompowerflag - 1:EndIf
Return

setupgame:
  ;set game variables
  played=0   ;played start music?
  board=startinglevel-1
  looped=0   ;looped through 100 boards?
  score=0
  bonuscount=1
  Select sklevel
   Case 0
      pacmen=5
      freeman=20000
      restorezoom=1
      numghosts = 4
   Case 1
      pacmen=3
      freeman=30000
      restorezoom=1
      numghosts = 4
   Case 2
      pacmen=3
      freeman=50000
      restorezoom=1
      numghosts = 5
   Case 3
      pacmen=2
      freeman=80000
      restorezoom=0
      numghosts = 6
   Case 4
      pacmen=1
      freeman=100000
      restorezoom=0
      numghosts = 6
  EndSelect
  Createghosts(numghosts-1)
Return

Procedure Createghosts(num.l)
  ;delete the current ghosts
  ClearList(g.ghost())
  ;create new ghosts
  For t.l=0 To num.l
     AddElement(g.ghost())
     g()\id = t
  Next
EndProcedure

setuplevel:
  Gosub soundoff
  ForEach pts.pointstype()
     pts()\v = 0
  Next
  munched=0:pillstotal=0:prizeseaten=0:bluesleft=0
  exspeed=#MAXEXSPEED:flashpill=0
  board+1:If board>#numbrds-1:board=0:looped+1:EndIf
  If looped=0 ; go to max and stay there
     ; ghost speed
     ForEach g.ghost()
        t = g()\id
        ts = Int(10-t/2+board/10)
        If ts < 8:ts = 8:EndIf
        If ts > 30:ts = 30:EndIf
        g()\gspeed = ts
     Next
 
     ; ghost #edible speed
     ts = Int(8+board/10)
     If ts < 8:ts = 8:EndIf
     If ts > 30:ts = 30:EndIf
     edspeed = ts
     
     ;ghost tunnel speed
     ts = Int(4+board/10)
     If ts < 4:ts = 4:EndIf
     If ts > 32:ts = 32:EndIf
     gtspeed = ts
     
     ;pac speed
     ts = Int(12+board/10)
     If ts < 12:ts = 12:EndIf
     If ts > 32:ts = 32:EndIf
     pspeed = ts
     
     ;pac tunnel speed
     ts = Int(12+board/10)
     If ts < 12:ts = 12:EndIf
     If ts > 32:ts = 32:EndIf
     ptspeed = ts
  EndIf
  PaletteSwitch()
  Gosub setupmap
Return
 
setpositions:
  timer=0:prizedir=0:gobble=0:bluesleft=0
  ForEach g.ghost()
    g()\x=#cagex
    g()\y=#cagey+1
    g()\sx=#gdsz*g()\x
    g()\sy=#gdsz*g()\y
    g()\vx=g()\gspeed
    g()\vy=0
    g()\bluetimer=0
    g()\bx=g()\sx*32:g()\by=g()\sy*32
    g()\frm=20:g()\intunnel=0
    g()\cage=0:g()\act=#deadly
    g()\cagetimer = 80+g()\id*100-board*2
    If g()\cagetimer < 0:g()\cagetimer=2:EndIf
    If g()\cagetimer > 500:g()\cagetimer=500:EndIf
  Next
 
  pac()\x=#cagex
  pac()\y=#cagey+7
  pac()\sx=#gdsz*pac()\x
  pac()\sy=#gdsz*pac()\y
  pac()\bx=pac()\sx*32
  pac()\by=pac()\sy*32
  pac()\frm=4
  pac()\intunnel=0
  pac()\vx = -pspeed
  pac()\vy = 0
 
  prize()\cage = 1
  prize()\x=#cagex
  prize()\y=#cagey+1
  prize()\sx=#gdsz*prize()\x
  prize()\sy=#gdsz*prize()\y
  prize()\frm=board
 
  FlushKeys()
Return

Procedure FlushKeys()
   ExamineKeyboard():While KeyboardPushed(#PB_Key_All):ExamineKeyboard():Wend
   ExamineKeyboard():For k=1 To 255:KeyboardPushed(k):ExamineKeyboard():Next
EndProcedure

Procedure GetPalettes()
  ClearScreen(0)
   DisplayTransparentSprite(paletteimg,0,0)
   ; grab the 7 colors from the 100 rows
   StartDrawing(ScreenOutput())
   For y = 0 To #numbrds-1
      For x = 0 To 6
         getcolor.l=Point(x,y)
         coltable(x,0,y) = Red(getcolor)
         coltable(x,1,y) = Green(getcolor)
         coltable(x,2,y) = Blue(getcolor)
      Next
      coltable(7,0,y) = coltable(4,0,y)
      coltable(7,1,y) = coltable(4,1,y)
      coltable(7,2,y) = coltable(4,2,y)
   Next
   StopDrawing()
EndProcedure

Procedure PaletteSwitch()
   ClearScreen(0)
   ; plot the red, green, blue, yellow, purple, white, cyan
  ; to the screen in their new colors
   imag.i=CreateSprite(#PB_Any,#screenw,#screenh)
   StartDrawing(SpriteOutput(imag))
   ForEach c.rgb()
      Plot(c()\x,c()\y,RGB(coltable(c()\col,0,board),coltable(c()\col,1,board),coltable(c()\col,2,board)))
   Next
   StopDrawing()
   ; grab the newly colored images
   For row=0 To 4
      For frm=0 To 12
         blockimages(frm+row*13)=miGrabimage(imag,16*frm,row*16,16,16)
      Next
   Next
   FreeSprite(imag)
EndProcedure

GetImageRGB:
   ; draw the block images
   ; check each pixel, if it is r,g,b,y,p,c, or w
   ;   then create an rgb object
   ; later used to plot the image in new colors
  ClearScreen(0)
  For row = 0 To 4
      For frm = 0 To 12
         DisplayTransparentSprite(blockimages(frm+row*13),16*frm,row*16)
      Next
   Next
   StartDrawing(ScreenOutput())
   For y = 1 To 16*5
      For x = 1 To 16*13
        col=Point(x,y)
         cr = Red(col)
         cg = Green(col)
         cb = Blue(col)
         col = 0
         If cr > 128:col|4:EndIf
         If cg > 128:col|2:EndIf
         If cb > 128:col|1:EndIf
         If col > 0
            AddElement(c.rgb())
            c()\col = col
            c()\x = x
            c()\y = y
         EndIf
      Next
   Next
   StopDrawing()
Return

soundoff:
  ;shut off looping sounds
  If SoundStatus(soundeyes,chsoundeyes)=#PB_Sound_Playing:StopSound(soundeyes,chsoundeyes):chsoundeyes=0:EndIf
  If SoundStatus(sounddeadly,chsounddeadly)=#PB_Sound_Playing:StopSound(sounddeadly,chsounddeadly):chsounddeadly=0:EndIf
  If SoundStatus(soundblue,chsoundblue)=#PB_Sound_Playing:StopSound(soundblue,chsoundblue):chsoundblue=0:EndIf
Return

prizeon:
  If prizeseaten < #numprizes
     prizedir = prizedir + 1
     If prizedir > 8:prizedir = 0:EndIf
     If prizedir = 1 And prize()\x=#cagex And prize()\y=#cagey+1
        ; pop out of the cage
        prize()\vx = #prizespeed:If Random(10)>4:prize()\vx=-prize()\vx:EndIf
        prize()\vy = 0
        prize()\sx = #cagex * #gdsz
        prize()\sy = (#cagey-1) * #gdsz
        prize()\bx = prize()\sx * 32
        prize()\by = prize()\sy * 32
        prize()\frm = board ; 0-100
        prize()\points = prizepoints(board)
        prize()\cage=0
        prize()\bouncedir = 1
        prize()\bouncehgt = 0
     EndIf
  EndIf
Return

moveprize:
  If prize()\cage = 0
     ; not in the cage
     If prize()\x<1 Or prize()\x>(#mapwidth-2):prize()\intunnel=-1:EndIf
     If prize()\y<1 Or prize()\y>(#mapheight-2):prize()\intunnel=1:EndIf
     If prize()\intunnel=0
        If prize()\vx<0 Or prize()\vy<0
           prize()\bx=prize()\bx+prize()\vx
           prize()\by=prize()\by+prize()\vy
           prize()\sx=(prize()\bx / 32)
           prize()\sy=(prize()\by / 32)
           prize()\x=prize()\sx/#gdsz
           prize()\y=prize()\sy/#gdsz
           If currentmap(prize()\x,prize()\y) < 52 ; crash ,change dir
              prize()\bx=prize()\bx-prize()\vx
              prize()\by=prize()\by-prize()\vy
              prize()\x=prize()\bx/(#gdsz*32)
              prize()\y=prize()\by/(#gdsz*32)
              pcngflg=10
           EndIf
        Else
           If prize()\vy>0 ; moving down
              y=((prize()\by/32)+#gdsz)/#gdsz
              x=prize()\x
              If currentmap(x,y) < 52
                 pcngflg=10
              Else
                 prize()\by=prize()\by+prize()\vy
              EndIf
           Else ; prize()\vx>0 moving right
              x =   ((prize()\bx/32)+#gdsz)/#gdsz
              y=prize()\y
              If currentmap(x,y) < 52
                 pcngflg=10
              Else
                 prize()\bx=prize()\bx+prize()\vx
              EndIf
           EndIf
        EndIf
     Else
        ; in tunnel
        If prize()\intunnel=-1
           ; left right tunnel
           prize()\bx=prize()\bx+Sign(prize()\vx)*#prizespeed
           If prize()\bx < 0
              prize()\bx = 32*(#mapwidth-1)*#gdsz
           ElseIf prize()\bx > 32*(#mapwidth-1)*#gdsz
              prize()\bx=0
           EndIf
           prize()\sx=prize()\bx/32
           prize()\x=prize()\sx/#gdsz
           If prize()\x>0 Or prize()\x<=(#mapwidth-2):prize()\intunnel=0:EndIf
        EndIf
        If prize()\intunnel=1
           ; up down tunnel
           prize()\by=prize()\by+Sign(prize()\vy)*#prizespeed
           If prize()\by < 0
              prize()\by = 32*(#mapheight-1)*#gdsz
           ElseIf prize()\by > 32*(#mapheight-1)*#gdsz
              prize()\by=0
           EndIf
           prize()\sy=prize()\by/32
           prize()\y=prize()\sy/#gdsz
           If prize()\y > 0 Or prize()\y<=(#mapheight-2):prize()\intunnel=0:EndIf
        EndIf
     EndIf
     prize()\sx=prize()\bx/32
     prize()\sy=prize()\by/32
     prize()\x=prize()\sx/#gdsz
     prize()\y=prize()\sy/#gdsz
 
     If prize()\bx%(32*#gdsz)<33 And prize()\by%(32*#gdsz)<33:square=1:Else:square=0:EndIf
 
     If square And Random(10)>6 And pcngflg=0:pcngflg = 10:EndIf
     If pcngflg>0:pcngflg=pcngflg-1:EndIf
     If pcngflg=9
        prize()\sx=prize()\x*#gdsz
        prize()\sy=prize()\y*#gdsz
        prize()\bx=prize()\sx*32
        prize()\by=prize()\sy*32
        Gosub changedirprize
     EndIf
 
     If square And prize()\x=#cagex And prize()\y = #cagey-1 And prizedir >1
        ; go back in cage and wait
        prizedir = 8
        prize()\cage=1
        prize()\y=#cagey+1
        prize()\sy=prize()\y*#gdsz
     EndIf
     ;\bouncehgt goes from 0 To -8 back to 0
     If prize()\bouncehgt <= -16 Or prize()\bouncehgt >=0:prize()\bouncedir = -prize()\bouncedir:EndIf
     prize()\bouncehgt = prize()\bouncehgt + prize()\bouncedir
     If prize()\bouncehgt = 0
        PlaySound(soundbounce)
     EndIf
  EndIf
Return

changedirprize:
  pick2=-1:If Random(10)>4:pick2=1:EndIf
  ; select the destination according to the prizedir
  Select (prizedir)
     Case 0
        ; randon dir
        xdiff=1:ydiff=1
        If Random(10)>4:xdiff=-1:EndIf
        If Random(10)>4:ydiff=-1:EndIf
     Case 1
        ; towards bottom right corner
        xdiff=1:ydiff=1
     Case 2
        ; towards bottom left corner
        xdiff=-1:ydiff=1
     Case 3
        ; towards top left corner
        xdiff=-1:ydiff=-1
     Case 4
        ; towards top right corner
        xdiff=1:ydiff=-1
     Default ; 5,6,7,8
        ; towards cage center
        xdiff=Sign(#cagex-prize()\x):ydiff=Sign((#cagey+1)-prize()\y)
  EndSelect
  Select mapopen(prize()\x,prize()\y)
     Case 0
        ; how? you shouldn't be on this tile!
     Case 1;up
        prize()\vy=-#prizespeed:prize()\vx=0
     Case 2;right
        prize()\vx=#prizespeed:prize()\vy=0
     Case 4;down
        prize()\vy=#prizespeed:prize()\vx=0
     Case 8;left
        prize()\vx=-#prizespeed:prize()\vy=0
     Case 3
        If prize()\vy>0:prize()\vx=#prizespeed:prize()\vy=0:Else:prize()\vx=0:prize()\vy=-#prizespeed:EndIf
     Case 5;u d
     Case 6;r d
        If prize()\vy<0:prize()\vx=#prizespeed:prize()\vy=0 :Else:prize()\vx=0:prize()\vy=#prizespeed:EndIf
     Case 10;l r
     Case 12;d l
        If prize()\vy<0:prize()\vx=-#prizespeed:prize()\vy=0:Else:prize()\vx=0:prize()\vy=#prizespeed:EndIf
     Case 9;l u
        If prize()\vy>0:prize()\vx=-#prizespeed:prize()\vy=0:Else:prize()\vx=0:prize()\vy=-#prizespeed:EndIf
     Case 7;urd
        If prize()\vx<0;going r , turn u or d
           prize()\vx=0:prize()\vy=ydiff*#prizespeed; up or d
           If prize()\vy = 0:prize()\vy=pick2*#prizespeed:EndIf
        Else
           If xdiff = 1:prize()\vx=#prizespeed:prize()\vy=0:EndIf; right
        EndIf
     Case 11
        If prize()\vy>0
           prize()\vy=0:prize()\vx=xdiff*#prizespeed; l or r
           If prize()\vx = 0:prize()\vx=pick2*#prizespeed:EndIf
        Else
           If ydiff = -1 :prize()\vy=-#prizespeed:prize()\vx=0:EndIf; u
        EndIf
     Case 13
        If prize()\vx>0
           prize()\vx=0:prize()\vy=ydiff*#prizespeed  ;  up or down
           If prize()\vy = 0:prize()\vy=pick2*#prizespeed:EndIf
        Else
           If xdiff = -1:prize()\vx=-#prizespeed:prize()\vy=0:EndIf; l
        EndIf
     Case 14
        If prize()\vy<0
           prize()\vy=0:prize()\vx=xdiff*#prizespeed    ; l or r
           If prize()\vx = 0:prize()\vx=pick2*#prizespeed:EndIf
        Else
           If ydiff = 1:prize()\vy=#prizespeed:prize()\vx=0:EndIf; d
        EndIf
     Case 15
        If Random(10) > 4; keep going 40% of time
           If prize()\vx = 0 ; going up or down
              If Random(10)>4 Or xdiff=0:xdiff = pick2:EndIf
              prize()\vx = xdiff*#prizespeed:prize()\vy=0
           Else ; going l or r
              If Random(10)>4 Or ydiff=0:ydiff = pick2:EndIf
              prize()\vy = ydiff*#prizespeed:prize()\vx=0
           EndIf
        EndIf
  EndSelect
Return

movepac:
  If slowdown > 0:slowmo=2:Else:slowmo = 1:EndIf ;go half speed when digesting
  wdirx=0:wdiry=0
  If keyorjoy=0
      If KeyboardPushed(#PB_Key_Left):wdirx = -1:EndIf
      If KeyboardPushed(#PB_Key_Right):wdirx = 1:EndIf
      If KeyboardPushed(#PB_Key_Up):wdiry = -1:EndIf
      If KeyboardPushed(#PB_Key_Down):wdiry = 1:EndIf
   Else
     ExamineJoystick(0)
    wdirx=JoystickAxisX(0):wdiry=JoystickAxisY(0)
  EndIf
  If pac()\sx%#gdsz=0 And pac()\sy%#gdsz=0:square=1:Else:square=0:EndIf
  If square Or (pac()\vx=0 And pac()\vy=0)
     If wdirx=-1 And mapopen(pac()\x,pac()\y)&8=8
        pac()\vx=-pspeed
        pac()\vy=0
     EndIf
     If wdirx=1 And mapopen(pac()\x,pac()\y)&2=2
        pac()\vx=pspeed
        pac()\vy=0
     EndIf
     If wdiry=-1 And mapopen(pac()\x,pac()\y)&1=1
        pac()\vy=-pspeed
        pac()\vx=0
     EndIf
     If wdiry=1 And mapopen(pac()\x,pac()\y)&4=4
        pac()\vy=pspeed
        pac()\vx=0
     EndIf
  Else
     If wdirx=-1 And pac()\vx
        pac()\vx=-pspeed
        pac()\vy=0
     EndIf
     If wdirx=1 And pac()\vx
        pac()\vx=pspeed
        pac()\vy=0
     EndIf
     If wdiry=-1 And pac()\vy
        pac()\vy=-pspeed
        pac()\vx=0
     EndIf
     If wdiry=1 And pac()\vy
        pac()\vy=pspeed
        pac()\vx=0
     EndIf
  EndIf
 
  If pac()\intunnel=0
     If pac()\x<1 Or pac()\x>#mapwidth-2:pac()\intunnel=-1:EndIf
     If pac()\y<1 Or pac()\y>#mapheight-2:pac()\intunnel=1:EndIf
     If pac()\vx<0 Or pac()\vy<0
        pac()\bx=pac()\bx+(pac()\vx/slowmo)
        pac()\by=pac()\by+(pac()\vy/slowmo)
        pac()\sx=pac()\bx/32
        pac()\sy=pac()\by/32
        pac()\x=pac()\sx/#gdsz
        pac()\y=pac()\sy/#gdsz
        If currentmap(pac()\x,pac()\y)<52 ; crash ,change dir
           pac()\bx=pac()\bx-pac()\vx/slowmo
           pac()\by=pac()\by-pac()\vy/slowmo
           pac()\x=pac()\bx/(#gdsz*32)
           pac()\y=pac()\by/(#gdsz*32)
           If pac()\vy<0:pac()\frm=8:Else:pac()\frm=5:EndIf
           pac()\vx=0:pac()\vy=0
        EndIf
     Else
        ;down or right
        If pac()\vy>0
           ;moving down
           y=((pac()\by/32)+#gdsz)/#gdsz
           x=pac()\x
           If currentmap(x,y)<52 
              pac()\vy=0:pac()\vx=0
              pac()\frm=11
           Else
              ;pac()\bx=pac()\bx+(pac()\vx/slowmo)
              pac()\by=pac()\by+(pac()\vy/slowmo)
              ;pac()\sx=pac()\bx/32
              pac()\sy=pac()\by/32
              ;pac()\x=pac()\sx/#gdsz
              pac()\y=pac()\sy/#gdsz
           EndIf
        ElseIf pac()\vx>0
           ; vx > 0 - moving right
           x = ((pac()\bx/32)+#gdsz)/#gdsz
           y=pac()\y
           If currentmap(x,y)<52
              pac()\vy=0:pac()\vx=0
              pac()\frm=2
           Else
              pac()\bx=pac()\bx+(pac()\vx/slowmo)
              ;pac()\by=pac()\by+(pac()\vy/slowmo)
              pac()\sx=pac()\bx/32
              ;pac()\sy=pac()\by/32
              pac()\x=pac()\sx/#gdsz
              ;pac()\y=pac()\sy/#gdsz
           EndIf
        EndIf
     EndIf
  Else
     ; in tunnel
     If pac()\intunnel=-1
        ;left right tunnel
        pac()\bx=pac()\bx+Sign(pac()\vx)*ptspeed
        If pac()\bx < 0
           pac()\bx = 32*(#mapwidth-1)*#gdsz
        Else
           If pac()\bx > 32*(#mapwidth-1)*#gdsz:pac()\bx = 0:EndIf
        EndIf
        pac()\sx=pac()\bx/32
        pac()\x=pac()\sx/#gdsz
        If pac()\bx>0 And pac()\x<=(#mapwidth-2):pac()\intunnel=0:EndIf
     EndIf
     If pac()\intunnel=1
        ; up down tunnel
        pac()\by=pac()\by+Sign(pac()\vy)*ptspeed
        If pac()\by < 0
           pac()\by = 32*(#mapheight-1)*#gdsz
        Else
           If pac()\by > 32*(#mapheight-1)*#gdsz:pac()\by = 0:EndIf
        EndIf
        pac()\sy=pac()\by/32
        pac()\y=pac()\sy/#gdsz
        If pac()\by>0 And pac()\y<=#mapheight-2:pac()\intunnel=0:EndIf
     EndIf
  EndIf
 
  pac()\sx=pac()\bx/32
  pac()\cx=Int((((pac()\bx+(pac()\vx*2))/32)+4)/#gdsz)
  pac()\sy=pac()\by/32
  pac()\cy=Int((((pac()\by+(pac()\vy*2))/32)+4)/#gdsz)
  pac()\x=pac()\sx/#gdsz
  pac()\y=pac()\sy/#gdsz
 
  char.a=currentmap(pac()\cx,pac()\cy)
  gobble = 0
  If char<>255 And char>51:gobble = 1:EndIf
 
  If pac()\vx>0:pac()\frm=0+2:EndIf
  If pac()\vx<0:pac()\frm=3+2:EndIf
  If pac()\vy<0:pac()\frm=6+2:EndIf
  If pac()\vy>0:pac()\frm=9+2:EndIf
 
  If pac()\vx <>0 Or pac()\vy <>0
     ;images are rrrllluuuddd
     pac()\frmcnt=pac()\frmcnt+2:If pac()\frmcnt > 63:pac()\frmcnt=0:EndIf
     sc=Int(pac()\frmcnt/16)
     Select sc
        Case 0
           pac()\frm=pac()\frm-1
        Case 1
           pac()\frm=pac()\frm-2
        Case 2
           pac()\frm=pac()\frm-1
        Case 3
           pac()\frm=pac()\frm
     EndSelect
  EndIf
Return

moveghosts:
ForEach g.ghost()
   If g()\act=#eyes Or pass=0
      ;enter the cage?
      If g()\act=#eyes And g()\y=#cagey-1 And g()\x=#cagex
        If g()\sx%#gdsz=0 And g()\cage=0
            If SoundStatus(soundeyes,chsoundeyes)=#PB_Sound_Playing:StopSound(soundeyes,chsoundeyes):chsoundeyes=0:EndIf
            If SoundStatus(sounddeadly,chsounddeadly)<>#PB_Sound_Playing
               chsounddeadly=PlaySound(sounddeadly,#PB_Sound_MultiChannel)
            EndIf
            g()\vx=0:g()\vy=10   ;gspeed
            g()\cage=1
         EndIf
      EndIf
      ;exit cage ?
      If g()\act<>#eyes And g()\y-1=#cagey And g()\x=#cagex
         g()\cagetimer = g()\cagetimer-1
         If g()\sx%#gdsz=0 And g()\cagetimer<0
            g()\vx=0:g()\vy=-g()\gspeed
            g()\cage=-1
            If SoundStatus(sounddeadly,chsounddeadly)<>#PB_Sound_Playing
               chsounddeadly=PlaySound(sounddeadly,#PB_Sound_MultiChannel)
            EndIf
         EndIf
      EndIf
      ;if not in cage - move
      If g()\cage=0
         If g()\x<1 Or g()\x>(#mapwidth-2):g()\intunnel=-1:EndIf
         If g()\y<1 Or g()\y>(#mapheight-2):g()\intunnel=1:EndIf
         ; not in tunnel
         If g()\intunnel=0
            If g()\vx<0 Or g()\vy<0
               ; moving up or left
               If g()\act=#eyes
                  If g()\vx<0:g()\vx=-#eyespeed:Else:g()\vy=-#eyespeed:EndIf
               ElseIf g()\act=#edible
                  If g()\vx<0:g()\vx=-edspeed:Else:g()\vy=-edspeed:EndIf
               EndIf
               g()\bx=g()\bx + g()\vx  ; 0 - 32*#mapwidth*#gdsz
               g()\by=g()\by + g()\vy  ; 0 - 32*#mapheight*#gdsz
               g()\sx=g()\bx/32
               g()\sy=g()\by/32
               g()\x=g()\sx/#gdsz
               g()\y=g()\sy/#gdsz
               If currentmap(g()\x,g()\y)<52 ; crash ,change dir
                  g()\bx=g()\bx - g()\vx  ; 0 - 32*#mapwidth*#gdsz
                  g()\by=g()\by - g()\vy  ; 0 - 32*#mapheight*#gdsz
                  g()\x=g()\bx/(#gdsz*32)
                  g()\y=g()\by/(#gdsz*32)
                  Gosub changedirg
                  g()\changed=10
                  g()\bx=g()\bx + g()\vx  ;0-32*#mapwidth*#gdsz
                  g()\by=g()\by + g()\vy  ;0-32*#mapheight*#gdsz
               EndIf
            Else
               If g()\vy>0
                  ; moving down
                  If g()\act=#eyes:g()\vy=#eyespeed:ElseIf g()\act=#edible:g()\vy=edspeed:EndIf
                  tsy=g()\sy+#gdsz
                  y=tsy/#gdsz
                  x=g()\x
                  If currentmap(x,y)<52
                     Gosub changedirg  ; crash ,change dir
                     g()\changed=10
                  EndIf
                  g()\bx=g()\bx + g()\vx  ;0-32*#mapwidth*#gdsz
                  g()\by=g()\by + g()\vy  ;0-32*#mapheight*#gdsz
               Else
                  ; \vx>0 - moving right
                  If g()\act=#eyes:g()\vx=#eyespeed:ElseIf g()\act=#edible:g()\vx=edspeed:EndIf
                  tsx=g()\sx + #gdsz
                  x=tsx/#gdsz
                  y=g()\y
                  If currentmap(x,y)<52
                     Gosub changedirg ; crash ,change dir
                     g()\changed=10
                  EndIf
                  g()\bx=g()\bx + g()\vx ;0-32*#mapwidth*#gdsz
                  g()\by=g()\by + g()\vy ;0-32*#mapheight*#gdsz
               EndIf
            EndIf
            g()\sx=g()\bx/32
            g()\sy=g()\by/32
            g()\x=g()\sx/#gdsz
            g()\y=g()\sy/#gdsz
      
            g()\changed=g()\changed-1
            If g()\changed<=0
               If g()\sx%#gdsz=0 And g()\sy%#gdsz=0
                  Select g()\act
                     Case #deadly  ; 2
                        If Random(10)  > 4 ; 50% of time change dir
                           Gosub changedirg
                           g()\changed=5; don't change again until 10 steps away
                      EndIf
                     Case #edible  ; 1
                        If Random(10)  > 7 ; blue is dumb, don't change as much
                           Gosub changedirg
                           g()\changed=5; don't change again until 10 steps away
                     EndIf
                     Case #eyes    ; 3
                        If Random(10)  > 2 ; #eyes head home quickly
                           Gosub changedirg
                           g()\changed=5; don't change again until 10 steps away
                      EndIf
                  EndSelect
               EndIf
            EndIf
         Else
            ; intunnel<>0
            If  g()\intunnel=-1
               ; left right
               g()\bx=g()\bx + Sign(g()\vx)*gtspeed
               If g()\bx < 0
                  g()\bx = 32*(#mapwidth-1)*#gdsz
               ElseIf g()\bx > 32*(#mapwidth-1)*#gdsz
                  g()\bx = 0
               EndIf
               g()\sx=g()\bx/32
               g()\x=g()\sx/#gdsz
               If g()\x>0 And g()\x<=#mapwidth-2:g()\intunnel=0:EndIf
            EndIf
            If g()\intunnel=1
               ; up down
               g()\by=g()\by + Sign(g()\vy)*gtspeed
               If g()\by < 0
                  g()\by = 32*(#mapheight-1)*#gdsz
               ElseIf g()\by > 32*(#mapheight-1)*#gdsz
                  g()\by = 0
               EndIf
               g()\sy=g()\by/32
               g()\y=g()\sy/#gdsz
               If g()\y>0 And g()\y<=#mapheight-2:g()\intunnel=0:EndIf
            EndIf
         EndIf
      Else
         ; inside cage stuff
         g()\by=g()\by + Sign(g()\vy)*8 ; move slowly in/out
         g()\sy=g()\by/32
         g()\y=g()\sy/#gdsz
         If g()\y<(#cagey-1) Or g()\y>#cagey
            If g()\cage=1
               g()\act=#deadly
               g()\cagetimer = 20+g()\id*(20-board/5)
               g()\by=(#cagey+1)*#gdsz*32
               g()\vy=0
               g()\vx=g()\gspeed
            Else
               g()\by=(#cagey-1)*#gdsz*32
            EndIf
              g()\cage=0
         EndIf
      EndIf
      
      ; select anim frame
      ;images are:   rrlluudd - red   
      ;then      rrlluudd - pink 
      ;then      rrlluudd - cyan
      ;then      rrlluudd - orange
      ;then      rrlluudd - green
      ;then      rrlluudd - yellow      
      ;then      bbwwee
                  
      g()\frmcnt=g()\frmcnt+1:If g()\frmcnt>63:g()\frmcnt=0:EndIf

      If g()\vy>0:g()\frm=6+g()\id*8:EndIf
      If g()\vy<0:g()\frm=4+g()\id*8:EndIf
      If g()\vx>0:g()\frm=0+g()\id*8:EndIf
      If g()\vx<0:g()\frm=2+g()\id*8:EndIf
      
      If g()\bluetimer > 0
         g()\bluetimer = g()\bluetimer-1
      EndIf
      If g()\act=#edible
         If g()\bluetimer = 0
            g()\act = #deadly
            bluesleft = bluesleft - 1
            g()\vx = Sign(g()\vx) * g()\gspeed
            g()\vy = Sign(g()\vy) * g()\gspeed
            If SoundStatus(soundblue,chsoundblue)=#PB_Sound_Playing:StopSound(soundblue,chsoundblue):chsoundblue=0:EndIf
            If SoundStatus(sounddeadly,chsounddeadly)<>#PB_Sound_Playing
               chsounddeadly = PlaySound(sounddeadly,#PB_Sound_MultiChannel)
            EndIf
         Else
            g()\frm = #frmgb   ; blue  32,33
            ;                                                               setsoundPitch(chsoundblue,35000-g()\bluetimer*20)
            If g()\bluetimer<160
               If g()\frmcnt&4=4:g()\frm = #frmgw:EndIf ; white 34,35
            Else
               If g()\bluetimer<360
                  If g()\frmcnt&32=32:g()\frm = #frmgw:EndIf ; white 34,35
               EndIf
            EndIf
         EndIf
      EndIf
      
      If g()\frmcnt > 30:g()\frm = g()\frm+1:EndIf
      
      If g()\act=#eyes
         g()\frm= #frmge ; #eyes 36,37
         If g()\frmcnt&16=16:g()\frm = g()\frm + 1:EndIf ; blink
      EndIf
   EndIf
Next
Return

changedirg:
  xdiff=Sign(pac()\x-g()\x)
  ydiff=Sign(pac()\y-g()\y)
  t=g()\id
  ;if pink,ink, or sue head towards prize 20% of time
  If t > 3 And Random(15) > 11
     xdiff=Sign(prize()\x-g()\x):ydiff=Sign(prize()\y-g()\y)
  EndIf
 
  ; if #eyes, head towards cage
  If g()\act=#eyes
     xdiff=Sign(#cagex-g()\x):ydiff=Sign((#cagey-1)-g()\y)
  EndIf
 
  ; if blue then head away from pac
  If g()\act=#edible:xdiff=-xdiff:ydiff=-ydiff:EndIf
 
  pick2=-1:If Random(10)>4:pick2=1:EndIf

  Select mapopen(g()\x,g()\y)
     Case 0
        ; how? you shouldn't be on this tile!
     Case 1
        ; up
        g()\vy=-g()\gspeed:g()\vx=0
     Case 2
        ; right
        g()\vx=g()\gspeed:g()\vy=0
     Case 4
        ; down
        g()\vy=g()\gspeed:g()\vx=0
     Case 8
        ; left
        g()\vx=-g()\gspeed:g()\vy=0
     Case 3
        ; up or right
        If g()\vy>0:g()\vx=g()\gspeed:g()\vy=0:Else:g()\vx=0:g()\vy=-g()\gspeed:EndIf
     Case 5
        ; ghosts don't reverse on their own
        ; up OR down
        ; If Rnd > .95
        ;  \vx=0:\vy=ydiff*\gspeed
        ; EndIf
     Case 6
        ; right or down
        If g()\vy<0:g()\vx=g()\gspeed:g()\vy=0:Else:g()\vx=0:g()\vy=g()\gspeed:EndIf
     Case 10
        ; right or left
         If g()\vy < 0  ; getting out of cage only
           g()\vx=xdiff*g()\gspeed:g()\vy=0
           If g()\vx=0:g()\vx = g()\gspeed:EndIf
        EndIf
     Case 12
        ; down or left
        If g()\vy<0:g()\vx=-g()\gspeed:g()\vy=0:Else:g()\vx=0:g()\vy=g()\gspeed:EndIf
     Case 9
        ; up or left
        If g()\vy>0:g()\vx=-g()\gspeed:g()\vy=0:Else:g()\vx=0:g()\vy=-g()\gspeed:EndIf
     Case 7
        ; up right down
        If g()\vx<0
           ; moving left hit wall, go u or d
           g()\vx=0:g()\vy=ydiff*g()\gspeed; up or d
           If g()\vy = 0:g()\vy=pick2*g()\gspeed:EndIf
        Else
           ; else cont up or down, or turn right
           If xdiff = 1:g()\vx=g()\gspeed:g()\vy=0:EndIf; right
        EndIf
     Case 11
        ; up left right
        If g()\vy>0
           ; moving d hit wall, go l or r
           g()\vy=0:g()\vx=xdiff*g()\gspeed; l or r
           If g()\vx = 0:g()\vx=pick2*g()\gspeed:EndIf
        Else
           ; else moving l or r, cont or turn u
           If ydiff = -1:g()\vy=-g()\gspeed:g()\vx=0:EndIf; u
        EndIf
     Case 13
        ; up left down
        If g()\vx>0
           ; moving r hit wall, go u or d
           g()\vx=0:g()\vy=ydiff*g()\gspeed  ;  up or down
           If g()\vy = 0:g()\vy=pick2*g()\gspeed:EndIf
        Else
           ; else moving up or down, cont or turn l
           If xdiff = -1:g()\vx=-g()\gspeed:g()\vy=0:EndIf; l
        EndIf
     Case 14
        ; down left right
        If g()\vy<0
           ; moving u hit wall, go l or r
           g()\vy=0:g()\vx=xdiff*g()\gspeed    ; l or r
           If g()\vx = 0:g()\vx=pick2*g()\gspeed:EndIf
        Else
           ; else moving l or r, cont or turn d
           If ydiff = 1:g()\vy=g()\gspeed:g()\vx=0:EndIf; d
        EndIf
     Case 15
        ; up right down or left open
        If g()\vx = 0 ; going up or down
           If Random(10)>4 Or xdiff=0:xdiff = pick2:EndIf
           g()\vx = xdiff*g()\gspeed:g()\vy=0
        Else ; going l or r
           If Random(10)>4 Or ydiff=0:ydiff = pick2:EndIf
           g()\vy = ydiff*g()\gspeed:g()\vx=0
        EndIf
  EndSelect
Return

reverse:
  ForEach g.ghost()
     If g()\act = #deadly
        If g()\vy And g()\cage=0:g()\vy=-g()\vy:EndIf
        If g()\vx:g()\vx=-g()\vx:EndIf
     EndIf
  Next
Return

turnblue:
  ForEach g.ghost()
     If g()\act<>#eyes
        ;change direction if not blue
        If g()\act<>#edible
            If g()\vy And g()\cage=0:g()\vy=-g()\vy:EndIf
           If g()\vx:g()\vx=-g()\vx:EndIf
           bluesleft = bluesleft + 1
        EndIf
        g()\bluetimer = 1000-board*10
        g()\frm=36
        g()\act=#edible
        If SoundStatus(sounddeadly,chsounddeadly)=#PB_Sound_Playing:StopSound(sounddeadly,chsounddeadly):chsounddeadly=0:EndIf
        ;If SoundStatus(soundeyes,chsoundeyes)=#PB_Sound_Playing:StopSound(soundeyes,chsoundeyes):chsoundeyes=0:endif
        If SoundStatus(soundblue,chsoundblue)<>#PB_Sound_Playing
           chsoundblue = PlaySound(soundblue)
           ;                                                   ChannelPitch chsoundblue,25000-360*10
        EndIf
     EndIf
  Next
  killed=0
Return

drawghosts:
  ForEach g.ghost()
     DisplayTransparentSprite(ghostimages(g()\frm),g()\sx+#M_XOFF,g()\sy)
  Next
Return

drawpac:
  If pac()\sx > 4 And pac()\sx < (#mapwidth-1)*#gdsz-4
     DisplayTransparentSprite(pacimages(pac()\frm),pac()\sx+#M_XOFF,pac()\sy)
  EndIf
Return

drawpoints:
  ForEach pts.pointstype()
     If pts()\v > 0
        pts()\v=pts()\v-1
        DisplayTransparentSprite(pointimages(pts()\frm),pts()\x+#M_XOFF,pts()\y)
        If pts()\v = 0:DeleteElement(pts(),1):EndIf
     EndIf
  Next
Return

drawprize:
  If prize()\cage = 0
     prizey=prize()\sy+prize()\bouncehgt/2+2:If prizey<0:prizey = 0:EndIf
     DisplayTransparentSprite(prizeimages(prize()\frm),prize()\sx+#M_XOFF,prizey)
  Else
     ;draw it in the cage
     DisplayTransparentSprite(prizeimages(prize()\frm),prize()\sx+#M_XOFF,prize()\sy)
  EndIf
Return

drawpacsleft:
  t = 1
  While t<6 And t<pacmen
   DisplayTransparentSprite(pacimages(0),t*14+#M_XOFF,#gdsz*#mapheight)
   t = t + 1
  Wend
Return

drawlevel:
  ;draw prize/board number
  For t = 0 To 3
     If board+t-3 >= 0
        If board < 4:xoff = board:Else:xoff = 3:EndIf
        DisplayTransparentSprite(prizeimages(t+board-3),264-(xoff+t)*17+#M_XOFF,#gdsz*#mapheight)
     EndIf
  Next
Return

drawscore:
  If score>=freeman*bonuscount
    PlaySound(soundbonus)
    bonuscount=bonuscount+1
    pacmen=pacmen+1
  EndIf
  If score>999999:score-999999:bonuscount=1:EndIf
  sc=score
  For t=0 To 5
     DisplayTransparentSprite(numberimages(30+sc%10),#gdsz*(13-t)+(5-t)*2+#M_XOFF,#gdsz*#mapheight)
     sc/10
  Next
Return

drawzoom:
  DisplayTransparentSprite(zoomimage,7+#M_XOFF,0)
  StartDrawing(ScreenOutput())
  FrontColor(RGB(255,255,0))
  Box(4+26+#M_XOFF,1,exspeed,4)
  FrontColor(RGB(255,0,0))
  DrawingMode(#PB_2DDrawing_Outlined)
  Box(4+25+#M_XOFF,0,#MAXEXSPEED+2,6)
  StopDrawing()
Return

;.drawzoom
;DrawImage zoomimage,#M_XOFF-4,0
;Color 255,255,0
;Rect #M_XOFF+1-4,26,4,exspeed
;Color 255,0,0
;Rect #M_XOFF-4,25,6,#MAXEXSPEED+2,0
;Return

drawgetready:
  DisplayTransparentSprite(getreadyimage,#gdsz*#cagex-8+#M_XOFF,#gdsz*(#cagey+3))
Return

drawgameover:
  DisplayTransparentSprite(gameoverimage,#gdsz*#cagex-8+#M_XOFF,#gdsz*(#cagey+3))
Return

drawpause:
  For tt = 9 To 0 Step -1
     pausex(tt) = pausex(tt) + driftx(tt)
     pausey(tt) = pausey(tt) + drifty(tt)
     If tt > 0
        diffx.f = pausex(tt-1) - pausex(tt)
        diffy.f = pausey(tt-1) - pausey(tt)
        mag.f = Sqr(diffx*diffx + diffy*diffy)
        If mag > 10
           driftx(tt) = driftx(tt) + diffx/mag*2
           drifty(tt) = drifty(tt) + diffy/mag*2
        EndIf
     Else
        If Random(100) > 80
           diffx.f = pausex(9) - pausex(tt)
           diffy.f = pausey(9) - pausey(tt)
           mag.f = Sqr(diffx*diffx + diffy*diffy)
           If mag > 10
              driftx(tt) = driftx(tt) + diffx/mag
              drifty(tt) = drifty(tt) + diffy/mag
           EndIf
        EndIf
     EndIf
     If pausex(tt) < 0:driftx(tt) = -driftx(tt):pausex(tt) = 2:EndIf
     If pausex(tt) > #gdsz*#mapwidth:driftx(tt) = -driftx(tt):pausex(tt) = #gdsz*#mapwidth-2:EndIf
     If pausey(tt) < #gdsz:drifty(tt) = -drifty(tt):pausey(tt) = #gdsz+2:EndIf
     If pausey(tt) > #gdsz*#mapheight:drifty(tt) = -drifty(tt):pausey(tt) = #gdsz*#mapheight-2:EndIf
 
     If linepause.b
        If tt > 0:Line(pausex(tt)+#M_XOFF,pausey(tt),pausex(tt-1)+#M_XOFF,pausey(tt-1)):EndIf
     Else
        If tt < 6
           DrawImage(pauseimage(tt),pausex(tt)+#M_XOFF,pausey(tt))
        Else   
           fr=tt-6+board-3
           If fr>=0:DisplayTransparentSprite(prizeimages(fr),pausex(tt)+#M_XOFF,pausey(tt)):EndIf
        EndIf
     EndIf
     If Random(100) > 95:driftx(tt) = driftx(tt) + Random(1,-1):EndIf
     If Random(100) > 95:drifty(tt) = drifty(tt) + Random(1,-1):EndIf
     If Abs(driftx(tt)) > 4:driftx(tt) = Sign(driftx(tt))*4:EndIf
     If Abs(drifty(tt)) > 4:drifty(tt) = Sign(drifty(tt))*4:EndIf
  Next
Return

checkcollisions:
  ;check collisons with ghosts
  sx=pac()\sx
  sy=pac()\sy
  ForEach g.ghost()
     Select g()\act
        Case #eyes
           ; do nothing
        Case #edible
           If Abs(sx-g()\sx)<7 And Abs(sy-g()\sy)<7
              ;collision between pac and ghost t
              PlaySound(soundghost)
              If SoundStatus(soundeyes,chsoundeyes)<>#PB_Sound_Playing:StopSound(soundblue,chsoundblue):chsoundeyes=PlaySound(soundeyes):EndIf
              g()\act=#eyes
              killed=killed+1
              bluesleft = bluesleft-1
              If bluesleft = 0:If SoundStatus(soundblue,chsoundblue)=#PB_Sound_Playing:StopSound(soundblue,chsoundblue):chsoundblue=0:EndIf:EndIf
              score=score+200*Pow(2,killed-1)
              AddElement(pts.pointstype())
              pts()\v=#pointtime
              pts()\x=g()\x*#gdsz
              pts()\y=g()\y*#gdsz
              pts()\frm=killed+99
           EndIf
        Case #deadly
           If Abs(sx-g()\sx)<4 And Abs(sy-g()\sy)<4
              ;collision between pac and ghost t
              If #invincible = 0:gmode = #dyingmode:EndIf
           EndIf
     EndSelect
  Next
  ;check collision with prize
  If prize()\cage = 0
     ; check if pac and prize overlap
     ; if so eat prize
     If Abs(sx-prize()\sx)<6 And Abs(sy-prize()\sy)<6
        PlaySound(soundprize)
        score+prizepoints(board)
        prizeseaten = prizeseaten+1
        AddElement(pts.pointstype())
        pts()\v=#pointtime
        pts()\x=prize()\sx
        pts()\y=prize()\sy
        pts()\frm=prizepoints(board)/100-1
        ; move back to cage
        prize()\cage = 1
        prizedir = 8
        prize()\y=#cagey+1
        prize()\x=#cagex
        prize()\sy=prize()\y*#gdsz
        prize()\sx=prize()\x*#gdsz
        exspeed = exspeed + #PRIZEEXSPEED
        If #PRIZEEXSPEED> 0:zoompowerflag = 60:EndIf
        If exspeed > #MAXEXSPEED:exspeed = #MAXEXSPEED:EndIf
     EndIf
  EndIf
Return

gobble:
  x=pac()\cx
  y=pac()\cy
  If gobble=1
     munched=munched+1
     slowdown = 3
     If currentmap(x,y)=53
        ; power pellet
        PlaySound(soundpower)
        score+50
        Gosub turnblue
     ElseIf currentmap(x,y)=52
        ; dot
        PlaySound(sounddot)
        score+10
     EndIf
     currentmap(x,y)=255
  EndIf
  If munched=pillstotal
     gmode = #donemode
  EndIf
Return

boardclear:
  Gosub soundoff
  Delay(300)
  PlaySound(soundboarddone)
  Delay(100)
  spbns=exspeed*10
  score+spbns*10
  For ft=0 To 8
     If Int(ft/2)*2 = ft
        Gosub drawmap
        If spbns > 0
           DisplayTransparentSprite(bonusimage,#gdsz*#cagex-8+#M_XOFF,#gdsz*(#cagey+3))
        Else
           DisplayTransparentSprite(nobonusimage,#gdsz*#cagex-8+#M_XOFF,#gdsz*(#cagey+3))
        EndIf
     Else
        ClearScreen(0)
     EndIf
     Gosub drawpacsleft
     Gosub drawlevel
     Gosub drawzoom
     Gosub drawscore
     FlipBuffers()
     Delay(150)
  Next
Return

death:
  Gosub soundoff
  PlaySound(sounddeath)
  ForEach pts.pointstype()
     DeleteElement(pts(),1)
  Next
  ;animate the death
  For ft = 0 To 3
    pac()\frm = 12+ft
     Gosub drawmap
     Gosub drawpac
     Gosub drawscore
     Gosub drawzoom
     Gosub drawpacsleft
     Gosub drawlevel
     FlipBuffers()
     Delay(300)
  Next
  ;one less pacman
  pacmen-1
  If restorezoom = 1
    exspeed = #MAXEXSPEED
  EndIf
  Gosub drawmap
  Gosub drawscore
  Gosub drawzoom
  Gosub drawpacsleft
  Gosub drawlevel
  FlipBuffers()
  Delay(300)
Return

loadmaps:
  fh.i=OpenFile(#PB_Any,"maps/allmaps.bin")
  For m=0 To #numbrds-1
     For y=0 To #mapheight
        chars$=ReadString(fh,#PB_Ascii)
        For x=0 To #mapwidth
           ch.a=Asc(Mid(chars$,x+1,1))-32
        maps(x,y,m)=ch ; read in all the chars
        Next
     Next
  Next
  CloseFile(fh)
Return

setupmap:
  ; put 255s in the far right and bottom
  ; array pos for the openmap() array
  For x=0 To #mapwidth
     currentmap(x,#mapheight)=255
  Next
  For y=0 To #mapheight
     currentmap(#mapwidth,y)=255
  Next
  ; copy map from the maps()
  For x=0 To #mapwidth-1
     For y=0 To #mapheight-1
        character.a = maps(x,y,board)
        If character.a=52 Or character.a=53
           pillstotal+1
        EndIf
        If character.a=0:character.a=255:EndIf
        currentmap(x,y) = character.a
     Next
  Next
  ;create the mapopen array
  For x=1 To #mapwidth-2
     For y=1 To #mapheight-2
        opu = 0:If currentmap(x,y-1)>51:opu=1:EndIf ; above open
        opd = 0:If currentmap(x,y+1)>51:opd=4:EndIf ; below open
        opl = 0:If currentmap(x-1,y)>51:opl=8:EndIf ; left open
        opr = 0:If currentmap(x+1,y)>51:opr=2:EndIf ; right open
        mapopen(x,y)=opu+opd+opl+opr ; 0,1,2,3,4...15
     Next
  Next
Return

drawmap:
  ClearScreen(0)
  If Random(30)>25:shinv = 1:Else:shinv = 0:EndIf
  ;DrawingMode(#PB_2DDrawing_Outlined)
  ;Box(0,0,320,240)
  ;DrawingMode(#PB_2DDrawing_Default)
  For y = 0 To #mapheight-1
     For x = 0 To #mapwidth-1
        character.a = currentmap(x,y)
        Select character.a
        Case 51
           If shinv = 1:DisplayTransparentSprite(blockimages(2),x*#gdsz+#M_XOFF,y*#gdsz):EndIf
        Case 53
           ; powerpill flashes on/off
           If flashpill = 1
              DisplayTransparentSprite(blockimages(character.a),x*#gdsz+#M_XOFF,y*#gdsz)
           Else
              DisplayTransparentSprite(blockimages(character.a+1),x*#gdsz+#M_XOFF,y*#gdsz)
           EndIf
        Case 255
           ; do nothing
        Default
           DisplayTransparentSprite(blockimages(character.a),x*#gdsz+#M_XOFF,y*#gdsz)
        EndSelect
     Next
  Next
Return

colorcycle:
  col+1
  If col = 9
     col = 0
     Colo=$FFFFFF
  EndIf
  If col = 1
     Colo=RGB(255,0,0)
  EndIf
Return

credits:
  pac()\sx=320:pac()\sy=200
  Createghosts(5)
  ForEach g.ghost()
     g()\sx=320:g()\sy=200:g()\frm=39
  Next
  ClearScreen(0)
  ; grab the ghost colors for printing their names
  For t=0 To 5
    DisplayTransparentSprite(ghostimages(t*8),0,t*16)
    StartDrawing(ScreenOutput())
    getcolor.l=Point(7,t*16+1)
     gkol(t,0)=Red(getcolor)
     gkol(t,1)=Green(getcolor)
     gkol(t,2)=Blue(getcolor)
    StopDrawing()
  Next
  ctmr = 850:If highscore>0:ctmr=600:EndIf
  timer = 0
  resetcmtr=1200
  ExamineKeyboard()
  While KeyboardPushed(#PB_Key_F4)=0 And KeyboardPushed(#PB_Key_Escape)=0  ; f4 (62) to start, ESC (1) to quit
    If windowed And WindowEvent()=#PB_Event_CloseWindow:End:EndIf
    ExamineKeyboard()
    ClearScreen(0)
    DisplayTransparentSprite(mspacimage,106,28)
    StartDrawing(ScreenOutput())
    DrawingFont(FontID(0))
   
    col = timer
    FrontColor(RGB(255,0,0))
    For t = 0 To 18
       Gosub colorcycle
    ;   DrawText(90+t*7,9,".",colo)
       Box(90+t*7,12+9,2,2,colo)
    Next
    For t = 1 To 8
       Gosub colorcycle
    ;   DrawText(216,t*7+8,".",colo)
       Box(216,12+t*7+8,2,2,colo)
    Next
    For t = 18 To 0 Step -1
       Gosub colorcycle
    ;   DrawText(90+t*7,70,".",colo)
       Box(90+t*7,12+70,2,2,colo)
    Next
    For t = 8 To 1 Step -1
       Gosub colorcycle
    ;   DrawText(90,t*7+8,".",colo)
       Box(90,12+t*7+8,2,2,colo)
    Next
    timer=timer+1:If timer > 8:timer = 0:EndIf
 
    ; move g onto screen
    If ctmr < 6
       ForEach g.ghost()
          If g()\id = ctmr
             g()\sx = g()\sx - 2
             g()\frmcnt = g()\frmcnt + 4:If g()\frmcnt >63:g()\frmcnt = 0:EndIf
             g()\frm = g()\id*8 + 2 + g()\frmcnt/32 ; left
             If g()\sx < 90
                g()\sx = 90
                g()\sy = g()\sy - 2
                 g()\frm =  g()\id*8 + 4 + g()\frmcnt/32 ; up
                If g()\sy < 90 + ctmr*16
                     g()\sy = 90+ctmr*16
                   g()\frm =  g()\id*8 + 6 ; down
                   ctmr = ctmr+1
                 EndIf
             EndIf
          EndIf
       Next
    EndIf
   
    If ctmr > 5:ctmr=ctmr+1:EndIf
   
    colo=RGB(240,50,50)
    If ctmr >= 0 And ctmr <600
       DrawText(130,90, "Blinky",RGB(gkol(0,0),gkol(0,1),gkol(0,2)))
    EndIf
    If ctmr >= 1 And ctmr <600
       DrawText(130,106, "Pinky",RGB(gkol(1,0),gkol(1,1),gkol(1,2)))
    EndIf
    If ctmr >= 2 And ctmr <600
       DrawText(130,122, "Inky",RGB(gkol(2,0),gkol(2,1),gkol(2,2)))
    EndIf
    If ctmr >= 3 And ctmr <600
       DrawText(130,138, "Sue",RGB(gkol(3,0),gkol(3,1),gkol(3,2)))
    EndIf
    If ctmr >= 4 And ctmr <600
       DrawText(130,154, "Winky",RGB(gkol(4,0),gkol(4,1),gkol(4,2)))
    EndIf
    If ctmr >= 5 And ctmr <600
       DrawText(130,170, "Clyde",RGB(gkol(5,0),gkol(5,1),gkol(5,2)))
    EndIf
    If ctmr > 198 + 205 And ctmr <600
       DrawText(130,200,"Ms BlitzMan",RGB(255,255,0))
    EndIf
    If ctmr = 198 + 15
       ForEach g.ghost()
          g()\frm = g()\id*8 + 0 ;gstrchar
      Next
    EndIf
    If ctmr = 198 + 100
       ForEach g.ghost()
          g()\frm = g()\id*8 + 6 ;gstdchar
      Next
    EndIf
    If ctmr = 198 + 120
       ForEach g.ghost()
          g()\frm = g()\id*8 + 2 ;gstlchar
      Next
    EndIf
    If ctmr = 198 + 196
       ForEach g.ghost()
          g()\frm = g()\id*8 + 6 ;gstdchar
      Next
    EndIf
     
    If ctmr > 198 And ctmr < 198 + 204
       If ctmr < 198 + 160
          pac()\sx=pac()\sx-2
          pac()\frm=5
       Else
          pac()\sx = pac()\sx+2
          pac()\frm=2
       EndIf
       pac()\frmcnt=pac()\frmcnt+4:If pac()\frmcnt > 63:pac()\frmcnt=0:EndIf
       sc=Int(pac()\frmcnt/16)
       Select sc
          Case 0
             pac()\frm=pac()\frm-1
          Case 1
             pac()\frm=pac()\frm-2
          Case 2
             pac()\frm=pac()\frm-1
          Case 3
             pac()\frm=pac()\frm
       EndSelect
    EndIf
    StopDrawing()
    If ctmr < 600
       ForEach g.ghost()
          If ctmr >= g()\id
             DisplayTransparentSprite(ghostimages(g()\frm),g()\sx,g()\sy)
          EndIf
       Next
    EndIf
    If ctmr < 600 And ctmr > 198:DisplayTransparentSprite(pacimages(pac()\frm),pac()\sx,pac()\sy):EndIf
     
    If ctmr > 600 And ctmr < 850
      If highscore>0
        StartDrawing(ScreenOutput())
        DrawingFont(FontID(0))
        DrawText(85,120,"    High Score     ",RGB(200,200,200))
        StopDrawing()
          skol = Int(Random(3,0))*10 ; random digit color
          score = highscore
          DisplayTransparentSprite(numberimages(skol),180,140) ; 0
          score/10
          DisplayTransparentSprite(numberimages(skol+score1-Int(score1/10)*10),168,140) ; 10s
          score1/10
          DisplayTransparentSprite(numberimages(skol+score1-Int(score1/10)*10),156,140) ; 100s
          score1/10
          DisplayTransparentSprite(numberimages(skol+score1-Int(score1/10)*10),144,140) ; 1 000s
          score1/10
          DisplayTransparentSprite(numberimages(skol+score1-Int(score1/10)*10),132,140) ; 10 000s
          score1/10
          DisplayTransparentSprite(numberimages(skol+score1-Int(score1/10)*10),120,140) ; 100 000s
       Else
          ctmr = 850
       EndIf
    EndIf
    If ctmr < 850
       For key = #PB_Key_F1 To #PB_Key_F5
         ExamineKeyboard()
         If KeyboardPushed(key):ctmr = 850:EndIf
       Next
    EndIf
    If ctmr > 849
      StartDrawing(ScreenOutput())
      DrawingFont(FontID(0))
      DrawText(50,120,"F1: Starting Level - ",RGB(180,240,180))
      StopDrawing()
      DisplayTransparentSprite(prizeimages(startinglevel),238,120)
       StartDrawing(ScreenOutput())
      DrawingFont(FontID(0))
      control$ = "F2: Control Type - "
       If keyorjoy = 0
          control$ = control$ + "Keyboard"
       Else
          control$ = control$ + "Joystick"
       EndIf
       DrawText(50,140, control$,RGB(180,240,180))
       difficulty$ = "F3: Skill Level - "
       Select sklevel
          Case 0
             difficulty$ = difficulty$ + "Easy"
          Case 1
             difficulty$ = difficulty$ + "Normal"
          Case 2
             difficulty$ = difficulty$ + "Medium"
          Case 3
             difficulty$ = difficulty$ + "Hard"
          Case 4
             difficulty$ = difficulty$ + "Hard++"
       EndSelect
       DrawText(50,160, difficulty$,RGB(180,240,180))
       DrawText(50,180, "F4: Start Game",RGB(180,240,180))
       DrawText(50,210, "F5: Help",RGB(180,240,180))
       If KeyboardReleased(#PB_Key_F1):ctmr=850:startinglevel+1:If startinglevel>lastboard:startinglevel=0:EndIf:EndIf
       If KeyboardReleased(#PB_Key_F2):ctmr=850:keyorjoy+1:If keyorjoy>1:keyorjoy=0:EndIf:EndIf
       If KeyboardReleased(#PB_Key_F3)
          ctmr=850
          sklevel = sklevel + 1
          If sklevel > 4:sklevel = 0:EndIf
       EndIf
       If KeyboardReleased(#PB_Key_F5)
         ctmr = 850
          Gosub helpscreen
       EndIf
      StopDrawing()
    EndIf
    If ctmr > resetcmtr
       ctmr = 0
       pac()\sx=320:pac()\sy=200
       ForEach g.ghost()
          g()\sx=320:g()\sy=200:g()\frm=39
       Next
    EndIf
    FlipBuffers()
    ;If KeyboardReleased(#PB_Key_F12) SaveBuffer(FrontBuffer(),"SNAPHOT"+timer+".bmp")
  Wend
  If KeyboardPushed(#PB_Key_Escape):End:EndIf
Return

helpscreen:
  StopDrawing()
  ClearScreen(0)
  FlipBuffers()
  ClearScreen(0)
   StartDrawing(ScreenOutput())
  DrawingFont(FontID(0))
  DrawText(50,5,"     Ms Blitzman Help",RGB(250,20,0))
  DrawText(50,30,  "  Keyboard Controls:",RGB(250,100,0))
  DrawText(50,50, "    Cursor Keys L/R/U/D",RGB(250,200,0))
  DrawText(50,70, "    SPACEBAR for Zoom",RGB(200,250,0))
  DrawText(50,100, "  Joystick Controls:",RGB(100,250,0))
  DrawText(50,120, "        L/R/U/D",RGB(20,250,0))
  DrawText(50,140, "   Fire Button for Zoom",RGB(20,250,100))
  DrawText(50,160, "   ESC to Quit Playing",RGB(20,250,200))
  DrawText(50,180, "Eat Prizes For Zoom Power",RGB(20,200,250))
  DrawText(50,200, "    Hit F5 to Return",RGB(20,100,250))
  StopDrawing()
  FlipBuffers()
  ExamineKeyboard()
  While KeyboardReleased(#PB_Key_F5)=0
    Delay(10):ExamineKeyboard()
  Wend
Return

_________________
http://www.zeitgeistmovie.com

While world=business:world+mafia:Wend


Last edited by Psychophanta on Sun Jan 21, 2018 10:38 pm, edited 1 time in total.

Top
 Profile  
Reply with quote  
 Post subject: Re: Ms BlitzMan translated to PB
PostPosted: Wed Jan 17, 2018 6:38 pm 
Online
Addict
Addict
User avatar

Joined: Sun Nov 05, 2006 11:42 pm
Posts: 4685
Location: Lyon - France
Waooouuuh very nice !!! :shock:
Works fine here with W10 X64 8)
I'm not really a fan of games, but i surprising me several time, to play with your translate of PACMAN old game :lol:
That remember the good time of the first games when i have young and found that a miracle of electronic :shock:
Thanks for sharing this great code 8)

_________________
ImageThe happiness is a road...
Not a destination


Top
 Profile  
Reply with quote  
 Post subject: Re: Ms BlitzMan translated to PB
PostPosted: Wed Jan 17, 2018 8:30 pm 
Offline
Addict
Addict
User avatar

Joined: Wed Jun 11, 2003 9:33 pm
Posts: 4625
Location: Spa, relaxing and thinking, and learning...
Thank you Kwai chang :)

_________________
http://www.zeitgeistmovie.com

While world=business:world+mafia:Wend


Top
 Profile  
Reply with quote  
 Post subject: Re: Ms BlitzMan translated to PB
PostPosted: Thu Jan 18, 2018 12:48 am 
Offline
PureBasic Team
PureBasic Team
User avatar

Joined: Fri Apr 25, 2003 6:14 pm
Posts: 1841
Location: Germany (Saxony, Deutscheinsiedel)
Very nice old-skool game, thank you :mrgreen:

More conversions of old (BlitzBasic) game packages are welcome! 8)

_________________
Bye,
...André
(PureBasicTeam::Docs & Support - PureArea.net | Order:: PureBasic | PureVisionXP)


Top
 Profile  
Reply with quote  
 Post subject: Re: Ms BlitzMan translated to PB
PostPosted: Thu Jan 18, 2018 9:16 am 
Offline
Addict
Addict
User avatar

Joined: Wed Jun 11, 2003 9:33 pm
Posts: 4625
Location: Spa, relaxing and thinking, and learning...
Andre wrote:
Very nice old-skool game, thank you :mrgreen:

More conversions of old (BlitzBasic) game packages are welcome! 8)


Thanks Mr. Andre.
Indeed, to the PB is wellcome the conversions from BlitzBasic, and there are lots of nice works waiting to be converted.
The bad part is there seem not possible to make a software to convert it, not even to make the task easy, I mean, finally, the conversion implicates to get more or less deeply in the code.

Salud!

_________________
http://www.zeitgeistmovie.com

While world=business:world+mafia:Wend


Top
 Profile  
Reply with quote  
 Post subject: Re: Ms BlitzMan translated to PB
PostPosted: Thu Jan 18, 2018 2:06 pm 
Offline
Addict
Addict
User avatar

Joined: Tue Oct 09, 2007 2:15 am
Posts: 1127
Sorry, but it will give me an IMA at line 191 "StartDrawing(ScreenOutput())" and I don't know why.....

I try to compile it with pb5.46 x86,x64 and pb 5.61 x86 and x64... on Win10 Pro x64....

_________________
PureBasic 5.72 LTS (Windows x86/x64) | Windows10 Pro x64 | Z370 Extreme4 | i7 8770k | 32GB RAM | iChill GeForce RTX 2080 Super | HAF XF Evo​​
English is not my native language... (I often use DeepL to translate my texts.)


Top
 Profile  
Reply with quote  
 Post subject: Re: Ms BlitzMan translated to PB
PostPosted: Thu Jan 18, 2018 6:22 pm 
Offline
Enthusiast
Enthusiast
User avatar

Joined: Mon May 09, 2011 9:36 am
Posts: 507
Bisonte wrote:
Sorry, but it will give me an IMA at line 191 "StartDrawing(ScreenOutput())" and I don't know why.....

I try to compile it with pb5.46 x86,x64 and pb 5.61 x86 and x64... on Win10 Pro x64....


i get the very same ERROR
using those same PB versions
but on Win-7 64-bit Computer using PB x86 versions

_________________
 
PureBasic .... making tiny electrons do what you want !

"With every mistake we must surely be learning" - George Harrison


Top
 Profile  
Reply with quote  
 Post subject: Re: Ms BlitzMan translated to PB
PostPosted: Thu Jan 18, 2018 7:09 pm 
Offline
Addict
Addict
User avatar

Joined: Fri May 12, 2006 6:51 pm
Posts: 2535
Location: Germany
320x240 not supported ?

How to find sounds and images?

_________________
My Projects ThreadToGUI / OOP-BaseClass / OOP-BaseClassDispatch / EventDesigner V3
PB v3.30 / v5.70 - OS Mac Mini OSX 10.xx - VM Window Pro / Linux Ubuntu
Downloads on my Webspace


Top
 Profile  
Reply with quote  
 Post subject: Re: Ms BlitzMan translated to PB
PostPosted: Thu Jan 18, 2018 7:28 pm 
Offline
Addict
Addict
User avatar

Joined: Tue Oct 09, 2007 2:15 am
Posts: 1127
Not supported ScreenSize ;) You are right. The next Problem are the loaded images... and now I see I have to download the original ;)

_________________
PureBasic 5.72 LTS (Windows x86/x64) | Windows10 Pro x64 | Z370 Extreme4 | i7 8770k | 32GB RAM | iChill GeForce RTX 2080 Super | HAF XF Evo​​
English is not my native language... (I often use DeepL to translate my texts.)


Top
 Profile  
Reply with quote  
 Post subject: Re: Ms BlitzMan translated to PB
PostPosted: Sun Jan 21, 2018 10:40 pm 
Offline
Addict
Addict
User avatar

Joined: Wed Jun 11, 2003 9:33 pm
Posts: 4625
Location: Spa, relaxing and thinking, and learning...
Yes, the problem is modern VGAs, with lacks about some resolutions, and 16 bit depth (which is the screen depth in the original Blitz code).

Edited the first post to fix code for pause the game pushing "P" key.

_________________
http://www.zeitgeistmovie.com

While world=business:world+mafia:Wend


Top
 Profile  
Reply with quote  
 Post subject: Re: Ms BlitzMan translated to PB
PostPosted: Mon Jan 22, 2018 12:16 am 
Offline
Enthusiast
Enthusiast

Joined: Mon Apr 10, 2017 6:17 pm
Posts: 350
Location: Germany
I just checked on my system with an nvidia card on windows. The nvidia sytemcontrol lists the gfx modes and allows to change them. The lowest resolution is 800x600, but i have the option to create and enable custom resolutions including 16bit ones and lowresolutions. I guess you could create a custom setting but then the monitor support will be the next big problem. Its also rather impractical to ask users to do all this themselves just to execute some game which otherwise simply fails with "cant switch to 320x240 16-bit videomode".

But luckily todays computers are fast enough to upscale video graphics in realtime, so i suggest three solutions.
a) find the best supported video resolution with the same aspect ratio, switch to the resolution and scale a virtual 320x240 buffer up to display it
b) show it in a window in original resolution (beware, this will be laughable tiny, so you better offer the option to show x2, x4, x8 versions
c) do B) but with a window where the border and top line is hidden and its displayed at a negative offset covering the full screen, basically it will act like a fullscreen to the user (i think some other games call this a fullscreen window mode)

All three solutions will make the game appear like the original 320x240 arcade screen without giving the user trouble with video mode hacking or resolution/monitor problems. So it will be super easy to run the game which means you have more fans/users and basically you need such a solution for ancient resolutions anyway :)

Also you better convert the 16-bit colormode display to a 32bit RGBA - but this can be done during the postprocessing/upscaling of the 320x240 framebuffer.

_________________
webpage


Top
 Profile  
Reply with quote  
 Post subject: Re: Ms BlitzMan translated to PB
PostPosted: Mon Jan 22, 2018 9:46 am 
Offline
Addict
Addict
User avatar

Joined: Wed Jun 11, 2003 9:33 pm
Posts: 4625
Location: Spa, relaxing and thinking, and learning...
Thank you for your advise Bitblazer.
I really want to translate more BlitzBasic programs to PureBasic, and I am making some tools to make easier these tasks. Not enough time is the omnipresent obstacle, but I will try.
So, thanks again for your careful observation.

_________________
http://www.zeitgeistmovie.com

While world=business:world+mafia:Wend


Top
 Profile  
Reply with quote  
 Post subject: Re: Ms BlitzMan translated to PB
PostPosted: Mon Feb 26, 2018 10:59 pm 
Offline
User
User
User avatar

Joined: Mon Feb 26, 2018 10:41 pm
Posts: 91
Location: Netherlands
Hey.

Its nicly done. I like it.
I am a former PBlitz3D user. Did do a lot in blitz. An d currently buzu is a big project of reprogramming a old AMIGA game to PC. Using the Blitz3D for it. This project takes alreadt up 3 years. A lot of graphics and sound ripping.
The sound has to cleaned up to be for good use. The graphics is on a very low pixel mode. All the graphics i had to upsized time 2. And that was a lot of hand working. Cause Blitz3D did do the job not correctly.
Anyway beside the poind. The screen resolution is on my computer no problem i use a MSI win 10 16GB mem and 4 TB SSD (Got it in china). The whole program is working like a charm. The 16 bits mode is a problem on the newer computers. Itys not that the screen can't handle. Its the drivers that not willing. When upgrade to 32 bits its ok. Today computers can handle this. I had a computer that works on win 8.1 64 bits. And it hase the same problem, could not handle 16 bits. Then i search the internet and found some pretty old drivers for that computer. Removed the new drivers and install the old drivers. And what you think. The 16 bits mode was no problem anymore.
Testing in game speed using the 16 and the 32 mode. I could not find any differend is speed, but in Blitz3D there was a frame lost of 2 FPS from 35 to 33. This is stil good there a frame rate or 30 is the bare minimum to get good animation on screen.

Keep working and do please recode a lot of Blitz3D files to PD.

N.B. I am starting from today a new PB user.

_________________
From my first self made computer till now I stil like computers.


Top
 Profile  
Reply with quote  
Display posts from previous:  Sort by  
Post new topic Reply to topic  [ 13 posts ] 

All times are UTC + 1 hour


Who is online

Users browsing this forum: No registered users and 9 guests


You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum

Search for:
Jump to:  

 


Powered by phpBB © 2008 phpBB Group
subSilver+ theme by Canver Software, sponsor Sanal Modifiye