Wie erkenne ich bei Kollisionen Mauern o.ä. hinter einer verschiebbaren Box?

  • GM 7

Diese Seite verwendet Cookies. Durch die Nutzung unserer Seite erklären Sie sich damit einverstanden, dass wir Cookies setzen. Weitere Informationen

  • Wie erkenne ich bei Kollisionen Mauern o.ä. hinter einer verschiebbaren Box?

    Hallo,

    ich möchte einen Sokoban-Klon programmieren. Es handelt sich um ein Remake eines alten C64-Spiels aus der Magic Disk 64 (falls die noch jemand kennt).

    Die Grafiken habe ich fertig, die Bewegungen der Spielerfigur funktionieren auch. Selbst die Bewegung der "Kiste" (hier ist es ein Herz) klappt inzwischen ganz gut. Bis auf einen Umstand: Sobald ich die Kiste an der Wand habe und nochmal drücke, bewegt sich die Spielerfigur noch ein paar Pixel und steckt dann in der Kiste fest. :-/ Hat da jemand einen Tipp, was ich machen muß?

    Ich habe mal ein kleines Beispiel angehängt, welches das Problem sicherlich veranschaulicht.

    Wäre super, wenn mir jemand helfen könnte.

    Gruß,
    Terrance

    shift_test.zip
  • Füg bei der colllision mit dem Herz von folgende Abfrage ein:

    GML-Quellcode

    1. if place_free(x+lengthdir_x(4,objPlayer.direction),y+lengthdir_y(4,objPlayer.direction))

    und am besten gibst du den beiden Objekten noch quadratische Masks.
  • Meine Empfehlung wäre, allen Objekten, mit denen eine Kollision geprüft werden soll, ein Parent zuzuweisen (z.B. "par_collision") und dann in deine Bewegungsaktionen mittels !place_meeting(x,y,par_collision) zu überprüfen, ob sich an den entsprechenden Positionen solche Objekte befinden.

    Wenn du dich zum Beispiel nach rechts bewegen willst:

    GML-Quellcode

    1. if !place_meeting (x+4,y,par_collision){
    2. direction=0;
    3. speed=4;
    4. }
  • Beides scheint leider nicht zu funktionieren. Der Fehler bleibt (fast) der gleiche. Solange ich für jeden Schritt die jeweilige Bewegungstaste extra drücke, funktioniert es. Halte ich aber die Taste gedrückt, bewegt sich entweder mein Herz immer weiter, oder der Player bleibt wieder im Herz hängen.

    So langsam glaube ich, dass mein Ansatz einfach falsch ist. :headtouch:
  • Bewegliche Objekte sollten niemals solid sein.
    Hier ein einfaches Beispiel mit 3 Objekten:

    obj_wall:
    - ist solid

    obj_player:
    - nicht solid
    - Step Event:

    GML-Quellcode

    1. move=false;
    2. speed=0;
    3. if (keyboard_check(vk_right))
    4. {
    5. direction=0;
    6. move=true;
    7. }
    8. if (keyboard_check(vk_up))
    9. {
    10. direction=90;
    11. move=true;
    12. }
    13. if (keyboard_check(vk_left))
    14. {
    15. direction=180;
    16. move=true;
    17. }
    18. if (keyboard_check(vk_down))
    19. {
    20. direction=270;
    21. move=true;
    22. }
    23. if (move==true)
    24. {
    25. speed=5;
    26. if (place_meeting(x+hspeed,y+vspeed,obj_wall))
    27. {
    28. speed=0;
    29. move_contact_solid(direction,speed);
    30. }
    31. }
    Alles anzeigen


    obj_box:
    - nicht solid
    - Collision Event mit obj_player:

    GML-Quellcode

    1. if (place_empty(x+other.hspeed,y+other.vspeed))
    2. {
    3. x+=other.hspeed;
    4. y+=other.vspeed;
    5. }
    6. else
    7. {
    8. other.x=other.xprevious;
    9. other.y=other.yprevious;
    10. move_contact_all(other.direction,other.speed);
    11. with(other) move_contact_all(direction,speed);
    12. }
    Alles anzeigen
    Einige meiner Spiele:
  • Ah, super. Das funktioniert! Vielen, vielen Dank!

    Eine Frage habe ich aber noch: Kannst du mir noch verraten, wie ich das mache, dass pro Bewegung der Player immer eine bestimmte Anzahl von Schritten geht? Sokoban ist ja ein grid-basiertes Spiel.

    Trotzdem schonmal vielen Dank, das Skript hilft mir ein ganzes Stück weiter.