Seite 2 von 4

Re: SpritePixelCollision?

Verfasst: 28.12.2012 19:06
von HeX0R
Mach einfach mal den Debugger an, er sagt Dir dann was falsch ist.

Re: SpritePixelCollision?

Verfasst: 28.12.2012 19:42
von jojo1541
Du willst in deiner Kollisionsabfrage die Araystelle 501 abfragen. Dein Array ist allerdings in dieser Dimension nur bis 90 definiert.

Der Rest sollte kein Problem sein. :wink:

Re: SpritePixelCollision?

Verfasst: 29.12.2012 16:23
von TheNewOne
Ah stimmt ja. :lol:

Re: SpritePixelCollision?

Verfasst: 01.01.2013 19:41
von TheNewOne
Habe meinen Code nun überarbeitet, und bin nun auf ein kleines Problem gestoßen. Egal was ich probiere der "Spieler" kollidiert nicht richtig. Man kann teilweise durch den Halben Block durch.

Code: Alles auswählen

;----------- Variablen ---------------;
Global ende.i = 0                    ; Beendet das Spiel
Global pX.i = Random(1600)            ; X-Position des Spielers
Global pY.i = Random(200)             ; Y-Position des Spielers
Global fg.i                          ; Schwerkraft
Global hoehe.i
Global richtung.i                    ; besagt ob bei der nächsten X-Koordinate der Block höher oder tiefer liegt
Global nHoehe.i                      ; die Höhe der nächsten X-Koordinate

;----------- Structuren --------------;

Structure BlockEigenschaften
  id.i                                ; 0 für Luft, 1 für Erde
  maxHoehe.i                          ; Höchster Block (0 für Nein, 1 für Ja)
EndStructure

;----------- Arrays ------------------;

Global Dim Block.BlockEigenschaften(90,45)

;--------- Generate World ------------;

Procedure Generate()
  
  hoehe = Random(20) + 20
  
  For x = 0 To 90
    
    richtung = Random(1)
    nHoehe = Random(2)
    
    If richtung = 0
      nHoehe * -1
    EndIf
    
    hoehe + nHoehe                          ; nächste Hoehe festegelgt
    
    If hoehe < 0
      hoehe = 0
    ElseIf hoehe > 45
      hoehe = 45
    EndIf
    
    For y = 45 To hoehe Step -1            ; Block = Erde
      Block(x,y)\id = 1
      Block(x,y)\maxHoehe = 0
      If m = hoehe                          ; Höhe der X-Koordinate
        Block(n,m)\maxHoehe = 1
      EndIf
    Next
    
    For y = hoehe To 0 Step -1             ; Block = Luft
      Block(x,y)\id = 0
    Next
  Next
  
EndProcedure  

;---------- Draw ---------------------;

Procedure CreateSprites()
  
  CreateSprite(0, 20, 20)            ; Spieler erstellen
  StartDrawing(SpriteOutput(0))
  Circle(10, 10, 10, RGB(225, 255,0))
  StopDrawing()
  
  CreateSprite(1, 20, 20)              ; Erde erstellen
  StartDrawing(SpriteOutput(1))
  Box(0, 0, 20, 20, RGB(0, 150, 0))
  StopDrawing()
  
EndProcedure

Procedure DrawSprites()
  
  For x = 0 To 90
    For y = 0 To 45    
      If Block(x,y)\id = 1
        DisplaySprite(1,x*20,y*20) 
      EndIf
    Next
  Next
  
  DisplayTransparentSprite(0, pX, pY)
  TransparentSpriteColor(0,0)
  
EndProcedure

;---------- Movement -----------------;

Procedure MovePlayer()
  
  ExamineKeyboard()
  
  If Block(px/20,(py+20)/20)\maxHoehe = 0
    pY + fg                                ; Schwerkraft
  EndIf
  
  If Block(pX/20,(pY+20)/20)\id = 0
    fg + 1
  ElseIf Block(pX/20,(pY+20)/20)\id = 1
    fg = 0
  EndIf

  
  If KeyboardReleased(#PB_Key_Escape)    ; Beenden
    ende = #True
  EndIf
  
  If KeyboardPushed(#PB_Key_W)           ; Hüpfen
    fg = -5
  EndIf
  
  If KeyboardPushed(#PB_Key_A)           ; Links
    If Block(px/20, (py)/20)\id  = 0 Or Block(px/20, (py+20)/20)\id = 0
      pX - 5
    EndIf
  EndIf
  
  If KeyboardPushed(#PB_Key_D)           ; Rechts
    If Block((px+20)/20, py/20)\id = 0 Or Block((px+20)/20, (py+20)/20)
      pX + 5
    EndIf
  EndIf
  
EndProcedure

;---------- Screen öffnen ------------;

InitSprite()
InitKeyboard()
OpenScreen(1600, 900, 32, "FullScreen")

Generate()
CreateSprites()

Repeat
  ClearScreen(RGB(0,0,0))
  ExamineKeyboard()
  MovePlayer()
  DrawSprites()
  FlipBuffers()
Until ende = #True

Re: SpritePixelCollision?

Verfasst: 01.01.2013 23:34
von man-in-black
If KeyboardPushed(#PB_Key_D) ; Rechts
If Block((px+20)/20, py/20)\id = 0 Or Block((px+20)/20, (py+20)/20)
pX + 5
EndIf
EndIf
da fehlt ein "\id = 0" :mrgreen:

Re: SpritePixelCollision?

Verfasst: 02.01.2013 01:20
von jojo1541
Ach ja, das Problem kenn ich. :lol:

Da müsstest du aber leider wen anders fragen, da ich mich mit diesem Problem bis jetzt noch nie richtig beschäftigt habe.

Re: SpritePixelCollision?

Verfasst: 02.01.2013 16:39
von TheNewOne
Hmm, kann es sein dass ich hier:

Code: Alles auswählen

 If Block(px/20, (py)/20)\id  = 0 Or Block(px/20, (py+20)/20)\id = 0
für jeden einzelnen Punkt des "Spielers" die id abfragen muss? Also py+1,py+2 usw. ?

Re: SpritePixelCollision?

Verfasst: 02.01.2013 20:09
von man-in-black
1. Mir ist aufgefallen, dass du "TransparentSpriteColor(0,0)" in der Repeat schleife stehen hast (durch die Procedure DrawSprites()). Den Befehl brauchst aber eigt nur einmal aufrufen, weil du das Sprite damit nachhaltig modifizierst.

2. Du brauchst nur die Boxen links und rechts neben der Box, auf der du aktuell bist, abfragen. Die Aktuelle zu prüfen is unnötig, da man davon ausgehen kann, dass der Spieler durch einen geprüften Schritt dorthin gekommen ist.

Code: Alles auswählen

;für links:
if px=>20   ;ganz wichtig, da du sonst das Array überfordern könntest ;)
  spieler_raster_x = Round(px/20,1)-1        ;geht auch, wenn du das Round weg lässt. Wollte es nur sauber schreiben.
  spieler_raster_y = (py)/20
  If Block(spieler_raster_x, spieler_raster_y)\id  = 0 
...

;für rechts:
if px< "___Anzahl_Boxen____"-20
  spieler_raster_x = Round(px/20,1)+1
  spieler_raster_y = (py)/20
  If Block(spieler_raster_x, spieler_raster_y)\id  = 0 
...
Wenn deine Schritte weiterhin deutlich unter der Blockbreite bleiben, reicht es, nur eine Box neben dem Spieler zu überprüfen. Man kann dann nämlich davon ausgehen, dass du niemals ausversehen eine Box "tunneln" und dadurch einen Bug erzeugen wirst.

Re: SpritePixelCollision?

Verfasst: 09.01.2013 18:52
von TheNewOne
Danke euch zwei erst mal für die geduldigen Antworten :lol: .
Ich habe nur noch ein Problem, dass ich einfach nicht zu beheben schaffe:
Die Kollision vom "Spieler" und dem Boden. Egal was ich rumprobiere, ich schaffe es nicht dass der "Spieler" sauber AUF den Blöcken landet, und beim hin- und herbewegen nicht andauernd durch halbe Blöcke rutscht /:-> .
Bitte um Hilfe :(

Re: SpritePixelCollision?

Verfasst: 09.01.2013 22:58
von jojo1541
Füg mal ein

Code: Alles auswählen

pY = py/20 * 20
nach

Code: Alles auswählen

 ElseIf Block(pX/20,(pY+20)/20)\id = 1
    fg = 0
ein.

Das gleiche für pX.

Code: Alles auswählen

 If KeyboardPushed(#PB_Key_A)           ; Links
    If Block((px - 5)/20, (py)/20)\id  = 0
      pX - 5
    Else
      pX = pX/20 * 20
    EndIf
  EndIf
 
  If KeyboardPushed(#PB_Key_D)           ; Rechts
    If Block((px+20)/20, py/20)\id = 0
      pX + 5
    Else
      pX = pX/20 * 20
    EndIf
  EndIf
Wichtig ist hier das pX - 5 in der Abfrage, damit du auch wirklich die Arraystelle links von dir abfragst.

Ich weiß nicht, ob es ideal ist, aber es sollte (zumindest bei den Symptomen) helfen.