How to draw a rectangle that could move to the edge of the PictureBox and when it reached the edge, it would unfold. And there could be several such rectangles
Here is the code of the class with the Draw function (Pike.cs):
using System.Drawing;
namespace course_project
{
internal class Pike : Fish
{
private Point coordinates;
private Size size = new Size(40, 40);
private Size speed;
public Pike(Point data, AquariumForm aquariumForm) : base(Color.Green, aquariumForm)
{
Data = data;
speed = new Size();
}
public Pike Next { get; set; }
public override void Draw(Graphics graphics)
{
graphics.FillEllipse(brush, coordinates.X, coordinates.Y, size.Width, size.Height);
}
public void UpdateLocation(Rectangle bounds)
{
if (!bounds.Contains(coordinates + speed))
{
if (coordinates.X + speed.Width < bounds.Left || coordinates.X + speed.Width > bounds.Right - size.Width)
{
speed.Width *= -1;
}
if (coordinates.Y + speed.Height < bounds.Top || coordinates.Y + speed.Height > bounds.Bottom - size.Height)
{
speed.Height *= -1;
}
}
coordinates += speed;
}
}
}
Linked List (PikeFlock.cs):
using System.Collections;
using System.Collections.Generic;
using System.Drawing;
namespace course_project
{
internal class PikeFlock : IEnumerable<Pike>
{
Pike head;
Pike tail;
int count;
public void Add(Point data, AquariumForm aquariumForm)
{
Pike pike = new Pike(data, aquariumForm);
if (head == null)
head = pike;
else
tail.Next = pike;
tail = pike;
count++;
}
public bool Remove(Point data)
{
Pike current = head;
Pike previous = null;
while (current != null)
{
if (current.Data.Equals(data))
{
if (previous != null)
{
previous.Next = current.Next;
if (current.Next == null)
{
tail = previous;
}
}
else
{
head = head.Next;
if (head == null)
tail = null;
}
count--;
return true;
}
previous = current;
current = current.Next;
}
return false;
}
public int Count { get { return count; } }
public bool IsEmpty { get { return count == 0; } }
public void Clear()
{
head = null;
tail = null;
count = 0;
}
public bool Contains(Point data)
{
Pike current = head;
while (current != null)
{
if (current.Data.Equals(data))
return true;
current = current.Next;
}
return false;
}
public void AppendFirst(Point data, AquariumForm aquariumForm)
{
Pike pike = new Pike(data, aquariumForm)
{
Next = head
};
head = pike;
if (count == 0)
{
tail = head;
}
count++;
}
public IEnumerator<Pike> GetEnumerator()
{
Pike current = head;
while (current != null)
{
yield return current;
current = current.Next;
}
}
IEnumerator IEnumerable.GetEnumerator()
{
return ((IEnumerable)this).GetEnumerator();
}
}
}
AquariumForm.cs (The form itself):
using System;
using System.Drawing;
using System.Windows.Forms;
namespace course_project
{
public partial class AquariumForm : Form
{
readonly Aquarium aquarium;
public AquariumForm()
{
InitializeComponent();
DoubleBuffered = true;
aquarium = new Aquarium(ClientRectangle);
aquarium_timer.Interval = 100;
aquarium_timer.Tick += Timer_Tick;
aquarium_timer.Enabled = true;
}
private void Timer_Tick(object sender, EventArgs e)
{
foreach (Pike pike in aquarium.pikeFlock)
{
pike.UpdateLocation(ClientRectangle);
}
foreach (Carp carp in aquarium.carpFlock)
{
carp.UpdateLocation(ClientRectangle);
}
Invalidate();
}
private void Add_carp_button_Click(object sender, EventArgs e)
{
aquarium.carpFlock.Add(new Point(), this);
}
private void Add_pike_button_Click(object sender, EventArgs e)
{
aquarium.pikeFlock.Add(new Point(), this);
}
protected override void OnPaint(PaintEventArgs e)
{
base.OnPaint(e);
aquarium.Paint(e.Graphics);
}
}
}
Aquarium.cs:
using System.Drawing;
namespace course_project
{
internal class Aquarium
{
readonly public PikeFlock pikeFlock;
readonly public CarpFlock carpFlock;
readonly Color waterColor;
public Aquarium(Rectangle clientRectangle)
{
waterColor = Color.LightSkyBlue;
pikeFlock = new PikeFlock();
carpFlock = new CarpFlock();
}
public void Paint(Graphics graphics)
{
graphics.Clear(waterColor);
foreach (Pike pike in pikeFlock)
pike.Draw(graphics);
foreach (Carp carp in carpFlock)
carp.Draw(graphics);
}
}
}
Fish.cs
using System.Drawing;
namespace course_project
{
internal class Fish
{
private protected Brush brush;
private protected AquariumForm aquarium_form;
public Fish(Color color, AquariumForm aquariumForm)
{
aquarium_form = aquariumForm;
brush = new SolidBrush(color);
}
public virtual void Draw(Graphics graphics) { }
public Point Data { get; set; }
}
}
Confused just at the point where you need to animate it all. By clicking the button everything is created as it should be, but animation does not work, even I do not know how :(