I have 5 ghosts, 4 of which are disabled and invisible and sitting off to the side until a timer brings them in. problem is, once they are in, they dont move. How do i make my ghosts chase pacman? I am using Visual Basic Express 2008. i have enclosed a copy of my program for further refrence as well.
Firstly a question, how are you making Pacman move just now? The answer, you have to push a direction using one of the arrow keys. It just so happens that when you hold down an arrow key, the method that you call just so happens to continually get repeated. However, at the end of the day, what is a button push? It's an event that is raised when the button gets pushed. And what happens when that event is raised? The specified event handler for that event gets called. In this case, that event handler is the button click event.
Where am I going with this? Let me try and explain...
What happens when the timer interval expires? An event is raised, and the corresponding event handler for that event gets called, in this case, the timer tick event.
What does all the mean?
How about make a timer and on the tick event of the timer, make a ghost move?
Does that make sense?
Let me know what you think. I won't say too much more, cause I know you want to try and figure this out, but let me know what you think.
To answer your other question, you would need to do the following...
At the minute, you are setting the Image property of the Pacman picturebox at design time, but there is nothing to stop you setting this at runtime.
For instance, assuming you have four resources called pac_man_up, pac_man_down, pac_man_left and pac_man_right, then you should be able to use the following:
Code:
'move pacman
If e.KeyCode = Keys.Up Then
Pacman.Top -= 8
Pacman.Image = My.Resources.pac_man_up
ElseIf e.KeyCode = Keys.Down Then
Pacman.Top -= -8
Pacman.Image = My.Resources.pac_man_down
ElseIf e.KeyCode = Keys.Left Then
Pacman.Left -= 8
Pacman.Image = My.Resources.pac_man_left
ElseIf e.KeyCode = Keys.Right Then
Pacman.Left -= -8
Pacman.Image = My.Resources.pac_man_right
End If
Thanks a lot gep! I get where your going for you timer idea, but that would be just total random movement. that doesnt get me anywhere. i was thinking more along the lines of when the tick is called, the ghost moves up. if the intersectswith code is activated though(it hits a wall) it goes in a new direction. This too is totaly random movement, but its a step up. And i figured that was the code i just didnt have my.resources.... i was just putting resources lol. and clarky, i am doing this for total amusement, not a class. but if you could teach me how to make an ai, then i would be grateful. From what i know of ai's though they are insanly difficult to make (warcraft 3 world editor =]) im not sure if its easier on vb but im just a beginner so im not sure if ai is in the picture.
'Move Ghosts
Private Sub Timer5_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles GhostMove.Tick
Ghost.Top += -8
For Each mycontrol As Control In Me.Controls
If TypeOf mycontrol Is PictureBox Then
If Ghost.Bounds.IntersectsWith(mycontrol.Bounds) Then
If mycontrol.Name.StartsWith("Wall") Then
Ghost.Location = Ghostlocation
Ghost.Top += 0
Ghost.Left += 8
End If
End If
End If
Next
Ghostlocation = Ghost.Location
End Sub
Now beng pros, you guys can probably spot a million different errors on this code. i can only get one. because pacman is moving on tick, he will ALWAYS be moving up. That really screws me up. And if hes not moving up, hes not hitting the wall, which means he wont be moving left. 0.o what i have now makes pacman move all the way up to the wall above him, and follow that wall right. when that wall ends, he goes up again. and it goes on and on. sugestion, is there any way a random number generator could help? (i have no idea what that means ive just heard it before and it has random in it which is what i want)
I think you are heading in the right direction, but you might want to change your technique slightly. For instance, how about using a variable that stores the direction that the ghostis moving, and then when you detect a collision, choose a random direction for the ghost to travel?
For instance, you could do something similar to the following:
Code:
Private Sub Timer1_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Timer1.Tick
Select Case direction
Case MovementDirection.Down
Ghost1.Top += 8
Case MovementDirection.Up
Ghost1.Top -= 8
Case MovementDirection.Left
Ghost1.Left -= 8
Case MovementDirection.Right
Ghost1.Left += 8
End Select
DetectCollection(Ghost1)
End Sub
I have created a DetectCollision method, and it's sole purpose is to loop through all the pictureboxs and find out when a collision happens:
Code:
Private Function DetectCollection(ByVal ghost As PictureBox) As Boolean
For Each wall As PictureBox In WallCollection
If ghost.Bounds.IntersectsWith(wall.Bounds) Then
direction = MovementDirection.Right
End If
Next
End Function
At the minute, the ghost starts by going up, and as soon as it detects a collision I am forcing it to go to the right, but at this point you could select a random direction and make it go in that direction.
As per our previous discussions, I have created a collection of pictureboxs so that I can do this looping, this is done on the load event of the form:
Code:
Private Sub Form1_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
Ghost1.Location = New Point(510, 252)
Ghost1.Visible = True
Ghost1.Enabled = True
direction = MovementDirection.Up
For Each myControl As Control In Me.Controls
If TypeOf myControl Is PictureBox Then
If myControl.Name.StartsWith("Wall") Then
WallCollection.Add(myControl)
ElseIf myControl.Name.StartsWith("PictureBox") Then
FoodCollection.Add(myControl)
ElseIf myControl.Name.StartsWith("Ghost") Then
GhostCollection.Add(myControl)
End If
End If
Next
End Sub
The necessary variables are declared as such:
Code:
#Region "Global"
Dim currentLocation As Point
Dim score As Double = 0
Dim direction As MovementDirection
Dim WallCollection As New List(Of PictureBox)()
Dim GhostCollection As New List(Of PictureBox)()
Dim FoodCollection As New List(Of PictureBox)()
#End Region
In order to store the direction that the ghost is going, I have created an enumeration:
Code:
Public Enum MovementDirection
Up
Down
Left
Right
End Enum
What you think? Make sense?
I noticed a slight bug in your code. Once you have collected all the food you pop up a message box, well you click ok, if you then move pacman again, this message box keeps popping up.
Couple of things, what exactly is "case?" and Movement direction isnt something i can declare a variable to. i copied and pasted it right on there and it said that it didnt exist. Also how do i make the movement completly random?
Select Case is similar to a set of nested if then else's. If you have a lot of cases, then a Select Case structure is slightly neater in my opinion. You could read the above as:
Code:
If direction = MovementDirection.Up Then
Else
End If
Here is the full version of the code that I modified:
Code:
Public Class Form1
#Region "Pac Man"
Public Enum MovementDirection
Up
Down
Left
Right
End Enum
Private Sub Pacman_KeyDown(ByVal sender As System.Object, ByVal e As System.Windows.Forms.KeyEventArgs) Handles Pacman.KeyDown, MyBase.KeyDown
'move pacman
If e.KeyCode = Keys.Up Then
Pacman.Top -= 8
Pacman.Image = My.Resources.pac_man_up
ElseIf e.KeyCode = Keys.Down Then
Pacman.Top -= -8
Pacman.Image = My.Resources.pac_man_down
ElseIf e.KeyCode = Keys.Left Then
Pacman.Left -= 8
Pacman.Image = My.Resources.pac_man_left
ElseIf e.KeyCode = Keys.Right Then
Pacman.Left -= -8
Pacman.Image = My.Resources.pac_man_right
End If
For Each food As PictureBox In FoodCollection
If food.Visible = True Then
If Pacman.Bounds.IntersectsWith(food.Bounds) Then
food.Visible = False
score = score + 1
Label1.Text = score
End If
End If
Next
For Each wall As PictureBox In WallCollection
If Pacman.Bounds.IntersectsWith(wall.Bounds) Then
Pacman.Location = currentLocation
End If
Next
currentLocation = Pacman.Location
If Label1.Text = 188 Then
MsgBox("Congratulations! You win!")
End If
End Sub
#End Region
#Region "Ghosts"
'make Ghosts
Private Sub Timer1_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Timer1.Tick
Select Case direction
Case MovementDirection.Down
Ghost1.Top += 8
Case MovementDirection.Up
Ghost1.Top -= 8
Case MovementDirection.Left
Ghost1.Left -= 8
Case MovementDirection.Right
Ghost1.Left += 8
End Select
DetectCollection(Ghost1)
End Sub
Private Function DetectCollection(ByVal ghost As PictureBox) As Boolean
For Each wall As PictureBox In WallCollection
If ghost.Bounds.IntersectsWith(wall.Bounds) Then
direction = MovementDirection.Right
End If
Next
End Function
Private Sub Timer2_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Timer2.Tick
Ghost2.Location = New Point(510, 252)
Ghost2.Visible = True
Ghost2.Enabled = True
Timer2.Stop()
End Sub
#End Region
#Region "Global"
Dim currentLocation As Point
Dim score As Double = 0
Dim direction As MovementDirection
Dim WallCollection As New List(Of PictureBox)()
Dim GhostCollection As New List(Of PictureBox)()
Dim FoodCollection As New List(Of PictureBox)()
#End Region
Private Sub Form1_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
Ghost1.Location = New Point(510, 252)
Ghost1.Visible = True
Ghost1.Enabled = True
direction = MovementDirection.Up
For Each myControl As Control In Me.Controls
If TypeOf myControl Is PictureBox Then
If myControl.Name.StartsWith("Wall") Then
WallCollection.Add(myControl)
ElseIf myControl.Name.StartsWith("PictureBox") Then
FoodCollection.Add(myControl)
ElseIf myControl.Name.StartsWith("Ghost") Then
GhostCollection.Add(myControl)
End If
End If
Next
End Sub
End Class
As to how you could make the movement random... You would need to look into using the Random Class you pick a random number between 1 and 4, and then say Up = 1, Down = 2, Left = 3, Right = 4 etc.
I am at work just now, but I could always have a look at this tonight if I get a chance.
the movementdirection still doesnt work. I dont think its a valid code for me. vb 2008 express and whats the use of the enum function you have at the top?
The code that I pasted is a direct copy from my Visual Basic Express 2008, so it should work in yours also.
The enum function at the top is the MovementDirection declaration, so you will need to include that. If you have a variable that you know only has a set number of variables, you can create an enum, or enumeration. In this case, there are only four direction that the ghost can go. Up, Down, Left, Right. Therefore, I created an enum to hold these values, which means I can then reference them in the code using MovementDirection.Up.
If you make a copy of your project and copy all of the code that I pasted above into your Form1.vb file, then you should see it all working.
It is a method, or rather a Function, it is declared just under the Timer1_Tick event, here it is again.
Code:
Private Function DetectCollection(ByVal ghost As PictureBox) As Boolean
For Each wall As PictureBox In WallCollection
If ghost.Bounds.IntersectsWith(wall.Bounds) Then
direction = MovementDirection.Right
End If
Next
End Function
To see all the code working did you try what I suggested in #11?
thing is like i said before in another post, i dont want to just copy and paste code. i want to know whats happeneing. I didnt know you could declare things like that lol. also, when i start up my program now, the ghost doesnt move. he just stands still.
Public Class Form1
#Region "Pac Man"
Private Sub Pacman_KeyDown(ByVal sender As System.Object, ByVal e As System.Windows.Forms.KeyEventArgs) Handles Pacman.KeyDown, MyBase.KeyDown
'move pacman
If e.KeyCode = Keys.Up Then
Pacman.Top -= 8
Pacman.Image = My.Resources.Pac_man_up
ElseIf e.KeyCode = Keys.Down Then
Pacman.Top -= -8
Pacman.Image = My.Resources.Pac_man_down
ElseIf e.KeyCode = Keys.Left Then
Pacman.Left -= 8
Pacman.Image = My.Resources.Pac_man
ElseIf e.KeyCode = Keys.Right Then
Pacman.Left -= -8
Pacman.Image = My.Resources.Pac_man1
End If
'stop pacman from hitting walls
For Each myControl As Control In Me.Controls
If TypeOf myControl Is PictureBox Then
If Pacman.Bounds.IntersectsWith(myControl.Bounds) Then
If myControl.Name.StartsWith("Wall") Then
Pacman.Location = currentLocation
ElseIf myControl.Name.StartsWith("PictureBox") Then
If myControl.Visible = True Then
myControl.Visible = False
score = score + 1
Label1.Text = score
ElseIf myControl.Name.StartsWith("Ghost") Then
Pacman.Location = New Point(901, 83)
End If
End If
End If
End If
Next
currentLocation = Pacman.Location
If Label1.Text = 188 Then
MsgBox("Congratulations! You win!")
If DialogResult = MsgBoxResult.Ok Then
Application.Exit()
End If
End If
End Sub
#End Region
#Region "Ghosts"
'make Ghosts
Private Sub Timer1_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Timer1.Tick
Ghost1.Location = New Point(510, 252)
Ghost1.Visible = True
Ghost1.Enabled = True
Timer1.Stop()
End Sub
Private Sub Timer2_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Timer2.Tick
Ghost2.Location = New Point(510, 252)
Ghost2.Visible = True
Ghost2.Enabled = True
Timer2.Stop()
End Sub
Private Sub Timer3_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Timer3.Tick
Ghost3.Location = New Point(510, 252)
Ghost3.Visible = True
Ghost3.Enabled = True
Timer3.Stop()
End Sub
Private Sub Timer4_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Timer4.Tick
Ghost4.Location = New Point(510, 252)
Ghost4.Visible = True
Ghost4.Enabled = True
Timer4.Stop()
End Sub
'Move Ghosts
Private Sub Timer5_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles GhostMove.Tick
Select Case direction
Case Movementdirection.Down
Ghost.Top += 8
Case Movementdirection.Up
Ghost.Top -= 8
Case Movementdirection.Left
Ghost.Left -= 8
Case Movementdirection.Right
Ghost.Left += 8
End Select
DetectCollection(Ghost1)
End Sub
Private Function DetectCollection(ByVal ghost As PictureBox) As Boolean
For Each wall As PictureBox In WallCollection
If ghost.Bounds.IntersectsWith(wall.Bounds) Then
direction = Movementdirection.Up
End If
Next
End Function
#End Region
#Region "Global"
Dim currentLocation As Point
Dim score As Double = 0
Dim Ghostlocation As Point
Dim direction As Movementdirection
Dim WallCollection As New List(Of PictureBox)()
Dim FoodCollection As New List(Of PictureBox)()
Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
For Each box As Control In Me.Controls
If box.Name.StartsWith("Wall") Then
WallCollection.Add(box)
ElseIf box.Name.StartsWith("PictureBox") Then
FoodCollection.Add(box)
End If
Next
Ghost.Location = New Point(510, 252)
Ghost.Visible = True
Ghost.Enabled = True
direction = Movementdirection.Up
End Sub
Public Enum Movementdirection
Up
Down
Left
Right
End Enum
#End Region
End Class
Private Function DetectCollection(ByVal ghost As PictureBox) As Boolean
For Each wall As PictureBox In WallCollection
If ghost.Bounds.IntersectsWith(wall.Bounds) Then
direction = Movementdirection.Up
End If
If ghost.Bounds.IntersectsWith(wall.Bounds) Then
If direction = Movementdirection.Up Then
direction = Movementdirection.Right
End If
End If
Next
End Function
ive been messing around with this code but i cant seem to get it right. In this code if the ghost hits a wall, it will go right. that part works. but if he hits a wall going right, he goes right through it. thats to be expected. so i added a bunch of elseif's, but they didnt work
Code:
Private Function DetectCollection(ByVal ghost As PictureBox) As Boolean
For Each wall As PictureBox In WallCollection
If ghost.Bounds.IntersectsWith(wall.Bounds) Then
direction = Movementdirection.Up
End If
If ghost.Bounds.IntersectsWith(wall.Bounds) Then
If direction = Movementdirection.Up Then
direction = Movementdirection.Right
ElseIf direction = Movementdirection.Right Then
direction = Movementdirection.Down
End If
End If
Next
End Function
Okay, I noticed a couple of things with your code.
Firstly, the GhostMove Timer is not enabled, so the ghost will never start moving. You either need to enable to timer in the load event of the form, or Enable it while in design mode.
Also, you currently have:
Code:
DetectCollection(Ghost1)
but if you are trying to move the ghost that I am thinking of, then you are going to want to do this:
Code:
DetectCollection(Ghost)
Also, the reason why the ghost is just going straight through the wall is that on detecting a collision, you are setting the direction to up, which is not going to stop the ghost, you need to change it to something other than Up, and it should work.
Now, in terms of picking a random direction, you can do something like this:
Code:
Dim random As New Random
direction = DirectCast(random.Next(1, 5), Movementdirection)
This is using the built in random number generator to pick a random number, and then picking the direction that equates to this number. In order to achieve this I changed the definition of the enum as follows:
Code:
Public Enum Movementdirection
Up = 1
Down = 2
Left = 3
Right = 4
End Enum
here's how i made the ghosts chase in mine: First the movement was random as in yours, but...
as pacman moves around the screen, he leaves an invisible trail that is exactly equal to whatever direction he was moving when he left that square. When a ghost comes across the trail (invisible - it's in a 2 dimensional array equal to the size of the game grid), it locks on to the trail and starts following it. Now, here's the fun part. If you cross your trail the ghost will automatically veer onto the newest direction. as long as the ghosts are moving faster than you, there is NO ESCAPE. You WILL be caught. But you can also introduce some randomness as well for when you eat the pellets. (note in my game pellets are randomly placed as well). When you go into munch mode, the ghosts can randomly flee, as long as the direction isn't directly towards you in a straight line.
Also in my game: There was a super-ghost mode where they could go through walls. It was higher levels.
it's not even remotely relatable to your code as is. I actually was playing around with excel scripts and it was written entirely as a vbscript on an excel worksheet. The ghosts moved one square at a time and so did i.
But it wouldn't be that hard to implement a chase sequence. You must already have the direction you want to go stored in a variable. Just copy it to a variable in the game grid. You can make your game grid a custom structure. This is how i did my wormy game in .net. In the paint event it reads from the structure one square at a time (tiled-graphics style) to determine where to draw the dots and game area. The structure would look something like this:
Code:
structure GameSquare
dot as boolean
direction as byte
'optional: walltype as byte
end structure
then whatever square the pacman is currently in, you write the current movement direction as 1,2,3,or 4 in that particular underlying part of the array.
let's say your game grid is 50x50
Code:
dim GameGrid(50,50) as GameSquare 'yes i know i have an extra element
'---
place code here to initialize game grid
'---
now in your game loop, not only can you write the position onto the grid, but you also can make sure if the next square in the current movement position is a wall and stop movement. The ghosts would be moved in the same loop but they would check the underlying square for the movement direction. If it exists, set their movement the same direction. If not, check for a wall in existing movement direction. If wall exists, random a new direction (in a do loop)
[code]
let's say ghost is moving east
Code:
'1 is north, 2 is east, 3 is south, 4 is west
'first figure out current ghost square (code not shown) and store in a point named GhostLocation
ReadDir = gamegrid(ghostlocation.x, ghostlocation.y).dir 'checks direction in underlying game grid
if readdir = 0 then
select case ghostdirection
case 0
ghostdirection = rnd() * 4 + 1'gets ghost moving if it's sitting still
case 1
if gamegrid(ghostlocation.x , ghostlocation.y-1).walltype > 0 then ghostdirection = 0 'stops forward movement if a wall is ahead
case 2
if gamegrid(ghostlocation.x + 1, ghostlocation.y).walltype > 0 then ghostdirection = 0 'stops forward movement if a wall is ahead
case 3
if gamegrid(ghostlocation.x , ghostlocation.y+1).walltype > 0 then ghostdirection = 0 'stops forward movement if a wall is ahead
case 4
if gamegrid(ghostlocation.x - 1, ghostlocation.y).walltype > 0 then ghostdirection = 0 'stops forward movement if a wall is ahead
end select
else
ghostdirection = readdir
end if
i think this might give you the idea of how to get going. In this partially coded example, if a ghost finds your trail, it latches onto it. If it doesn't, it moves in a straight line until it hits a wall and then randomly moves a new direction. Obviosly this doesn't take into account you in munch mode. You would need a whole separate block of code for that and choose which one with an if/then.
Im not taking much of that in.... I think im just gonna stick with the ghost moving random since im a begginer. Which brings us back to the original question. how do i make random movement!
Also, if pacman touches the ghost, i want him to go back to his original position. But pacman is moving right through him the code im using isnt working.
Code:
For Each myControl As Control In Me.Controls
If TypeOf myControl Is PictureBox Then
If Pacman.Bounds.IntersectsWith(myControl.Bounds) Then
If myControl.Name.StartsWith("Wall") Then
Pacman.Location = currentLocation
ElseIf myControl.Name.StartsWith("PictureBox") Then
If myControl.Visible = True Then
myControl.Visible = False
score = score + 1
Label1.Text = score
ElseIf myControl.Name.StartsWith("Ghost") Then
Pacman.Location = New Point(901, 83)
End If
End If
End If
End If
Next
For Each myControl As Control In Me.Controls
If TypeOf myControl Is PictureBox Then
If Pacman.Bounds.IntersectsWith(myControl.Bounds) Then
If myControl.Name.StartsWith("Wall") Then
Pacman.Location = currentLocation
ElseIf myControl.Name.StartsWith("PictureBox") Then
If myControl.Visible = True Then
myControl.Visible = False
score = score + 1
Label1.Text = score
ElseIf myControl.Name.StartsWith("Ghost") Then
Pacman.Location = New Point(901, 83)
End If
End If
End If
End If
Next
The way you've got it now, the control has to start with "picturebox" to get to the check to see if it starts with "ghost". Obviously it will never start with ghost if it has to start with picturebox.
I haven't looked at all of your code, but this change SHOULD fix it...
Code:
For Each myControl As Control In Me.Controls
If TypeOf myControl Is PictureBox Then
If Pacman.Bounds.IntersectsWith(myControl.Bounds) Then
If myControl.Name.StartsWith("Wall") Then
Pacman.Location = currentLocation
ElseIf myControl.Name.StartsWith("PictureBox") Then
If myControl.Visible = True Then
myControl.Visible = False
score = score + 1
Label1.Text = score
end if
ElseIf myControl.Name.StartsWith("Ghost") Then
Pacman.Location = New Point(901, 83)
End If
End If
End If
Next
In the situation you are describing above, it is always a good idea to set a breakpoint on the line of code that you are interested in, then when you move the pacman you can check to see what code is being executed, that way you will better understand what the code is doing, and how you can fix it.
I never used breakpoints. Never really knew what they did. is that all they do?
And i just want to stick with random movement so how do i get it. the one gep gave me didnt work.
You can set a break point on any line of code that you want. One of the easiest ways to do it would be to select the line, and then hit F9. Then, when you run your code in debug mode, execution will stop on the line that you have selected. Then by hitting F11 you can step through the code to see what path it is taking.
While in debug mode, it is then possible to highlight variables to find out what their current value is.
Using breakpoints is a very powerful way to debug your application, and I use them on a daily basis. I would highly recommend that you get into the habit of using them, as they can save you a lot of time and headaches
When you say the code that I posted doesn't work, can you show me what you tried. I have code a modified version of the code that you posted that has the Ghost travelling all over the screen in a random manner.
Public Class Form1
#Region "Pac Man"
Private Sub Pacman_KeyDown(ByVal sender As System.Object, ByVal e As System.Windows.Forms.KeyEventArgs) Handles Pacman.KeyDown, MyBase.KeyDown
'move pacman
If e.KeyCode = Keys.Up Then
Pacman.Top -= 8
Pacman.Image = My.Resources.Pac_man_up
ElseIf e.KeyCode = Keys.Down Then
Pacman.Top -= -8
Pacman.Image = My.Resources.Pac_man_down
ElseIf e.KeyCode = Keys.Left Then
Pacman.Left -= 8
Pacman.Image = My.Resources.Pac_man
ElseIf e.KeyCode = Keys.Right Then
Pacman.Left -= -8
Pacman.Image = My.Resources.Pac_man1
End If
'stop pacman from hitting walls
For Each myControl As Control In Me.Controls
If TypeOf myControl Is PictureBox Then
If Pacman.Bounds.IntersectsWith(myControl.Bounds) Then
If myControl.Name.StartsWith("Wall") Then
Pacman.Location = currentLocation
ElseIf myControl.Name.StartsWith("PictureBox") Then
If myControl.Visible = True Then
myControl.Visible = False
score = score + 1
Label1.Text = score
End If
ElseIf myControl.Name.StartsWith("Ghost") Then
Pacman.Location = New Point(901, 83)
Lives = CDbl(Label2.Text)
Label2.Text = Lives - 1
End If
End If
End If
Next
currentLocation = Pacman.Location
If Label1.Text = 188 Then
MsgBox("Congratulations! You win!")
Application.Exit()
End If
If Label2.Text = 0 Then
MsgBox("Game Over")
End If
End Sub
#End Region
#Region "Ghosts"
'make Ghosts
Private Sub Timer1_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Timer1.Tick
Ghost1.Location = New Point(510, 252)
Ghost1.Visible = True
Ghost1.Enabled = True
Timer1.Stop()
End Sub
Private Sub Timer2_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Timer2.Tick
Ghost2.Location = New Point(510, 252)
Ghost2.Visible = True
Ghost2.Enabled = True
Timer2.Stop()
End Sub
Private Sub Timer3_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Timer3.Tick
Ghost3.Location = New Point(510, 252)
Ghost3.Visible = True
Ghost3.Enabled = True
Timer3.Stop()
End Sub
Private Sub Timer4_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Timer4.Tick
Ghost4.Location = New Point(510, 252)
Ghost4.Visible = True
Ghost4.Enabled = True
Timer4.Stop()
End Sub
'Move Ghosts
Private Sub Timer5_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles GhostMove.Tick
Select Case direction
Case Movementdirection.Down
Ghost.Top += 8
Case Movementdirection.Up
Ghost.Top -= 8
Case Movementdirection.Left
Ghost.Left -= 8
Case Movementdirection.Right
Ghost.Left += 8
End Select
DetectCollection(Ghost)
End Sub
Private Function DetectCollection(ByVal ghost As PictureBox) As Boolean
For Each wall As PictureBox In WallCollection
If ghost.Bounds.IntersectsWith(wall.Bounds) Then
direction = Movementdirection.Up
End If
If ghost.Bounds.IntersectsWith(wall.Bounds) Then
If direction = Movementdirection.Up Then
direction = Movementdirection.Right
ElseIf direction = Movementdirection.Right Then
direction = Movementdirection.Down
End If
End If
Next
End Function
Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
For Each box As Control In Me.Controls
If box.Name.StartsWith("Wall") Then
WallCollection.Add(box)
ElseIf box.Name.StartsWith("PictureBox") Then
FoodCollection.Add(box)
End If
Next
Ghost.Location = New Point(510, 252)
Ghost.Visible = True
Ghost.Enabled = True
direction = Movementdirection.Up
End Sub
#End Region
#Region "Global"
Dim currentLocation As Point
Dim score As Double = 0
Dim Ghostlocation As Point
Dim WallCollection As New List(Of PictureBox)()
Dim FoodCollection As New List(Of PictureBox)()
Dim random As New Random
Dim direction = DirectCast(random.Next(1, 5), Movementdirection)
Dim Lives As Double
Public Enum Movementdirection
Up = 1
Down = 2
Left = 3
Right = 4
End Enum
#End Region
End Class
The ghost just moves up then right then disappears... *sigh*
Maybe I didn't explain myself very well, but you need to create a Random direction each time that you detect a collision of the ghost with a wall. At the minute, you are only creating a random direction when the form loads.
This is one example of what your DetectCollision should look like:
Code:
Private Function DetectCollection(ByVal ghost As PictureBox) As Boolean
For Each wall As PictureBox In WallCollection
If ghost.Bounds.IntersectsWith(wall.Bounds) Then
ghost.Location = ghostCurrentLocation
direction = DirectCast(random.Next(1, 5), Movementdirection)
End If
Next
ghostCurrentLocation = ghost.Location
End Function
This is possible because in the Globals section I have:
Code:
Dim currentLocation As Point
Dim ghostCurrentLocation As Point
Dim score As Double = 0
Dim Ghostlocation As Point
Dim direction As Movementdirection
Dim WallCollection As New List(Of PictureBox)()
Dim FoodCollection As New List(Of PictureBox)()
Dim random As New Random
Ok, I am not sure what you have done, but I have taken the code that you posted in #33, and replace the globals section and the definition of the DetectCollisions method with what I pasted in post #34 and it builds and works exactly as I expect it to.
Public Class Form1
#Region "Pac Man"
Private Sub Pacman_KeyDown(ByVal sender As System.Object, ByVal e As System.Windows.Forms.KeyEventArgs) Handles Pacman.KeyDown, MyBase.KeyDown
'MOVE PACMAN
If e.KeyCode = Keys.Up Then
Pacman.Top -= 8
Pacman.Image = My.Resources.Pac_man_up
ElseIf e.KeyCode = Keys.Down Then
Pacman.Top -= -8
Pacman.Image = My.Resources.Pac_man_down
ElseIf e.KeyCode = Keys.Left Then
Pacman.Left -= 8
Pacman.Image = My.Resources.Pac_man
ElseIf e.KeyCode = Keys.Right Then
Pacman.Left -= -8
Pacman.Image = My.Resources.Pac_man1
End If
'PACMAN ACTIONS
For Each myControl As Control In Me.Controls
If TypeOf myControl Is PictureBox Then
If Pacman.Bounds.IntersectsWith(myControl.Bounds) Then
If myControl.Name.StartsWith("Wall") Then
Pacman.Location = currentLocation
ElseIf myControl.Name.StartsWith("PictureBox") Then
If myControl.Visible = True Then
myControl.Visible = False
score = score + 1
Label1.Text = score
End If
ElseIf myControl.Name.StartsWith("Ghost") Then
Pacman.Location = New Point(901, 83)
Lives = CDbl(Label2.Text)
Label2.Text = Lives - 1
End If
End If
End If
Next
currentLocation = Pacman.Location
If Label1.Text = 188 Then
MsgBox("Congratulations! You win!")
Application.Exit()
End If
If Label2.Text = 0 Then
MsgBox("Game Over")
End If
End Sub
#End Region
#Region "Ghosts"
'MAKE GHOSTS
Private Sub Timer1_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Timer1.Tick
Ghost1.Location = New Point(510, 252)
Ghost1.Visible = True
Ghost1.Enabled = True
Timer1.Stop()
End Sub
Private Sub Timer2_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Timer2.Tick
Ghost2.Location = New Point(510, 252)
Ghost2.Visible = True
Ghost2.Enabled = True
Timer2.Stop()
End Sub
Private Sub Timer3_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Timer3.Tick
Ghost3.Location = New Point(510, 252)
Ghost3.Visible = True
Ghost3.Enabled = True
Timer3.Stop()
End Sub
Private Sub Timer4_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Timer4.Tick
Ghost4.Location = New Point(510, 252)
Ghost4.Visible = True
Ghost4.Enabled = True
Timer4.Stop()
End Sub
'MOVE GHOSTS
Private Sub Timer5_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles GhostMove.Tick
Select Case direction
Case Movementdirection.Down
Ghost.Top += 8
Case Movementdirection.Up
Ghost.Top -= 8
Case Movementdirection.Left
Ghost.Left -= 8
Case Movementdirection.Right
Ghost.Left += 8
End Select
DetectCollection(Ghost)
End Sub
Private Function DetectCollection(ByVal ghost As PictureBox) As Boolean
For Each wall As PictureBox In WallCollection
If ghost.Bounds.IntersectsWith(wall.Bounds) Then
ghost.Location = Ghostlocation
direction = DirectCast(random.Next(1, 5), Movementdirection)
End If
Next
ghost.Location = Ghostlocation
End Function
Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
For Each box As Control In Me.Controls
If box.Name.StartsWith("Wall") Then
WallCollection.Add(box)
ElseIf box.Name.StartsWith("PictureBox") Then
FoodCollection.Add(box)
End If
Next
Ghostlocation = New Point(510, 252)
Ghost.Visible = True
Ghost.Enabled = True
direction = Movementdirection.Up
End Sub
#End Region
#Region "Global"
Dim currentLocation As Point
Dim score As Double = 0
Dim Ghostlocation As Point
Dim WallCollection As New List(Of PictureBox)()
Dim FoodCollection As New List(Of PictureBox)()
Dim random As New Random
Dim direction As Movementdirection
Dim Lives As Double
Public Enum Movementdirection
Up = 1
Down = 2
Left = 3
Right = 4
End Enum
#End Region
End Class
The only change i think i made was capitalizing the comments lol
in the detectcollision part i took something out i think
Ok, I have copied the above code into my IDE, and I don't get a compilation error, but when I run it the ghost doesn't move, but if you change the method to the following:
Code:
Private Function DetectCollection(ByVal ghost As PictureBox) As Boolean
For Each wall As PictureBox In WallCollection
If ghost.Bounds.IntersectsWith(wall.Bounds) Then
ghost.Location = Ghostlocation
direction = DirectCast(random.Next(1, 5), Movementdirection)
End If
Next
Ghostlocation = ghost.Location
End Function
i dont know what i changed, but i did what you did and i got it working. I think thats all im going to do for now. im gonna redo the course a little so the ghost doesnt get trapped and set the code for the other ghosts. but thats it. If i need help with anything else, ill be posting right here lol.
Thanks a lot gep its been a hell lot of fun working with you. Fifteen and already got hair falling out cuz of this thing....