From a7d1adf175ae58b9a28c0b29aaf4bc603655e2c0 Mon Sep 17 00:00:00 2001 From: Marro64 Date: Wed, 17 Jun 2026 14:12:36 +0200 Subject: [PATCH] Ghost - PacMan collision detection --- Assets/Scripts/GameManager.cs | 10 +- Assets/Scripts/Ghost.cs | 40 +-- Assets/Scripts/PacMan.cs | 6 +- Assets/Scripts/PelletManager.asset | 314 +++++++++++++----- Assets/Scripts/PelletManager.cs | 57 +++- .../Sequences/AttractScreenIntroduction.cs | 2 +- 6 files changed, 302 insertions(+), 127 deletions(-) diff --git a/Assets/Scripts/GameManager.cs b/Assets/Scripts/GameManager.cs index b09126c..600c0d6 100644 --- a/Assets/Scripts/GameManager.cs +++ b/Assets/Scripts/GameManager.cs @@ -61,7 +61,7 @@ namespace Marro.PacManUdon ghostManager.Initialize(maze.ghostStarts, maze.ghostTargets, pacMan, pelletManager, this); pacMan.Initialize(playerInput, maze.pacManStart, this, pelletManager); bonusFruit.Initialize(); - pelletManager.Initialize(this, bonusFruit); + pelletManager.Initialize(this, bonusFruit, ghostManager.Ghosts); statusDisplay.Initialize(); playerInput.Initialize(this); soundManager.Initialize(); @@ -163,9 +163,9 @@ namespace Marro.PacManUdon SetFrozen(true); } - internal void GotPellet(Pellet pellet, PelletType pelletType, int pelletsCollectedCount, int pelletsRemainingCount) + internal void GotPellet(Pellet pellet, bool isPowerPellet, int pelletsCollectedCount, int pelletsRemainingCount) { - AddScore(pelletType == PelletType.PowerPellet ? 50 : 10); + AddScore(isPowerPellet ? 50 : 10); ghostManager.PelletConsumed(pelletsRemainingCount); @@ -178,7 +178,7 @@ namespace Marro.PacManUdon return; } - if (pelletType == PelletType.PowerPellet) + if (isPowerPellet) { if (gameState == PacManGameState.AttractMode) { @@ -234,7 +234,7 @@ namespace Marro.PacManUdon public void PacManCaught() { - return; + //return; StartTimeSequence(PacManTimeSequence.PacManCaught); } diff --git a/Assets/Scripts/Ghost.cs b/Assets/Scripts/Ghost.cs index d04e0a1..852152d 100644 --- a/Assets/Scripts/Ghost.cs +++ b/Assets/Scripts/Ghost.cs @@ -197,15 +197,10 @@ namespace Marro.PacManUdon TryToTurn(position, ref nextPosition); } - var distance = Vector2.Distance(position, nextPosition); - if (distance > 0.5f) - { - Debug.LogError($"{gameObject} Just jumped by distance {distance}! position: {position}, nextPosition: {nextPosition}, direction: {direction}, offGrid: {offGrid}, ghostState: {ghostState}"); - } - if (CrossesTileBorder(position, nextPosition, direction)) { - var inTunnel = pelletManager.IsInTunnel(nextPosition); + var inTunnel = pelletManager.GhostMoveToTile(nextPosition, Index); + if (inTunnel != this.inTunnel) { this.inTunnel = inTunnel; @@ -595,6 +590,20 @@ namespace Marro.PacManUdon } } + internal void HitPacMan() + { + if (isScared) + { + Debug.Log($"{gameObject} was cought!"); + ghostManager.GhostCaughtQueue(this); + } + else if (ghostState == PacManGhostState.Normal) + { + Debug.Log($"{gameObject} cought PacMan!"); + ghostManager.CapturedPacMan(); + } + } + public void Caught(int scoreBonus) { isScared = false; @@ -844,22 +853,5 @@ namespace Marro.PacManUdon return base.WriteSyncedData(data, ref index, eventType); } - - void OnTriggerEnter(Collider other) - { - if (other.gameObject.GetComponent()) - { - if (isScared) - { - // Debug.Log($"{gameObject} was cought!"); - ghostManager.GhostCaughtQueue(this); - } - else if (ghostState == PacManGhostState.Normal) - { - // Debug.Log($"{gameObject} cought PacMan!"); - ghostManager.CapturedPacMan(); - } - } - } } } \ No newline at end of file diff --git a/Assets/Scripts/PacMan.cs b/Assets/Scripts/PacMan.cs index 2e1c66b..7eca35c 100644 --- a/Assets/Scripts/PacMan.cs +++ b/Assets/Scripts/PacMan.cs @@ -213,13 +213,13 @@ namespace Marro.PacManUdon private void CheckNewTile(Vector2 position, Vector2 nextPosition) { - var pellet = pelletManager.EatAtTile(position, nextPosition); + var eatResult = pelletManager.PacManMoveToTile(position, nextPosition); - if (pellet == PelletType.Pellet) + if (eatResult == EatResult.Pellet) { freezeSeconds = 0.0166666666666667f; } - else if (pellet == PelletType.PowerPellet) + else if (eatResult == EatResult.PowerPellet) { freezeSeconds = freezeSeconds = 0.05f; } diff --git a/Assets/Scripts/PelletManager.asset b/Assets/Scripts/PelletManager.asset index 3c0e000..50b3466 100644 --- a/Assets/Scripts/PelletManager.asset +++ b/Assets/Scripts/PelletManager.asset @@ -43,7 +43,7 @@ MonoBehaviour: Data: - Name: Entry: 12 - Data: 13 + Data: 16 - Name: Entry: 7 Data: @@ -385,25 +385,25 @@ MonoBehaviour: Data: - Name: $k Entry: 1 - Data: powerPelletBlinkEnabled + Data: ghosts - Name: $v Entry: 7 Data: 22|UdonSharp.Compiler.FieldDefinition, UdonSharp.Editor - Name: k__BackingField Entry: 1 - Data: powerPelletBlinkEnabled + Data: ghosts - Name: k__BackingField Entry: 7 Data: 23|System.RuntimeType, mscorlib - Name: Entry: 1 - Data: System.Boolean, mscorlib + Data: Marro.PacManUdon.Ghost[], Assembly-CSharp - Name: Entry: 8 Data: - Name: k__BackingField Entry: 9 - Data: 23 + Data: 17 - Name: k__BackingField Entry: 7 Data: System.Nullable`1[[UdonSharp.UdonSyncMode, UdonSharp.Runtime]], mscorlib @@ -439,19 +439,19 @@ MonoBehaviour: Data: - Name: $k Entry: 1 - Data: powerPelletBlinkToggleInterval + Data: powerPelletBlinkEnabled - Name: $v Entry: 7 Data: 25|UdonSharp.Compiler.FieldDefinition, UdonSharp.Editor - Name: k__BackingField Entry: 1 - Data: powerPelletBlinkToggleInterval + Data: powerPelletBlinkEnabled - Name: k__BackingField Entry: 7 Data: 26|System.RuntimeType, mscorlib - Name: Entry: 1 - Data: System.Single, mscorlib + Data: System.Boolean, mscorlib - Name: Entry: 8 Data: @@ -493,19 +493,73 @@ MonoBehaviour: Data: - Name: $k Entry: 1 - Data: powerPelletBlinkProgress + Data: powerPelletBlinkToggleInterval - Name: $v Entry: 7 Data: 28|UdonSharp.Compiler.FieldDefinition, UdonSharp.Editor + - Name: k__BackingField + Entry: 1 + Data: powerPelletBlinkToggleInterval + - Name: k__BackingField + Entry: 7 + Data: 29|System.RuntimeType, mscorlib + - Name: + Entry: 1 + Data: System.Single, mscorlib + - Name: + Entry: 8 + Data: + - Name: k__BackingField + Entry: 9 + Data: 29 + - Name: k__BackingField + Entry: 7 + Data: System.Nullable`1[[UdonSharp.UdonSyncMode, UdonSharp.Runtime]], mscorlib + - Name: + Entry: 6 + Data: + - Name: + Entry: 8 + Data: + - Name: k__BackingField + Entry: 5 + Data: false + - Name: _fieldAttributes + Entry: 7 + Data: 30|System.Collections.Generic.List`1[[System.Attribute, mscorlib]], mscorlib + - Name: + Entry: 12 + Data: 0 + - Name: + Entry: 13 + Data: + - Name: + Entry: 8 + Data: + - Name: + Entry: 8 + Data: + - Name: + Entry: 8 + Data: + - Name: + Entry: 7 + Data: + - Name: $k + Entry: 1 + Data: powerPelletBlinkProgress + - Name: $v + Entry: 7 + Data: 31|UdonSharp.Compiler.FieldDefinition, UdonSharp.Editor - Name: k__BackingField Entry: 1 Data: powerPelletBlinkProgress - Name: k__BackingField Entry: 9 - Data: 26 + Data: 29 - Name: k__BackingField Entry: 9 - Data: 26 + Data: 29 - Name: k__BackingField Entry: 7 Data: System.Nullable`1[[UdonSharp.UdonSyncMode, UdonSharp.Runtime]], mscorlib @@ -520,7 +574,7 @@ MonoBehaviour: Data: false - Name: _fieldAttributes Entry: 7 - Data: 29|System.Collections.Generic.List`1[[System.Attribute, mscorlib]], mscorlib + Data: 32|System.Collections.Generic.List`1[[System.Attribute, mscorlib]], mscorlib - Name: Entry: 12 Data: 0 @@ -544,70 +598,16 @@ MonoBehaviour: Data: powerPelletBlinkCurrentlyVisible - Name: $v Entry: 7 - Data: 30|UdonSharp.Compiler.FieldDefinition, UdonSharp.Editor + Data: 33|UdonSharp.Compiler.FieldDefinition, UdonSharp.Editor - Name: k__BackingField Entry: 1 Data: powerPelletBlinkCurrentlyVisible - Name: k__BackingField Entry: 9 - Data: 23 + Data: 26 - Name: k__BackingField Entry: 9 - Data: 23 - - Name: k__BackingField - Entry: 7 - Data: System.Nullable`1[[UdonSharp.UdonSyncMode, UdonSharp.Runtime]], mscorlib - - Name: - Entry: 6 - Data: - - Name: - Entry: 8 - Data: - - Name: k__BackingField - Entry: 5 - Data: false - - Name: _fieldAttributes - Entry: 7 - Data: 31|System.Collections.Generic.List`1[[System.Attribute, mscorlib]], mscorlib - - Name: - Entry: 12 - Data: 0 - - Name: - Entry: 13 - Data: - - Name: - Entry: 8 - Data: - - Name: - Entry: 8 - Data: - - Name: - Entry: 8 - Data: - - Name: - Entry: 7 - Data: - - Name: $k - Entry: 1 - Data: syncedPelletsCollected - - Name: $v - Entry: 7 - Data: 32|UdonSharp.Compiler.FieldDefinition, UdonSharp.Editor - - Name: k__BackingField - Entry: 1 - Data: syncedPelletsCollected - - Name: k__BackingField - Entry: 7 - Data: 33|System.RuntimeType, mscorlib - - Name: - Entry: 1 - Data: System.Byte[], mscorlib - - Name: - Entry: 8 - Data: - - Name: k__BackingField - Entry: 9 - Data: 33 + Data: 26 - Name: k__BackingField Entry: 7 Data: System.Nullable`1[[UdonSharp.UdonSyncMode, UdonSharp.Runtime]], mscorlib @@ -643,19 +643,25 @@ MonoBehaviour: Data: - Name: $k Entry: 1 - Data: collisionMap + Data: syncedPelletsCollected - Name: $v Entry: 7 Data: 35|UdonSharp.Compiler.FieldDefinition, UdonSharp.Editor - Name: k__BackingField Entry: 1 - Data: collisionMap + Data: syncedPelletsCollected - Name: k__BackingField - Entry: 9 - Data: 33 + Entry: 7 + Data: 36|System.RuntimeType, mscorlib + - Name: + Entry: 1 + Data: System.Byte[], mscorlib + - Name: + Entry: 8 + Data: - Name: k__BackingField Entry: 9 - Data: 33 + Data: 36 - Name: k__BackingField Entry: 7 Data: System.Nullable`1[[UdonSharp.UdonSyncMode, UdonSharp.Runtime]], mscorlib @@ -670,7 +676,55 @@ MonoBehaviour: Data: false - Name: _fieldAttributes Entry: 7 - Data: 36|System.Collections.Generic.List`1[[System.Attribute, mscorlib]], mscorlib + Data: 37|System.Collections.Generic.List`1[[System.Attribute, mscorlib]], mscorlib + - Name: + Entry: 12 + Data: 0 + - Name: + Entry: 13 + Data: + - Name: + Entry: 8 + Data: + - Name: + Entry: 8 + Data: + - Name: + Entry: 8 + Data: + - Name: + Entry: 7 + Data: + - Name: $k + Entry: 1 + Data: collisionMap + - Name: $v + Entry: 7 + Data: 38|UdonSharp.Compiler.FieldDefinition, UdonSharp.Editor + - Name: k__BackingField + Entry: 1 + Data: collisionMap + - Name: k__BackingField + Entry: 9 + Data: 36 + - Name: k__BackingField + Entry: 9 + Data: 36 + - Name: k__BackingField + Entry: 7 + Data: System.Nullable`1[[UdonSharp.UdonSyncMode, UdonSharp.Runtime]], mscorlib + - Name: + Entry: 6 + Data: + - Name: + Entry: 8 + Data: + - Name: k__BackingField + Entry: 5 + Data: false + - Name: _fieldAttributes + Entry: 7 + Data: 39|System.Collections.Generic.List`1[[System.Attribute, mscorlib]], mscorlib - Name: Entry: 12 Data: 0 @@ -694,16 +748,16 @@ MonoBehaviour: Data: pelletMap - Name: $v Entry: 7 - Data: 37|UdonSharp.Compiler.FieldDefinition, UdonSharp.Editor + Data: 40|UdonSharp.Compiler.FieldDefinition, UdonSharp.Editor - Name: k__BackingField Entry: 1 Data: pelletMap - Name: k__BackingField Entry: 9 - Data: 33 + Data: 36 - Name: k__BackingField Entry: 9 - Data: 33 + Data: 36 - Name: k__BackingField Entry: 7 Data: System.Nullable`1[[UdonSharp.UdonSyncMode, UdonSharp.Runtime]], mscorlib @@ -718,7 +772,109 @@ MonoBehaviour: Data: false - Name: _fieldAttributes Entry: 7 - Data: 38|System.Collections.Generic.List`1[[System.Attribute, mscorlib]], mscorlib + Data: 41|System.Collections.Generic.List`1[[System.Attribute, mscorlib]], mscorlib + - Name: + Entry: 12 + Data: 0 + - Name: + Entry: 13 + Data: + - Name: + Entry: 8 + Data: + - Name: + Entry: 8 + Data: + - Name: + Entry: 8 + Data: + - Name: + Entry: 7 + Data: + - Name: $k + Entry: 1 + Data: ghostPositions + - Name: $v + Entry: 7 + Data: 42|UdonSharp.Compiler.FieldDefinition, UdonSharp.Editor + - Name: k__BackingField + Entry: 1 + Data: ghostPositions + - Name: k__BackingField + Entry: 7 + Data: 43|System.RuntimeType, mscorlib + - Name: + Entry: 1 + Data: System.Int32[], mscorlib + - Name: + Entry: 8 + Data: + - Name: k__BackingField + Entry: 9 + Data: 43 + - Name: k__BackingField + Entry: 7 + Data: System.Nullable`1[[UdonSharp.UdonSyncMode, UdonSharp.Runtime]], mscorlib + - Name: + Entry: 6 + Data: + - Name: + Entry: 8 + Data: + - Name: k__BackingField + Entry: 5 + Data: false + - Name: _fieldAttributes + Entry: 7 + Data: 44|System.Collections.Generic.List`1[[System.Attribute, mscorlib]], mscorlib + - Name: + Entry: 12 + Data: 0 + - Name: + Entry: 13 + Data: + - Name: + Entry: 8 + Data: + - Name: + Entry: 8 + Data: + - Name: + Entry: 8 + Data: + - Name: + Entry: 7 + Data: + - Name: $k + Entry: 1 + Data: pacManPosition + - Name: $v + Entry: 7 + Data: 45|UdonSharp.Compiler.FieldDefinition, UdonSharp.Editor + - Name: k__BackingField + Entry: 1 + Data: pacManPosition + - Name: k__BackingField + Entry: 9 + Data: 7 + - Name: k__BackingField + Entry: 9 + Data: 7 + - Name: k__BackingField + Entry: 7 + Data: System.Nullable`1[[UdonSharp.UdonSyncMode, UdonSharp.Runtime]], mscorlib + - Name: + Entry: 6 + Data: + - Name: + Entry: 8 + Data: + - Name: k__BackingField + Entry: 5 + Data: false + - Name: _fieldAttributes + Entry: 7 + Data: 46|System.Collections.Generic.List`1[[System.Attribute, mscorlib]], mscorlib - Name: Entry: 12 Data: 0 diff --git a/Assets/Scripts/PelletManager.cs b/Assets/Scripts/PelletManager.cs index 795cde6..eca7b3b 100644 --- a/Assets/Scripts/PelletManager.cs +++ b/Assets/Scripts/PelletManager.cs @@ -3,12 +3,13 @@ using UnityEngine; namespace Marro.PacManUdon { - enum PelletType + enum EatResult { None, Pellet, PowerPellet } + public class PelletManager : SyncedObject { public int PelletCount => pellets.Length; @@ -19,6 +20,7 @@ namespace Marro.PacManUdon Pellet[] pellets; Animator[] powerPellets; + Ghost[] ghosts; bool powerPelletBlinkEnabled; float powerPelletBlinkToggleInterval; @@ -33,10 +35,14 @@ namespace Marro.PacManUdon const int mazeWidth = 32; const int mazeHeight = 32; - public void Initialize(GameManager gameManager, BonusFruit bonusFruit) + private int[] ghostPositions = new int[4]; + private int pacManPosition; + + public void Initialize(GameManager gameManager, BonusFruit bonusFruit, Ghost[] ghosts) { this.gameManager = gameManager; this.bonusFruit = bonusFruit; + this.ghosts = ghosts; gameObject.SetActive(true); pellets = GetComponentsInChildren(includeInactive: true); @@ -101,29 +107,50 @@ namespace Marro.PacManUdon var index = GetTilemapIndex(position + directionVector); var tile = collisionMap[index]; var result = (tile & (int)PacManCollisionInfoType.Wall) != 0; - Debug.Log($"IsWallUpcoming {position}, {directionVector}. index {index}, tile {tile}, result {result}, collisionMap.Length {collisionMap.Length}"); + //Debug.Log($"IsWallUpcoming {position}, {directionVector}. index {index}, tile {tile}, result {result}, collisionMap.Length {collisionMap.Length}"); return result; } - public bool IsInTunnel(Vector2 position) + public bool GhostMoveToTile(Vector2 position, int ghostIndex) { - var result = (collisionMap[GetTilemapIndex(position)] & (int)PacManCollisionInfoType.Tunnel) != 0; - if (result) + var tile = GetTilemapIndex(position); + + ghostPositions[ghostIndex] = tile; + + if (tile == pacManPosition) { - Debug.Log($"In tunnel at {position}"); + Debug.Log("Ghost hit PacMan!"); + ghosts[ghostIndex].HitPacMan(); } - return result; + + return (collisionMap[tile] & (int)PacManCollisionInfoType.Tunnel) != 0; } - internal PelletType EatAtTile(Vector2 position, Vector2 nextPosition) + internal EatResult PacManMoveToTile(Vector2 position, Vector2 nextPosition) { var tilemapIndex = GetTilemapIndex(nextPosition); var tile = pelletMap[tilemapIndex]; + pacManPosition = tilemapIndex; + + TryEatGhost(tilemapIndex); + TryCollectFruit(tile, position, nextPosition); return TryCollectPellet(tile, tilemapIndex); } + private void TryEatGhost(int tilemapIndex) + { + for (int i = 0; i < ghosts.Length; i++) + { + if (ghostPositions[i] == tilemapIndex) + { + Debug.Log("PacMan hit ghost!"); + ghosts[i].HitPacMan(); + } + } + } + private void TryCollectFruit(int tile, Vector2 position, Vector2 nextPosition) { if (tile != (int)PacManConsumableType.FruitLeft && tile != (int)PacManConsumableType.FruitRight @@ -134,12 +161,12 @@ namespace Marro.PacManUdon var previousTile = pelletMap[GetTilemapIndex(position)]; - Debug.Log($"On fruit tile {tile}, previous tile was {previousTile}. Position {position}, nextPosition {nextPosition}"); + //Debug.Log($"On fruit tile {tile}, previous tile was {previousTile}. Position {position}, nextPosition {nextPosition}"); if (tile == (int)PacManConsumableType.FruitLeft && previousTile == (int)PacManConsumableType.FruitRight || tile == (int)PacManConsumableType.FruitRight && previousTile == (int)PacManConsumableType.FruitLeft) { - Debug.Log("Collecting fruit"); + //Debug.Log("Collecting fruit"); gameManager.GotFruit(); } @@ -163,11 +190,11 @@ namespace Marro.PacManUdon #endregion #region Pellet collecting - private PelletType TryCollectPellet(int tile, int tilemapIndex) + private EatResult TryCollectPellet(int tile, int tilemapIndex) { if (tile < 0 || tile >= pellets.Length) { - return PelletType.None; + return EatResult.None; } pelletMap[tilemapIndex] = (byte)PacManConsumableType.None; @@ -180,9 +207,9 @@ namespace Marro.PacManUdon PelletCollectedCount++; - var pelletType = pellet.isPowerPellet ? PelletType.PowerPellet : PelletType.Pellet; + var pelletType = pellet.isPowerPellet ? EatResult.PowerPellet : EatResult.Pellet; - gameManager.GotPellet(pellet, pelletType, PelletCollectedCount, PelletCount - PelletCollectedCount); + gameManager.GotPellet(pellet, pellet.isPowerPellet, PelletCollectedCount, PelletCount - PelletCollectedCount); return pelletType; } diff --git a/Assets/Scripts/Sequences/AttractScreenIntroduction.cs b/Assets/Scripts/Sequences/AttractScreenIntroduction.cs index 8b1fb8b..93c9b74 100644 --- a/Assets/Scripts/Sequences/AttractScreenIntroduction.cs +++ b/Assets/Scripts/Sequences/AttractScreenIntroduction.cs @@ -16,7 +16,7 @@ namespace Marro.PacManUdon // Initialize soundManager.SuppressSound(true); attractScreen.gameObject.SetActive(true); - attractScreen.Initialize(this, bonusFruit); + attractScreen.Initialize(this, bonusFruit, ghostManager.Ghosts); for (int i = 0; i <= 15; i++) { // Debug.Log($"{gameObject} TimeSequenceAttractScreen deactivating with iteration i");