C# one timer for multiple shapes - c#

For a school project I need to make a small game where multiple Ellipses move.
The last one that gets made with my method to make multiple at the same time moves with the timer I make.
How do you make one timer for all the Ellipses.
class EnemyTeam
{
private Ellipse enemy;
private Canvas canvas;
private double xChange = 50, yChange = 50;
public DispatcherTimer enemyTimer;
private char direction = '0';
private Thickness enemyThickness;
public EnemyTeam(Canvas canvas, double startPosition, SolidColorBrush playerBrush)
{
this.canvas = canvas;
DrawTeam(canvas, 40, playerBrush);
enemyTimer.Interval = TimeSpan.FromMilliseconds(100);
enemyTimer.Start();
}
private void DrawBall(SolidColorBrush brush, Canvas canvas,double x,double y)
{
enemy = new Ellipse();
enemy.Stroke = brush;
enemy.Fill = brush;
enemy.Height = 30;
enemy.Width = 30;
enemy.Margin = new Thickness(x,y, 0, 0);
enemyTimer = new DispatcherTimer();
enemyThickness = enemy.Margin;
canvas.Children.Add(enemy);
enemyTimer.Tick += enemyTimer_Tick;
}
void enemyTimer_Tick(object sender, EventArgs e)
{
if (enemyThickness.Left >= canvas.Width - 100)
{
GoDown();
direction = '1';
}
if (enemyThickness.Left <= 0 + 20)
{
GoDown();
direction = '0';
}
MoveTeam(enemy);
}
private void MoveTeam(Ellipse enemy)
{
enemyThickness = enemy.Margin;
if (direction == '1')
{
enemyThickness.Left -= xChange;
}
if (direction == '0')
{
enemyThickness.Left += xChange;
}
enemy.Margin = enemyThickness;
}
private void GoDown()
{
enemyThickness.Top += yChange;
enemy.Margin = enemyThickness;
}
}

Instead of initializing and assigning event handler in DrawBall method, do that in constructor of EnemyTeam class. This is will give you on timer per EnemyTeam object.

Declare enemyTimer as a static field:
class EnemyTeam
{
private static enemyTimer = new DispatcherTimer();
...
The keyword static will make the field shared for the class.

You're making multiple timers and throwing them away. See this line:
enemyTimer = new DispatcherTimer();
Every time you call that, you're making a new timer and throwing away the previous copy that enemyTimer held a reference to. Because enemyTimer.Start() is called after DrawTeam, it's called only on the last-created timer. None of the other timers get started.
But even if the other timers got started, you'd still only see one Ellipse move, because in enemyTimer_Tick you only ever make changes to enemy, which is a class member variable that points to the last Ellipse created.
I would suggest that you only use one timer, that you save all the Ellipses you create in a list for later use, and that in enemyTimer_Tick you update all of those Ellipses by iterating through the list.
EDIT: Here is a copy of your code, reworked a bit to show you what I mean. I don't really understand what you're trying to do with MoveTeam and the enemyThickness variable, so I didn't mess with that stuff. That is to say, this isn't a complete working solution, just an example of the changes I'm suggesting.
using System.Collections.Generic;
class EnemyTeam
{
private List<Ellipse> enemies = new List<Ellipse>();
private Canvas canvas;
private double xChange = 50, yChange = 50;
public DispatcherTimer enemyTimer;
private char direction = '0';
private Thickness enemyThickness;
public EnemyTeam(Canvas canvas, double startPosition, SolidColorBrush playerBrush)
{
this.canvas = canvas;
DrawTeam(canvas, 40, playerBrush);
enemyTimer = new DispatcherTimer();
enemyTimer.Interval = TimeSpan.FromMilliseconds(100);
enemyTimer.Tick += enemyTimer_Tick;
enemyTimer.Start();
}
private void DrawBall(SolidColorBrush brush, Canvas canvas,double x,double y)
{
enemy = new Ellipse();
enemy.Stroke = brush;
enemy.Fill = brush;
enemy.Height = 30;
enemy.Width = 30;
enemy.Margin = new Thickness(x,y, 0, 0);
enemyThickness = enemy.Margin; // what is this supposed to do?
canvas.Children.Add(enemy);
enemies.Add(enemy);
}
void enemyTimer_Tick(object sender, EventArgs e)
{
foreach (Ellipse enemy in enemies)
{
if (enemyThickness.Left >= canvas.Width - 100)
{
GoDown();
direction = '1';
}
if (enemyThickness.Left <= 0 + 20)
{
GoDown();
direction = '0';
}
MoveTeam(enemy);
}
}
private void MoveTeam(Ellipse enemy)
{
enemyThickness = enemy.Margin;
if (direction == '1')
{
enemyThickness.Left -= xChange;
}
if (direction == '0')
{
enemyThickness.Left += xChange;
}
enemy.Margin = enemyThickness;
}
private void GoDown()
{
enemyThickness.Top += yChange;
enemy.Margin = enemyThickness;
}
}

Related

How to make multiple bots follow the player?

I am learning C #, and I am creating a hypothetical game for me to understand the language. I want several bots to follow the Player who is moving the rectangle, but I can only move the player, but the automatic bots do not move.
I really researched what I could do to move these bots. And I came to the conclusion that I would have to understand Threads, which simply causes the program not to crash.
I leave here the full code of what I am trying.
public partial class Form1 : Form
{
public enum Direction { Up, Down, Left, Right }
private Player player;
private List<Bot> bots;
public Form1()
{
InitializeComponent();
this.Paint += Form1_Paint;
this.KeyPreview = true;
this.KeyDown += Form1_KeyDown;
this.player = new Player(new Size(8, 8));
this.bots = new List<Bot>();
for (int i = 0; i < 30; i++)
{
Bot bot = new Bot(player, new Size(8, 8));
bot.Follow();
this.bots.Add(bot);
}
}
private void Form1_KeyDown(object sender, KeyEventArgs e)
{
switch (e.KeyCode)
{
case Keys.Up:
player.Move(Direction.Up);
break;
case Keys.Down:
player.Move(Direction.Down);
break;
case Keys.Left:
player.Move(Direction.Left);
break;
case Keys.Right:
player.Move(Direction.Right);
break;
}
this.Invalidate();
}
private void Form1_Paint(object sender, PaintEventArgs e)
{
List<Rectangle> rs = new List<Rectangle>();
rs = this.bots.Select(x => x.Rectangle).ToList();
rs.Add(player.Rectangle);
if (rs.Count > 0)
{
e.Graphics.FillRectangles(new SolidBrush(Color.Red), rs.ToArray());
}
}
}
public class Player
{
private Rectangle rectangle;
public Rectangle Rectangle { get => rectangle; }
public Player(Size size)
{
this.rectangle = new Rectangle() { Size = size };
}
public void Move(Direction direction)
{
switch (direction)
{
case Direction.Up:
this.rectangle.Y -= 3;
break;
case Direction.Down:
this.rectangle.Y += 3;
break;
case Direction.Left:
this.rectangle.X -= 3;
break;
case Direction.Right:
this.rectangle.X += 3;
break;
default:
break;
}
}
}
public class Bot
{
private Rectangle rectangle;
private Player player;
public Rectangle Rectangle { get => rectangle; }
public Bot(Player player, Size size)
{
this.player = player;
this.rectangle = new Rectangle() { Size = size };
}
public void Follow()
{
Task.Run(() =>
{
while (true)
{
Point p = player.Rectangle.Location;
Point bot = rectangle.Location;
for (int i = bot.X; i < p.X; i += 2)
{
Thread.Sleep(100);
bot.X = i;
}
for (int i = bot.X; i > p.X; i -= 2)
{
Thread.Sleep(100);
bot.X = i;
}
for (int i = bot.Y; i < p.Y; i += 2)
{
Thread.Sleep(100);
bot.Y = i;
}
for (int i = bot.Y; i > p.Y; i -= 2)
{
Thread.Sleep(100);
bot.Y = i;
}
}
});
}
}
As you can see, I can only move the player, but the bots don't move what can I do to move the bots?
I think a Timer would work better here and remove the requirement for you to fully understanding threading at this point, as it will handle the details for you. I'm assuming you actually want the bots to "follow" instead of only moving when the Player moves and will fall behind if the player is moving quickly.
So to use a Timer, I would adjust your Bot class as below, to remove your usage of threads and only allow it to take a single step towards the player in the Follow method which will be called every 100ms. Note Rectangle is a struct, so it is not mutable - that is why your bots do not move - if you do the following:
Point bot = Rectangle.Location;
bot.X = 5;
You're probably thinking Rectangle.Location.X is now 5; but it is not. So we create a new rectangle using the new position.
public class Bot
{
private Player player;
public Rectangle Rectangle { get; set; }
public Bot(Player player, Size size)
{
this.player = player;
this.Rectangle = new Rectangle() { Size = size };
}
public void Follow()
{
Point p = player.Rectangle.Location;
Point bot = Rectangle.Location;
for (int i = bot.X + 2; i < p.X;)
{
bot.X = i;
break;
}
for (int i = bot.X - 2; i > p.X;)
{
bot.X = i;
break;
}
for (int i = bot.Y + 2; i < p.Y;)
{
bot.Y = i;
break;
}
for (int i = bot.Y - 2; i > p.Y;)
{
bot.Y = i;
break;
}
Rectangle = new Rectangle(bot, player.Rectangle.Size);
}
}
And add the following code to replace your existing constructor and add another method to handle the Timer tick.
private Timer timer;
public Form1()
{
InitializeComponent();
this.Paint += Form1_Paint;
this.KeyPreview = true;
this.KeyDown += Form1_KeyDown;
// setup a timer which will call Timer_Tick every 100ms
timer = new System.Windows.Forms.Timer();
timer.Interval = 100;
timer.Tick += Timer_Tick;
timer.Start();
this.player = new Player(new Size(8, 8));
this.bots = new List<Bot>();
for (int i = 0; i < 30; i++)
{
Bot bot = new Bot(player, new Size(8, 8));
bot.Follow();
this.bots.Add(bot);
}
}
private void Timer_Tick(object sender, System.EventArgs e)
{
foreach (var bot in bots)
bot.Follow();
this.Invalidate();
}
Point is a value type (a struct). (Read more about this at What's the difference between struct and class in .NET?)
When you did this:
Point bot = Rectangle.Location;
bot.X = i;
...you created a local Point and modified it. This doesn't change the Location of the Rectangle of the Bot. Also, Rectangles are structs too, so you have to modify the original Bot's Rectangle, or assign a new Rectangle to the Bot.
To fix, you could replace:
bot.X = i;
...with...
this.rectangle.X = i;
And make the similar change for .Y (in all your for loop locations)
Spelling it all out:
public void Follow()
{
Task.Run(() =>
{
while (true) {
Point p = player.Rectangle.Location;
Point bot = rectangle.Location;
for (int i = bot.X; i < p.X; i += 2) {
Thread.Sleep(100);
this.rectangle.X = i;
}
for (int i = bot.X; i > p.X; i -= 2) {
Thread.Sleep(100);
this.rectangle.X = i;
}
for (int i = bot.Y; i < p.Y; i += 2) {
Thread.Sleep(100);
this.rectangle.Y = i;
}
for (int i = bot.Y; i > p.Y; i -= 2) {
Thread.Sleep(100);
this.rectangle.Y = i;
}
}
});
}

UWP app .cs file inheritance static variable from xaml.cs

I have created a PlayPage.xaml, PlayPage.xaml.cs and Game.cs file.
The PlayPage.xaml.cs has two variable, windowWidth and windowHeight.
I would like access two public static variable from Game.cs.
Game.cs:
namespace UwpApp
{
class Game
{
static Rectangle rectangle;
PlayPage pg = new PlayPage();
//Create a rectangle
public Rectangle draw()
{
rectangle = new Rectangle();
rectangle.Width = 70;
rectangle.Height = 70;
rectangle.Fill = new SolidColorBrush(Colors.Green);
Canvas.SetLeft(rectangle, randPos());
Canvas.SetTop(rectangle, randPos());
return rectangle;
}
//Create a random X and Y position
private Int32 randPos()
{
Random rnd = new Random();
Debug.WriteLine(pg.windowWidth);
return rnd.Next(0 , (int)pg.windowWidth);
}
}
}
PlayPage.xaml.cs:
namespace UwpApp
{
/// <summary>
/// An empty page that can be used on its own or navigated to within a Frame.
/// </summary>
public partial class PlayPage : Page
{
DispatcherTimer timer;
Rectangle rect;
bool isTapped;
public static double windowWidth, windowHeight;
Game game = new Game();
public PlayPage()
{
this.InitializeComponent();
startCounter.Visibility = Visibility.Collapsed;
isTapped = false;
}
private void Load_Variable(object sender, RoutedEventArgs e)
{
windowWidth = canvas.ActualWidth;
windowHeight = canvas.ActualHeight;
}
//Counter animation. (Number opacity, fall)
private void counterAnimation()
{
startCounter.Visibility = Visibility.Visible;
//Set Counter Horizontal Align
double left = (canvas.ActualWidth - startCounter.ActualWidth) / 2;
Canvas.SetLeft(startCounter, left);
Storyboard storyboard = new Storyboard();
DoubleAnimation opacityAnim = new DoubleAnimation();
DoubleAnimation fallAnim = new DoubleAnimation();
opacityAnim.From = 1;
opacityAnim.To = 0;
opacityAnim.Duration = new Duration(TimeSpan.FromSeconds(1));
opacityAnim.AutoReverse = false;
opacityAnim.RepeatBehavior = new RepeatBehavior(3);
Storyboard.SetTarget(opacityAnim, this.startCounter);
Storyboard.SetTargetProperty(opacityAnim, "(UIElement.Opacity)");
fallAnim.From = -115;
fallAnim.To = canvas.ActualHeight / 2;
fallAnim.Duration = new Duration(TimeSpan.FromSeconds(1));
fallAnim.AutoReverse = false;
fallAnim.RepeatBehavior = new RepeatBehavior(3);
Storyboard.SetTarget(fallAnim, this.startCounter);
Storyboard.SetTargetProperty(fallAnim, "(Canvas.Top)");
storyboard.Children.Add(opacityAnim);
storyboard.Children.Add(fallAnim);
storyboard.Begin();
}
//Countdown Timer
private void countDown()
{
timer = new DispatcherTimer();
timer.Tick += startCounter_CountDown;
timer.Interval = new TimeSpan(0, 0, 1);
timer.Start();
}
//Change Countdown value
private void startCounter_CountDown(object sender, object e)
{
int counterNum = int.Parse(startCounter.Text);
counterNum -= 1;
startCounter.Text = counterNum.ToString();
if (counterNum == 1)
{
timer.Stop();
StartedGame();
}
}
//Tap or Click to start the game
private void TapToStart(object sender, TappedRoutedEventArgs e)
{
if(!isTapped)
{
isTapped = true;
counterAnimation();
countDown();
this.TapToStartText.Visibility = Visibility.Collapsed;
}
}
//Create rectangles
private void StartedGame()
{
rect = game.draw();
canvas.Children.Add(game.draw());
Debug.WriteLine(windowWidth.ToString());
}
}
}
One more thing: I get an error this line: PlayPage pg = new PlayPage();
Error (pic)
The error in your picture is due to infinite recursion, as it says. The constructor for Game instantiates a new PlayPage. The constructor for PlayPage instantiates a new Game. Which instantiates a new PlayPage. Which instantiates a new Game. and on and on.
Static members are accessed by class name, not by instance. Like so:
PlayPage.windowWidth

How to fade in and fade out (Fading transition ) image on panel(backgroud image)?

I'm sending to my method different images and I want insert some effect to this change.
How can I fade in and fade out images?
private void ShowImage(Image image, ImageLayout imageLayout, int numberOfSeconds)
{
try
{
if (this.image_timer != null)
this.KillImageTimer();
this.customer_form.DisplayImage(image, imageLayout);
this.image_timer = new Timer();
this.image_timer.Tick += (object s, EventArgs a) => NextImage();
this.image_timer.Interval = numberOfSeconds* 1000;
this.image_timer.Start();
}
catch
{
//Do nothing
}
public void DisplayImage(Image image, ImageLayout imageLayout)
{
panel1.BackgroundImage = image;
panel1.BackgroundImageLayout = imageLayout;
}
There are no built-in fading transitions in Winforms.
So you will need to write one yourself.
The simplest one I can think of uses a second Panel, that is layered upon the first one and in fact needs to be inside the first Panel or else the transparency effect won't work..
Here is the setup, using two Panels:
public Form1()
{
InitializeComponent();
pan_image.BackgroundImage = someImage;
pan_layer.Parent = pan_image;
pan_layer.BackColor = pan_image.BackColor;
pan_layer.Size = pan_image.Size;
pan_layer.Location = Point.Empty;
}
For the fading animation I use a Timer. This is a quick code example:
Timer timer1 = new Timer();
int counter = 0;
int dir = 1; // direction 1 = fade-in..
int secondsToWait = 5;
int speed1 = 25; // tick speed ms
int speed2 = 4; // alpha (0-255) change speed
void timer1_Tick(object sender, EventArgs e)
{
// we have just waited and now we fade-out:
if (dir == 0)
{
timer1.Stop();
dir = -speed2;
counter = 254;
timer1.Interval = speed2;
timer1.Start();
}
// the next alpha value:
int alpha = Math.Min(Math.Max(0, counter+= dir), 255);
button1.Text = dir > 0 ? "Fade In" : "Fade Out";
// fully faded-in: set up the long wait:
if (counter >= 255)
{
timer1.Stop();
button1.Text = "Wait";
timer1.Interval = secondsToWait * 1000;
dir = 0;
timer1.Start();
}
// fully faded-out: try to load a new image and set direction to fade-in or stop
else if (counter <= 0)
{
if ( !changeImage() )
{
timer1.Stop();
button1.Text = "Done";
}
dir = speed2;
}
// create the new, semi-transparent color:
Color col = Color.FromArgb(255 - alpha, pan_image.BackColor);
// display the layer:
pan_layer.BackColor = col;
pan_layer.Refresh();
}
I start it in a Button, on which I also show the current state:
private void button1_Click(object sender, EventArgs e)
{
dir = speed2;
timer1.Tick += timer1_Tick;
timer1.Interval = speed1;
timer1.Start();
}
As you can see I use two speeds you can set: One to control the speed of the Timer and one to control the steps by which the transparency changes on each Tick.
The effect is created by simply changing the Color from the BackgroundColor of the image Panel to fully transparent and back, waiting in between for a specified number of seconds.
And the end of the effect I call a function changeImage() to change the images. If this function returns false the Timer is stopped for good..
I'm pretty sure this could be written in a cleaner and more elegant way, but as it is it seems to work..
Update
for flicker-free display use a double-buffered control, like this Panel subclass:
class DrawPanel : Panel
{
public DrawPanel() { DoubleBuffered = true; }
}
Here is a sample implementation for changeImage:
bool changeImage()
{
if (pan_image.BackgroundImage != null)
{
var img = pan_image.BackgroundImage;
pan_image.BackgroundImage = null;
img.Dispose();
}
pan_image.BackgroundImage = Image.FromFile(imageFiles[index++]);
return index < imageFiles.Count;
}
It assumes two class level variables: a List<string> imageFiles filled with file names of images for a slide-show and an int index = 0.

Iterating through an array and play notes

I have an array which is populated by MusicNotes. Each MusicNote is an object with it's properties, e.g. pitch and duration. Duration is created using a timer in the MusicNote class.
The problem is that when I iterate through the array and play all the sounds the duration of each MusicNote is lost and it will play the whole wav file (for each note).
I know that the problem is related to the timer and I know that it maybe related to the Play() method in the MusicNote but I don't have any ideas on how to fix it. I have posted my the code related to this problem.
public class MusicNote : PictureBox
{
Timer tmr1 = new Timer();
int tmr1duration;
public SoundPlayer sp = new SoundPlayer();
public Timer tmr = new Timer();
public int pitch; //The no. of the music key (e.g. the sound freuency).
public int noteDuration; //Shape of note.
public string noteShape;
static int xLoc = 0;
int yLoc = 100;
public MusicNote(int iPitch, int iNoteDuration)
: base()
{
pitch = iPitch;
noteDuration = iNoteDuration;
Size = new Size(40, 40);
this.BackColor = Color.Transparent;
this.MouseClick += new MouseEventHandler(MusicNote_MouseClick);
this.MouseDown += new MouseEventHandler(MusicNote_MouseDown);
this.MouseUp += new MouseEventHandler(MusicNote_MouseUp);
tmr1.Tick += new EventHandler(tmr1_Tick);
tmr.Tick += new EventHandler(ClockTick);
}
public void ShowNote()
{
if (this.noteDuration == 1) noteShape = "Quaver.png";
if (this.noteDuration == 4) noteShape = "Crotchet.png";
if (this.noteDuration == 7) noteShape = "minim.png";
if (this.noteDuration == 10) noteShape = "DotMin.png";
if (this.noteDuration == 12) noteShape = "SemiBreve.png";
this.BackgroundImage = Image.FromFile(noteShape);
this.BackColor = Color.Transparent;
Location = new Point(xLoc, yLoc);
xLoc = xLoc + 40;
}
protected override void OnPaint(PaintEventArgs pe)
{
base.OnPaint(pe);
}
public void Play()
{
sp.SoundLocation = this.pitch + ".wav";
sp.Play();
//Timer to play the duration
this.tmr.Interval = 100 * this.noteDuration;
this.tmr.Start();
}
void ClockTick(object sender, EventArgs e)
{
sp.Stop();
tmr.Stop();
}
private void MusicNote_MouseClick(object sender, MouseEventArgs e)
{
if (e.Button == MouseButtons.Left)
{
Play();
}
}
}
}
And this is the class were I have the array...
public class MusicStaff: Panel
{
public ArrayList musicNotes = new ArrayList(); //Array to store the Music Notes.
SoundPlayer sp = new SoundPlayer();
public void AddNote(MusicNote newNote) //Method to add the notes.
{
musicNotes.Add(newNote);
}
public int ListSize()
{
return musicNotes.Count; //Returns the size of the list.
}
public void PlayAll()
{
foreach (MusicNote m in musicNotes)
{
m.Play();
}
I have removed some code from the classes which is not replated to the problem so that question is not too long. Any help how can I solve this would be greatly appreciated. Tks.
Try something like this:
public void PlayAll()
{
foreach (MusicNote m in musicNotes)
{
m.sp.Stop();
m.sp.PlaySync();
Thread.Sleep(m.noteDuration); //duration should be in milliseconds
}
}
Should this work you can remove your timer completely.
I suggest you look into the use of Properties in C# to not let fields be public.
By the way I did this assignment two years ago :)

i created a modified pacman, how to make him breath fire?

I created a modified Pacman, but I want to add a firebolt shooting out from the mouth of the Pacman. My code is:
namespace TestingPacman
{
class Firebolt
{
Bitmap firebolt0 = null;
Bitmap firebolt1 = null;
public Point fireboltposition;
int fireboltwidth = 0;
int fireboltheight = 0;
public Firebolt(int x, int y)
{
fireboltposition.X = x;
fireboltposition.Y = y;
if (firebolt0 == null)
firebolt0 = new Bitmap("firebolt0.gif");
if (firebolt1 == null)
firebolt1 = new Bitmap("firebolt1.gif");
int fireboltwidth = firebolt0.Width;
int fireboltheight = firebolt0.Height;
}
public Rectangle GetFrame()
{
Rectangle Labelrec = new Rectangle(fireboltposition.X, fireboltposition.Y, fireboltwidth, fireboltheight);
return Labelrec;
}
public void Draw(Graphics g)
{
Rectangle fireboltdecR = new Rectangle(fireboltposition.X, fireboltposition.Y, fireboltwidth, fireboltheight);
Rectangle fireboltsecR = new Rectangle(0, 0, fireboltwidth, fireboltheight);
g.DrawImage(firebolt0, fireboltdecR, fireboltsecR, GraphicsUnit.Pixel);
}
}
How can I make a firebolt move in the direction the pacman is facing?
I have a form1 that when I press "F" it will fire a firebolt
but it cant seem to produce the firebolt image. Why is that?
namespace TestingPacman
{
public partial class Form1 : Form
{
// int inc = 0;
Eater TheEater = new Eater(100,100);
TimeDisplay time = new TimeDisplay();
int sec = 0;
Score score = new Score();
int countofeaten=0;
Random r = new Random();
private List<Label> redlabels = new List<Label>();
private List<Label> bluelabels = new List<Label>();
Firebolt firebolt;
List<Firebolt> listfirebolt = new List<Firebolt>();
private void Form1_Paint(object sender, PaintEventArgs e)
{
Graphics g = e.Graphics;
g.FillRectangle(Brushes.White, 0, 0, this.ClientRectangle.Width, ClientRectangle.Height);
TheEater.Draw(g);
foreach(Firebolt f in listfirebolt)
f.Draw(g);
}
private void Form1_KeyDown(object sender, KeyEventArgs e)
{
timer1.Enabled = true;
string result = e.KeyData.ToString();
Invalidate(TheEater.GetFrame());
switch (result)
{
case "D1":
if (TheEater.eaterwidth >= 9 && TheEater.eaterheight >= 9)
{
TheEater.eaterwidth++;
TheEater.eaterheight++;
}
break;
case "F":
listfirebolt.Add(firebolt = new Firebolt(TheEater.Position.X, TheEater.Position.Y));
Invalidate(firebolt.GetFrame());
break;
case "D2":
if (TheEater.eaterwidth > 10 && TheEater.eaterheight > 10)
{
TheEater.eaterwidth--;
TheEater.eaterheight--;
}
break;
case "D9": TheEater.inc=TheEater.inc+2;
break;
case "D0": TheEater.inc=TheEater.inc-2;
break;
case "Left":
TheEater.MoveLeft(ClientRectangle);
Invalidate(TheEater.GetFrame());
break;
case "Right":
TheEater.MoveRight(ClientRectangle);
Invalidate(TheEater.GetFrame());
break;
case "Up":
TheEater.MoveUp(ClientRectangle);
Invalidate(TheEater.GetFrame());
break;
case "Down":
TheEater.MoveDown(ClientRectangle);
Invalidate(TheEater.GetFrame());
break;
default:
break;
}
RemoveifIntersected();
}
label2.Text = score.Iskore.ToString();
}
private void timer1_Tick(object sender, EventArgs e)
{
label1.Text = time.FormatTime(sec++);
}
}
}
Jeo, what you are missing in your code is the concept of "Time" as far as I can tell your game only reacts when you press keys. What you really need is a mechanism to pass time in your game. This is almost always done in games with repetitive calls to something called "A Game Loop". Here's a quick example of a game loop that might work for you
class Mob
{
float XPos;
float YPos;
float XVel;
float YVel;
}
List<Mob> EveryThingMovable = new List<Mob>();
void GameLoop() //This loop is called 30 times every second... use a timer or whatever, there are far more sophisticated models, but for a first attaempt at a game it's easiest.
{
MoveEverybody(); //make a function that moves everything that can move
//Later you will have to add collision detection to stop pacman from moving through walls
CollideFireballs(); //Check if a fireball hits the bad guys
//More game stuff...
}
void MoveEverybody()
{
foreach(Mob dude in EverythingMovable)
{
ifDoesntHitWall(dude)
{
dude.XPos += dude.XVel;
dude.YPos += dude.YVel;
}
}
}
anyways, read up on the idea of a Game Loop, I think it's the biggest hurtle you haven't passed in order to move ahead.

Categories

Resources