Collosions-Abfrage Fehler?

Anfängerfragen zum Programmieren mit PureBasic.
Benutzeravatar
Milchshake
Beiträge: 166
Registriert: 30.01.2006 17:47
Wohnort: Zwischen dem Sessel und dem Computer

Collosions-Abfrage Fehler?

Beitrag von Milchshake »

Hi,
ich versuche mich gerade an einem Jump-and-Run Game...
Da ich von Anfang an gewusst habe, dass das nicht leicht wird, habe ich
den Code in einzelne Teile zerlegt. Bisher wunderbar geklappt^^

Aber jetzt:
In diesem Teil von dem Game habe ich das Problem, wenn der
Platzhalter das erste Mal hinunterfliegt, ist alles ok...
doch beim zweiten Mal, also wenn man von der Plattform hinuntergeht,
dann steigt die PlayerY rapide an, d.h dass der Spieler hinnunterfällt.

Also hier mal der Code:

Code: Alles auswählen

InitSprite()
InitKeyboard()
InitSound()
InitMouse()

OpenScreen(1024,768,32,"Engine-Testing")

Structure Show
  x.w
  y.w
  Width.w
  Height.w
  Image.w
  SpeedX.w
  SpeedY.w
  Durchgehbar.w
EndStructure
Global NewList Show.Show()
Procedure AddShow(Sprite, x, y, SpeedX, SpeedY,Durchgehbar) 
  AddElement(Show())           
  Show()\x      = x
  Show()\y      = y
  Show()\Width  = SpriteWidth(Sprite)
  Show()\Height = SpriteHeight(Sprite)
  Show()\Image  = Sprite
  Show()\SpeedX = SpeedX
  Show()\SpeedY = SpeedY
  Show()\Durchgehbar = Durchgehbar
  
EndProcedure


CreateSprite(0,40,40)
 StartDrawing(SpriteOutput(0))       ;PLATZHALTE
 Box(0,0,40,40,#White)
 StopDrawing()

CreateSprite(5,1,40)              ;COLLISIONSABFRAGE1
 StartDrawing(SpriteOutput(5))
 Box(0,0,1,40,#Green)
 StopDrawing()
 
 CreateSprite(6,40,1)
 StartDrawing(SpriteOutput(6))    ;COLLISIONSABFRAGE2
 Box(0,0,40,1,#Green)
 StopDrawing()
 
   ; Image 1 (Testimage)
   CreateSprite(1,100,20)
    StartDrawing(SpriteOutput(1))
     Box(0,0,100,20,#Green)
    StopDrawing()
    
    
PlayerY = 200
PlayerX = 500
Gravity = 2
Repeat 
ExamineKeyboard()
ExamineMouse()
FlipBuffers()
ClearScreen(0)
If Loading = 0
AddShow(1,500,500,0,0,1)
EndIf 

DisplayTransparentSprite(0,PlayerX,PlayerY)  ;PLAYER-PLATZHALTEr
DisplayTransparentSprite(5,PlayerX-1,PlayerY) ;LINKS_COLLISIONSABFRAGE
DisplayTransparentSprite(5,PlayerX+41,PlayerY);RECHTS_COLLISIONSABFRAGE
DisplayTransparentSprite(6,PlayerX,PlayerY-1) ;OBEN_COLLISIONSABFRAGE
DisplayTransparentSprite(6,PlayerX,PlayerY+41);UNTEN_COLLISIONSABFRAGE

;SHOWING_SPRITES_EDITOR--------------

ResetList(Show())
While NextElement(Show())
;LÖSCHEN------------------------------

   
 If SpritePixelCollision(Show()\Image,Show()\x,Show()\y,0,MouseX(),MouseY()) And MouseButton(2)
      DeleteElement(Show())
     EndIf
;DARSTELLUNG--------------------------
  
  DisplayTransparentSprite(Show()\Image, Show()\x, Show()\y)   
  Show()\y + Show()\SpeedY
  Show()\x + Show()\SpeedX 
Wend

;------------------------------------

;COLLISION________________________---
 ResetList(Show())
    While NextElement(Show())
    
      If SpritePixelCollision(Show()\Image, Show()\x, Show()\y,6,PlayerX,PlayerY+41) = 0 ;AND JUMPING = 0 <- WICHTIG SONST DIE GANZE ZEIT MINUS (ODER EINFACH JUMPING_POWER ERHÖHEN
       Gravity = 2
       PlayerY + Gravity
       
      EndIf
        If SpritePixelCollision(Show()\Image, Show()\x, Show()\y,6,PlayerX,PlayerY+41) = 1 ;AND JUMPING = 0 <- WICHTIG SONST DIE GANZE ZEIT MINUS (ODER EINFACH JUMPING_POWER ERHÖHEN
        Gravity = 0
      EndIf
  
    Wend
    
    StartDrawing(ScreenOutput())
     DrawingMode(1)
     DrawText(0,0,"Gravity: " + Str(Gravity),#White)
     DrawText(0,15,"PlayerY: " + Str(PlayerY),#White)
     StopDrawing()
    
    
;FORTBEWEGUNG
If KeyboardPushed(#PB_Key_Left)
PlayerX - 2
EndIf

If KeyboardPushed(#PB_Key_Right) 
PlayerX + 2
EndIf

Until KeyboardPushed(#PB_Key_Escape)
Wie schaffe ich es, dass der Spieler langsamer fällt, nachdem er von der ersten Plattform hinunter fällt?

lg Milchshake
Hab jetzt PB 4.02
Muhahaha!!!!
Benutzeravatar
Max_der_Held
Beiträge: 595
Registriert: 18.04.2006 17:01
Wohnort: Bavaria
Kontaktdaten:

Beitrag von Max_der_Held »

ok :9

fehler (falls des nicht irgendein ausgefallener Trick is :P )

liegt bei der Kollisionsabfrage:

Code: Alles auswählen

;COLLISION________________________---
 ResetList(Show())
    While NextElement(Show())
   
      If SpritePixelCollision(Show()\Image, Show()\x, Show()\y,6,PlayerX,PlayerY+41) = 0 ;AND JUMPING = 0 <- WICHTIG SONST DIE GANZE ZEIT MINUS (ODER EINFACH JUMPING_POWER ERHÖHEN
       
       fallen = 1
       
      EndIf 
        If SpritePixelCollision(Show()\Image, Show()\x, Show()\y,6,PlayerX,PlayerY+41) = 1 ;AND JUMPING = 0 <- WICHTIG SONST DIE GANZE ZEIT MINUS (ODER EINFACH JUMPING_POWER ERHÖHEN
        Gravity = 0
      EndIf
 
    Wend
     
     If fallen = 1
       fallen  = 0
       Gravity = 2
       PlayerY + Gravity
     EndIf 
so Musses Heißen :)

sonst fliegt er für jedes SHOW- element nochmal um 2 weiter runter, und des kann fast net gewollt sein :)

ps: endlich mal was, wo ich ne sinnfolle antwort geben kann lol

viel spaß weiterhin,

dein max.
Benutzeravatar
Milchshake
Beiträge: 166
Registriert: 30.01.2006 17:47
Wohnort: Zwischen dem Sessel und dem Computer

Beitrag von Milchshake »

Ok, bis dahin hat es ganz gut geklappt, aber ich habe jetzt folgendes Problem.
Also, hier noch mal der Code:

Code: Alles auswählen

InitSprite()
InitKeyboard()
InitSound()
InitMouse()

OpenScreen(1024,768,32,"Engine-Testing")

Structure Show
  x.w
  y.w
  Width.w
  Height.w
  Image.w
  SpeedX.w
  SpeedY.w
  Durchgehbar.w
EndStructure
Global NewList Show.Show()
Procedure AddShow(Sprite, x, y, SpeedX, SpeedY,Durchgehbar) 
  AddElement(Show())           
  Show()\x      = x
  Show()\y      = y
  Show()\Width  = SpriteWidth(Sprite)
  Show()\Height = SpriteHeight(Sprite)
  Show()\Image  = Sprite
  Show()\SpeedX = SpeedX
  Show()\SpeedY = SpeedY
  Show()\Durchgehbar = Durchgehbar
  
EndProcedure


CreateSprite(0,40,40)
 StartDrawing(SpriteOutput(0))       ;PLATZHALTE
 Box(0,0,40,40,#White)
 StopDrawing()

CreateSprite(5,1,40)              ;COLLISIONSABFRAGE1
 StartDrawing(SpriteOutput(5))
 Box(0,0,1,40,#Green)
 StopDrawing()
 
 CreateSprite(6,40,1)
 StartDrawing(SpriteOutput(6))    ;COLLISIONSABFRAGE2
 Box(0,0,40,1,#Green)
 StopDrawing()
 
   ; Image 1 (Testimage)
   CreateSprite(1,100,20)
    StartDrawing(SpriteOutput(1))
     Box(0,0,100,20,#Green)
    StopDrawing()
    
    
PlayerY = 200
PlayerX = 500
Gravity = 2
Repeat 
ExamineKeyboard()
ExamineMouse()
FlipBuffers()
ClearScreen(0)
If Loading = 0
AddShow(1,500,500,0,0,1)   ;<- keine Collision
AddShow(1,600,520,0,0,1)   ;<- Collision funktioniert
Loading = 1
EndIf 

DisplayTransparentSprite(0,PlayerX,PlayerY)  ;PLAYER-PLATZHALTEr
DisplayTransparentSprite(5,PlayerX-1,PlayerY) ;LINKS_COLLISIONSABFRAGE
DisplayTransparentSprite(5,PlayerX+41,PlayerY);RECHTS_COLLISIONSABFRAGE
DisplayTransparentSprite(6,PlayerX,PlayerY-1) ;OBEN_COLLISIONSABFRAGE
DisplayTransparentSprite(6,PlayerX,PlayerY+41);UNTEN_COLLISIONSABFRAGE
Gosub Adding
Gosub Colli

    
    StartDrawing(ScreenOutput())
     DrawingMode(1)
     DrawText(0,0,"Gravity: " + Str(Gravity),#White)
     DrawText(0,15,"PlayerY: " + Str(PlayerY),#White)
     DrawText(0,30,"List-Elemente: " + Str(CountList(Show())),#White)
     StopDrawing()
    
    
;FORTBEWEGUNG
If KeyboardPushed(#PB_Key_Left)
PlayerX - 2
EndIf

If KeyboardPushed(#PB_Key_Right) 
PlayerX + 2
EndIf

Until KeyboardPushed(#PB_Key_Escape)
End 



Adding:

ResetList(Show())
While NextElement(Show())

;DARSTELLUNG--------------------------
 
  DisplayTransparentSprite(Show()\Image, Show()\x, Show()\y)   ; Display the bullet


Wend


Return 

Colli: 
    ResetList(Show())
    While NextElement(Show())
     If Show()\Durchgehbar = 1
      If SpritePixelCollision(Show()\Image, Show()\x, Show()\y,6,PlayerX,PlayerY+41) = 0
        fallen = 1
        
      EndIf
         If SpritePixelCollision(Show()\Image, Show()\x, Show()\y,6,PlayerX,PlayerY+41) = 1
        fallen = 0
        
      EndIf
      EndIf 
  
    Wend
     
     If fallen = 1
       
       PlayerY + Gravity
       
     EndIf
Return 
Das Problem ist, das nur das zweite Element, als Collisionsobjekt anerkannt wird. Ich glaube das liegt daran, das dieses Element das aktuelle ist. (Kann auch sein das ich falsch liege)
Schon im Vorraus danke für die Hilfe ;)
lg Milchshake
Hab jetzt PB 4.02
Muhahaha!!!!
Benutzeravatar
Max_der_Held
Beiträge: 595
Registriert: 18.04.2006 17:01
Wohnort: Bavaria
Kontaktdaten:

Beitrag von Max_der_Held »

ok :D
und wieder liegts an der Kollision ( wie nicht anders zu erwarten, wenn er doch das aufprallen nicht erkennt..)
  • der (denk) fehler war, dass:

    wenn er auf platte 0 trifft:
    fallen =0
    ok
    schauen, ob er auf platte 1 trifft (weil WHile-wend- schleife, bis alle platten überprüft)
    fallen = 1 ( auch, wenns vorher zur null gemacht wurde..
    ok
    .

    => wenn er nicht auf platte 1 fällt, wird er nicht gehalten :P


    .. evtl solltest auch 'n bisschen auf lesbarkeit/übersichtlichkeit schauen, z.b. mit ;{ ;} , und so :P

    hier die überarbeitete collision (war ziemlich knifflig :) )

Code: Alles auswählen

Colli:

   ;{ Collision..

       ResetList(Show())
    
       While NextElement(Show())
    
         If Show()\Durchgehbar = 1
     
               If SpritePixelCollision(Show()\Image, Show()\x, Show()\y,6,PlayerX,PlayerY+41) = 0
        
                  fallen = 1
       
               Else 
      
                 fallen = 0
                 Break    ; aus der schleife brechen, damit nicht der Nächste bodenblock das fallen auslöst :-)
              
               EndIf
         
         EndIf
 
       Wend
    
    
        ; runterfallen..
           
        If fallen = 1
       
             PlayerY + Gravity
          
        EndIf
     
    ;}
 
Return 
Antworten