From feac50420c81c15d58bae6b0128af2f1c391e74a Mon Sep 17 00:00:00 2001 From: dyakonovr Date: Tue, 3 Oct 2023 13:32:33 +0400 Subject: [PATCH] All done --- ProjectTank/DrawingTank.cs | 147 ------------------ ProjectTank/DrawningObjects/DrawningTank.cs | 63 ++++++++ .../DrawningObjects/DrawningTankBase.cs | 127 +++++++++++++++ ProjectTank/Entities/EntityTank.cs | 23 +++ ProjectTank/Entities/EntityTankBase.cs | 22 +++ ProjectTank/FormTank.Designer.cs | 48 +++++- ProjectTank/FormTank.cs | 75 ++++++--- .../MovementStrategy/AbstractStrategy.cs | 129 +++++++++++++++ .../MovementStrategy/DrawningObjectTank.cs | 31 ++++ .../MovementStrategy/IMoveableObject.cs | 33 ++++ ProjectTank/MovementStrategy/MoveToCenter.cs | 40 +++++ .../MoveToRightBottomCorner.cs | 40 +++++ .../MovementStrategy/ObjectParameters.cs | 56 +++++++ ProjectTank/MovementStrategy/Status.cs | 15 ++ ProjectTank/TankEntity.cs | 28 ---- 15 files changed, 679 insertions(+), 198 deletions(-) delete mode 100644 ProjectTank/DrawingTank.cs create mode 100644 ProjectTank/DrawningObjects/DrawningTank.cs create mode 100644 ProjectTank/DrawningObjects/DrawningTankBase.cs create mode 100644 ProjectTank/Entities/EntityTank.cs create mode 100644 ProjectTank/Entities/EntityTankBase.cs create mode 100644 ProjectTank/MovementStrategy/AbstractStrategy.cs create mode 100644 ProjectTank/MovementStrategy/DrawningObjectTank.cs create mode 100644 ProjectTank/MovementStrategy/IMoveableObject.cs create mode 100644 ProjectTank/MovementStrategy/MoveToCenter.cs create mode 100644 ProjectTank/MovementStrategy/MoveToRightBottomCorner.cs create mode 100644 ProjectTank/MovementStrategy/ObjectParameters.cs create mode 100644 ProjectTank/MovementStrategy/Status.cs delete mode 100644 ProjectTank/TankEntity.cs diff --git a/ProjectTank/DrawingTank.cs b/ProjectTank/DrawingTank.cs deleted file mode 100644 index 7cd3162..0000000 --- a/ProjectTank/DrawingTank.cs +++ /dev/null @@ -1,147 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Drawing.Drawing2D; -using System.IO; -using System.Linq; -using System.Text; -using System.Threading.Tasks; - -namespace ProjectTank -{ - internal class DrawingTank - { - public Tank? TankEntity { get; private set; } - private int pictureWidth; - private int pictureHeight; - private int startPosX; - private int startPosY; - private readonly int tankWidth = 150; - private readonly int tankHeight = 100; - public bool Init(int speed, double weight, Color bodyColor, Color additionalColor, int width, int height, bool isAntiAircraftGun, bool isTankTower) - { - if (width <= tankWidth || height <= tankHeight) return false; - pictureWidth = width; - pictureHeight = height; - TankEntity = new Tank(); - TankEntity.Init(speed, weight, bodyColor, additionalColor, isAntiAircraftGun, isTankTower); - return true; - } - public void SetPosition(int x, int y) - { - if (TankEntity == null) return; - startPosX = x; - startPosX = y; - - if (x + tankWidth >= pictureWidth || y + tankHeight >= pictureHeight) - { - startPosX = 1; - startPosY = 1; - } - } - public void MoveTransport(DirectionType direction) - { - if (TankEntity == null) return; - - switch (direction) - { - //влево - case DirectionType.Left: - if (startPosX - TankEntity.Step > 0) - { - startPosX -= (int)TankEntity.Step; - } - break; - //вверх - case DirectionType.Up: - if (startPosY - TankEntity.Step > 0) - { - startPosY -= (int)TankEntity.Step; - } - break; - // вправо - case DirectionType.Right: - if (startPosX + TankEntity.Step + tankWidth <= pictureWidth) - { - startPosX += (int)TankEntity.Step; - } - break; - //вниз - case DirectionType.Down: - if (startPosY + TankEntity.Step + tankHeight <= pictureHeight) - { - startPosY += (int)TankEntity.Step; - } - break; - } - } - public void DrawTransport(Graphics g) - { - if (TankEntity == null) return; - - Pen pen = new(TankEntity.BodyColor); - - // границы - g.DrawRectangle(new Pen(Color.Red), startPosX, startPosY, tankWidth, tankHeight); - - // гусеница - GraphicsPath path = new GraphicsPath(); - - int cornerRadius = 20; - - path.AddArc(startPosX, startPosY + 65, cornerRadius, cornerRadius, 180, 90); - path.AddArc(startPosX + tankWidth - cornerRadius, startPosY + 65, cornerRadius, cornerRadius, 270, 90); - path.AddArc(startPosX + tankWidth - cornerRadius, startPosY + tankHeight - cornerRadius, cornerRadius, cornerRadius, 0, 90); - path.AddArc(startPosX, startPosY + tankHeight - cornerRadius, cornerRadius, cornerRadius, 90, 90); - - path.CloseFigure(); - g.DrawPath(pen, path); - - // колеса - g.DrawEllipse(pen, startPosX + 1, startPosY + tankHeight - 5 - 25, 25, 25); - for (int i = 1; i < 5; i++) - { - g.DrawEllipse(pen, startPosX + 30 + (5 * i) + (15 * (i - 1)), startPosY + tankHeight - 5 - 15, 15, 15); - } - g.DrawEllipse(pen, startPosX + tankWidth - 25 - 1, startPosY + tankHeight - 5 - 25, 25, 25); - - if (TankEntity.IsTankMuzzle) - { - // дуло - g.DrawRectangle(pen, startPosX + 15, startPosY + 37, 30, 7); - } - - // башня - SolidBrush brush = new SolidBrush(TankEntity.AdditionalColor); - g.FillRectangle(brush, startPosX + 45, startPosY + 30, 60, 25); - - g.FillRectangle(brush, startPosX + 5, startPosY + 55 + 1, tankWidth - 10, 9); - - if (TankEntity.IsAntiAircraftGun) - { - // зенитное орудие - g.DrawRectangle(pen, startPosX + 65, startPosY + 18, 8, 12); - g.DrawRectangle(pen, startPosX + 65 + 8, startPosY + 16, 8, 14); - - Point[] leftRectanglePoints = - { - new Point(startPosX + 52, startPosY + 5), - new Point(startPosX + 67, startPosY + 18), - new Point(startPosX + 67 + 5, startPosY + 18), - new Point(startPosX + 57, startPosY + 5), - }; - - g.DrawPolygon(pen, leftRectanglePoints); - - Point[] rightRectanglePoints = - { - new Point(startPosX + 59, startPosY), - new Point(startPosX + 74, startPosY + 16), - new Point(startPosX + 74 + 5, startPosY + 16), - new Point(startPosX + 66, startPosY), - }; - - g.DrawPolygon(pen, rightRectanglePoints); - } - } - } -} \ No newline at end of file diff --git a/ProjectTank/DrawningObjects/DrawningTank.cs b/ProjectTank/DrawningObjects/DrawningTank.cs new file mode 100644 index 0000000..ad4e86e --- /dev/null +++ b/ProjectTank/DrawningObjects/DrawningTank.cs @@ -0,0 +1,63 @@ +using ProjectTank.Entities; +using System; +using System.Collections.Generic; +using System.Drawing.Drawing2D; +using System.IO; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace ProjectTank.DrawningObjects +{ + public class DrawningTank : DrawningTankBase + { + public DrawningTank(int speed, int weight, Color bodyColor, Color additionalColor, bool isTankTower, bool isAntiAirforceGun, int width, int height) : base(speed, weight, bodyColor, width, height) + { + if (EntityTankBase == null) return; + + EntityTankBase = new EntityTank(speed, weight, bodyColor, additionalColor, isTankTower, isAntiAirforceGun); + } + + public override void DrawTransport(Graphics g) + { + if (EntityTankBase is not EntityTank tank) return; + + Pen pen = new(tank.BodyColor); + + if (tank.TankTower) + { + // дуло + g.DrawRectangle(pen, startPosX + 15, startPosY + 37, 30, 7); + } + + base.DrawTransport(g); + + if (tank.AntiAirforceGun) + { + // зенитное орудие + g.DrawRectangle(pen, startPosX + 65, startPosY + 18, 8, 12); + g.DrawRectangle(pen, startPosX + 65 + 8, startPosY + 16, 8, 14); + + Point[] leftRectanglePoints = + { + new Point(startPosX + 52, startPosY + 5), + new Point(startPosX + 67, startPosY + 18), + new Point(startPosX + 67 + 5, startPosY + 18), + new Point(startPosX + 57, startPosY + 5), + }; + + g.DrawPolygon(pen, leftRectanglePoints); + + Point[] rightRectanglePoints = + { + new Point(startPosX + 59, startPosY), + new Point(startPosX + 74, startPosY + 16), + new Point(startPosX + 74 + 5, startPosY + 16), + new Point(startPosX + 66, startPosY), + }; + + g.DrawPolygon(pen, rightRectanglePoints); + } + } + } +} \ No newline at end of file diff --git a/ProjectTank/DrawningObjects/DrawningTankBase.cs b/ProjectTank/DrawningObjects/DrawningTankBase.cs new file mode 100644 index 0000000..6cf9ae9 --- /dev/null +++ b/ProjectTank/DrawningObjects/DrawningTankBase.cs @@ -0,0 +1,127 @@ +using ProjectTank.Entities; +using System; +using System.Collections.Generic; +using System.Drawing.Drawing2D; +using System.IO; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace ProjectTank.DrawningObjects +{ + public class DrawningTankBase + { + public EntityTankBase? EntityTankBase { get; protected set; } + private int pictureWidth; + private int pictureHeight; + protected int startPosX; + protected int startPosY; + protected readonly int tankWidth = 150; + protected readonly int tankHeight = 100; + + public int GetPosX => startPosX; + public int GetPosY => startPosY; + public int GetWidth => tankWidth; + public int GetHeight => tankHeight; + public DrawningTankBase(int speed, int weight, Color bodyColor, int width, int height) + { + if (width <= tankWidth || height <= tankHeight) return; + + pictureWidth = width; + pictureHeight = height; + EntityTankBase = new EntityTankBase(speed, weight, bodyColor); + } + protected DrawningTankBase(int speed, int weight, Color bodyColor, int width, int height, int _tankWidth, int _tankHeight) + { + if (width <= tankWidth || height <= tankHeight) return; + + pictureWidth = width; + pictureHeight = height; + tankWidth = _tankWidth; + tankHeight = _tankHeight; + EntityTankBase = new EntityTankBase(speed, weight, bodyColor); + } + public bool CanMove(DirectionType direction) + { + if (EntityTankBase == null) return false; + + return direction switch + { + DirectionType.Left => startPosX - EntityTankBase.Step > 0, + DirectionType.Up => startPosY - EntityTankBase.Step > 0, + DirectionType.Right => startPosX + tankWidth + EntityTankBase.Step < pictureWidth, + DirectionType.Down => startPosY + tankHeight + EntityTankBase.Step < pictureHeight, + _ => false, + }; + } + public void SetPosition(int x, int y) + { + if (EntityTankBase == null) return; + startPosX = x; + startPosX = y; + + if (x + tankWidth >= pictureWidth || y + tankHeight >= pictureHeight) + { + startPosX = 1; + startPosY = 1; + } + } + public void MoveTransport(DirectionType direction) + { + if (!CanMove(direction) || EntityTankBase == null) return; + + switch (direction) + { + //влево + case DirectionType.Left: + startPosX -= (int)EntityTankBase.Step; + break; + //вверх + case DirectionType.Up: + startPosY -= (int)EntityTankBase.Step; + break; + // вправо + case DirectionType.Right: + startPosX += (int)EntityTankBase.Step; + break; + //вниз + case DirectionType.Down: + startPosY += (int)EntityTankBase.Step; + break; + } + } + public virtual void DrawTransport(Graphics g) + { + if (EntityTankBase == null) return; + + Pen pen = new(EntityTankBase.BodyColor); + + // гусеница + GraphicsPath path = new GraphicsPath(); + + int cornerRadius = 20; + + path.AddArc(startPosX, startPosY + 65, cornerRadius, cornerRadius, 180, 90); + path.AddArc(startPosX + tankWidth - cornerRadius, startPosY + 65, cornerRadius, cornerRadius, 270, 90); + path.AddArc(startPosX + tankWidth - cornerRadius, startPosY + tankHeight - cornerRadius, cornerRadius, cornerRadius, 0, 90); + path.AddArc(startPosX, startPosY + tankHeight - cornerRadius, cornerRadius, cornerRadius, 90, 90); + + path.CloseFigure(); + g.DrawPath(pen, path); + + // колеса + g.DrawEllipse(pen, startPosX + 1, startPosY + tankHeight - 5 - 25, 25, 25); + for (int i = 1; i < 5; i++) + { + g.DrawEllipse(pen, startPosX + 30 + 5 * i + 15 * (i - 1), startPosY + tankHeight - 5 - 15, 15, 15); + } + g.DrawEllipse(pen, startPosX + tankWidth - 25 - 1, startPosY + tankHeight - 5 - 25, 25, 25); + + // башня + SolidBrush brush = new SolidBrush(EntityTankBase.BodyColor); + g.FillRectangle(brush, startPosX + 45, startPosY + 30, 60, 25); + + g.FillRectangle(brush, startPosX + 5, startPosY + 55 + 1, tankWidth - 10, 9); + } + } +} \ No newline at end of file diff --git a/ProjectTank/Entities/EntityTank.cs b/ProjectTank/Entities/EntityTank.cs new file mode 100644 index 0000000..642ee52 --- /dev/null +++ b/ProjectTank/Entities/EntityTank.cs @@ -0,0 +1,23 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Net.NetworkInformation; +using System.Text; +using System.Threading.Tasks; + +namespace ProjectTank.Entities +{ + public class EntityTank : EntityTankBase + { + public Color AdditionalColor { get; private set; } + public bool TankTower { get; private set; } + public bool AntiAirforceGun { get; private set; } + public EntityTank(int speed, double weight, Color bodyColor, Color +additionalColor, bool tankTower, bool antiAirforceGun) : base(speed, weight, bodyColor) + { + AdditionalColor = additionalColor; + TankTower = tankTower; + AntiAirforceGun = antiAirforceGun; + } + } +} diff --git a/ProjectTank/Entities/EntityTankBase.cs b/ProjectTank/Entities/EntityTankBase.cs new file mode 100644 index 0000000..bee2392 --- /dev/null +++ b/ProjectTank/Entities/EntityTankBase.cs @@ -0,0 +1,22 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace ProjectTank.Entities +{ + public class EntityTankBase + { + public int Speed { get; private set; } + public double Weight { get; private set; } + public Color BodyColor { get; private set; } + public double Step => (double)Speed * 100 / Weight; + public EntityTankBase(int speed, double weight, Color bodyColor) + { + Speed = speed; + Weight = weight; + BodyColor = bodyColor; + } + } +} diff --git a/ProjectTank/FormTank.Designer.cs b/ProjectTank/FormTank.Designer.cs index 48b36b7..9d2c622 100644 --- a/ProjectTank/FormTank.Designer.cs +++ b/ProjectTank/FormTank.Designer.cs @@ -34,6 +34,9 @@ buttonDown = new Button(); buttonRight = new Button(); buttonUp = new Button(); + comboBoxStrategy = new ComboBox(); + button1 = new Button(); + button2 = new Button(); ((System.ComponentModel.ISupportInitialize)pictureBoxTank).BeginInit(); SuspendLayout(); // @@ -49,13 +52,13 @@ // // createButton // - createButton.Location = new Point(885, 405); + createButton.Location = new Point(700, 406); createButton.Name = "createButton"; - createButton.Size = new Size(94, 41); + createButton.Size = new Size(130, 41); createButton.TabIndex = 8; - createButton.Text = "Create"; + createButton.Text = "Create tank base"; createButton.UseVisualStyleBackColor = true; - createButton.Click += buttonCreate_Click; + createButton.Click += ButtonCreateTankBase_Click; // // buttonLeft // @@ -105,11 +108,45 @@ buttonUp.UseVisualStyleBackColor = true; buttonUp.Click += moveButton_Click; // + // comboBoxStrategy + // + comboBoxStrategy.AutoCompleteCustomSource.AddRange(new string[] { "Move to center", "Move to border" }); + comboBoxStrategy.DropDownStyle = ComboBoxStyle.DropDownList; + comboBoxStrategy.FormattingEnabled = true; + comboBoxStrategy.Items.AddRange(new object[] { "Move to center", "Move to right bottom corner" }); + comboBoxStrategy.Location = new Point(757, 0); + comboBoxStrategy.Name = "comboBoxStrategy"; + comboBoxStrategy.Size = new Size(234, 28); + comboBoxStrategy.TabIndex = 13; + // + // button1 + // + button1.Location = new Point(840, 406); + button1.Name = "button1"; + button1.Size = new Size(139, 41); + button1.TabIndex = 14; + button1.Text = "Create full tank"; + button1.UseVisualStyleBackColor = true; + button1.Click += ButtonCreateTank_Click; + // + // button2 + // + button2.Location = new Point(897, 34); + button2.Name = "button2"; + button2.Size = new Size(94, 29); + button2.TabIndex = 15; + button2.Text = "Step"; + button2.UseVisualStyleBackColor = true; + button2.Click += ButtonStep_Click; + // // FormTank // AutoScaleDimensions = new SizeF(8F, 20F); AutoScaleMode = AutoScaleMode.Font; ClientSize = new Size(991, 458); + Controls.Add(button2); + Controls.Add(button1); + Controls.Add(comboBoxStrategy); Controls.Add(buttonUp); Controls.Add(buttonRight); Controls.Add(buttonDown); @@ -131,5 +168,8 @@ private Button buttonDown; private Button buttonRight; private Button buttonUp; + private ComboBox comboBoxStrategy; + private Button button1; + private Button button2; } } \ No newline at end of file diff --git a/ProjectTank/FormTank.cs b/ProjectTank/FormTank.cs index 0941bac..4a5292b 100644 --- a/ProjectTank/FormTank.cs +++ b/ProjectTank/FormTank.cs @@ -1,53 +1,90 @@ +using ProjectTank.DrawningObjects; +using ProjectTank.Entities; +using ProjectTank.MovementStrategy; +using static System.Windows.Forms.VisualStyles.VisualStyleElement; + namespace ProjectTank { public partial class FormTank : Form { - private DrawingTank? DrawingTank; + private DrawningTankBase? DrawningTank; + private AbstractStrategy? AbstractStrategy; public FormTank() { InitializeComponent(); } - private void buttonCreate_Click(object sender, EventArgs e) - { - Random random = new(); - DrawingTank = new DrawingTank(); - DrawingTank.Init(random.Next(50, 100), random.Next(1700, 3000), Color.FromArgb(random.Next(0, 255), random.Next(0, 255), random.Next(0, 255)), Color.FromArgb(random.Next(0, 255), random.Next(0, 255), random.Next(0, 255)), pictureBoxTank.Width, pictureBoxTank.Height, true, true); - DrawingTank.SetPosition(random.Next(10, 100), random.Next(10, 100)); - Draw(); - } - private void Draw() { - if (DrawingTank == null) return; + if (DrawningTank == null) return; Bitmap bmp = new(pictureBoxTank.Width, pictureBoxTank.Height); Graphics gr = Graphics.FromImage(bmp); - DrawingTank.DrawTransport(gr); + DrawningTank.DrawTransport(gr); pictureBoxTank.Image = bmp; } - + private void ButtonCreateTank_Click(object sender, EventArgs e) + { + Random random = new(); + DrawningTank = new DrawningTank(random.Next(100, 300), random.Next(1000, 3000), Color.FromArgb(random.Next(0, 256), random.Next(0, 256), random.Next(0, 256)), Color.FromArgb(random.Next(0, 256), random.Next(0, 256), random.Next(0, 256)), true, true, pictureBoxTank.Width, pictureBoxTank.Height); + DrawningTank.SetPosition(random.Next(10, 100), random.Next(10, 100)); + Draw(); + } + private void ButtonCreateTankBase_Click(object sender, EventArgs e) + { + Random random = new(); + DrawningTank = new DrawningTankBase(random.Next(100, 300), random.Next(1000, 3000), Color.FromArgb(random.Next(0, 256), random.Next(0, 256), random.Next(0, 256)), pictureBoxTank.Width, pictureBoxTank.Height); + DrawningTank.SetPosition(random.Next(10, 100), random.Next(10, 100)); + Draw(); + } private void moveButton_Click(object sender, EventArgs e) { - if (DrawingTank == null) return; + if (DrawningTank == null) return; - string name = ((Button)sender)?.Name ?? string.Empty; + string name = ((System.Windows.Forms.Button)sender)?.Name ?? string.Empty; switch (name) { case "buttonUp": - DrawingTank.MoveTransport(DirectionType.Up); + DrawningTank.MoveTransport(DirectionType.Up); break; case "buttonDown": - DrawingTank.MoveTransport(DirectionType.Down); + DrawningTank.MoveTransport(DirectionType.Down); break; case "buttonLeft": - DrawingTank.MoveTransport(DirectionType.Left); + DrawningTank.MoveTransport(DirectionType.Left); break; case "buttonRight": - DrawingTank.MoveTransport(DirectionType.Right); + DrawningTank.MoveTransport(DirectionType.Right); break; } Draw(); } + private void ButtonStep_Click(object sender, EventArgs e) + { + if (DrawningTank == null) return; + + if (comboBoxStrategy.Enabled) + { + AbstractStrategy = comboBoxStrategy.SelectedIndex + switch + { + 0 => new MoveToCenter(), + 1 => new MoveToRightBottomCorner(), + _ => null, + }; + if (AbstractStrategy == null) return; + AbstractStrategy.SetData(new DrawningObjectTank(DrawningTank), pictureBoxTank.Width, pictureBoxTank.Height); + comboBoxStrategy.Enabled = false; + } + if (AbstractStrategy == null) return; + + AbstractStrategy.MakeStep(); + Draw(); + if (AbstractStrategy.GetStatus() == MovementStrategy.Status.Finish) + { + comboBoxStrategy.Enabled = true; + AbstractStrategy = null; + } + } } } \ No newline at end of file diff --git a/ProjectTank/MovementStrategy/AbstractStrategy.cs b/ProjectTank/MovementStrategy/AbstractStrategy.cs new file mode 100644 index 0000000..6eb57d7 --- /dev/null +++ b/ProjectTank/MovementStrategy/AbstractStrategy.cs @@ -0,0 +1,129 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using static System.Windows.Forms.VisualStyles.VisualStyleElement; + +namespace ProjectTank.MovementStrategy +{ + public abstract class AbstractStrategy + { + /// + /// Перемещаемый объект + /// + private IMoveableObject? _moveableObject; + /// + /// Статус перемещения + /// + private Status _state = Status.NotInit; + /// + /// Ширина поля + /// + protected int FieldWidth { get; private set; } + /// + /// Высота поля + /// + protected int FieldHeight { get; private set; } + /// + /// Статус перемещения + /// + public Status GetStatus() { return _state; } + /// + /// Установка данных + /// + /// Перемещаемый объект + /// Ширина поля + /// Высота поля + public void SetData(IMoveableObject moveableObject, int width, int + height) + { + if (moveableObject == null) + { + _state = Status.NotInit; + return; + } + _state = Status.InProgress; + _moveableObject = moveableObject; + FieldWidth = width; + FieldHeight = height; + } + /// + /// Шаг перемещения + /// + public void MakeStep() + { + if (_state != Status.InProgress) return; + if (IsTargetDestination()) + { + _state = Status.Finish; + return; + } + MoveToTarget(); + } + /// + /// Перемещение влево + /// + /// Результат перемещения (true - удалось переместиться, false - неудача) + protected bool MoveLeft() => MoveTo(DirectionType.Left); + /// + /// Перемещение вправо + /// + /// Результат перемещения (true - удалось переместиться, false - неудача) + protected bool MoveRight() => MoveTo(DirectionType.Right); + /// + /// Перемещение вверх + /// + /// Результат перемещения (true - удалось переместиться, false - неудача) + protected bool MoveUp() => MoveTo(DirectionType.Up); + /// + /// Перемещение вниз + /// + /// Результат перемещения (true - удалось переместиться,false - неудача) + protected bool MoveDown() => MoveTo(DirectionType.Down); + /// + /// Параметры объекта + /// + protected ObjectParameters? GetObjectParameters => _moveableObject?.GetObjectPosition; + /// + /// Шаг объекта + /// + /// + protected int? GetStep() + { + if (_state != Status.InProgress) + { + return null; + } + return _moveableObject?.GetStep; + } + /// + /// Перемещение к цели + /// + protected abstract void MoveToTarget(); + /// + /// Достигнута ли цель + /// + /// + protected abstract bool IsTargetDestination(); + /// + /// Попытка перемещения в требуемом направлении + /// + /// Направление + /// Результат попытки (true - удалось переместиться, false - неудача) + /// + private bool MoveTo(DirectionType directionType) + { + if (_state != Status.InProgress) + { + return false; + } + if (_moveableObject?.CheckCanMove(directionType) ?? false) + { + _moveableObject.MoveObject(directionType); + return true; + } + return false; + } + } +} diff --git a/ProjectTank/MovementStrategy/DrawningObjectTank.cs b/ProjectTank/MovementStrategy/DrawningObjectTank.cs new file mode 100644 index 0000000..f29cace --- /dev/null +++ b/ProjectTank/MovementStrategy/DrawningObjectTank.cs @@ -0,0 +1,31 @@ +using ProjectTank.DrawningObjects; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace ProjectTank.MovementStrategy +{ + public class DrawningObjectTank : IMoveableObject + { + private readonly DrawningTankBase? DrawningTankBase = null; + public DrawningObjectTank(DrawningTankBase drawningTankBase) + { + DrawningTankBase = drawningTankBase; + } + public ObjectParameters? GetObjectPosition + { + get + { + if (DrawningTankBase == null || DrawningTankBase.EntityTankBase == null) return null; + + return new ObjectParameters(DrawningTankBase.GetPosX, + DrawningTankBase.GetPosY, DrawningTankBase.GetWidth, DrawningTankBase.GetHeight); + } + } + public int GetStep => (int)(DrawningTankBase?.EntityTankBase?.Step ?? 0); + public bool CheckCanMove(DirectionType direction) => DrawningTankBase?.CanMove(direction) ?? false; + public void MoveObject(DirectionType direction) => DrawningTankBase?.MoveTransport(direction); + } +} \ No newline at end of file diff --git a/ProjectTank/MovementStrategy/IMoveableObject.cs b/ProjectTank/MovementStrategy/IMoveableObject.cs new file mode 100644 index 0000000..dda0692 --- /dev/null +++ b/ProjectTank/MovementStrategy/IMoveableObject.cs @@ -0,0 +1,33 @@ +using ProjectTank.Entities; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace ProjectTank.MovementStrategy +{ + public interface IMoveableObject + { + /// + /// Получение координаты X объекта + /// + ObjectParameters? GetObjectPosition { get; } + /// + /// Шаг объекта + /// + int GetStep { get; } + /// + /// Проверка, можно ли переместиться по нужному направлению + /// + /// + /// + bool CheckCanMove(DirectionType direction); + /// + /// Изменение направления пермещения объекта + /// + /// Направление + void MoveObject(DirectionType direction); + } + +} diff --git a/ProjectTank/MovementStrategy/MoveToCenter.cs b/ProjectTank/MovementStrategy/MoveToCenter.cs new file mode 100644 index 0000000..84cd754 --- /dev/null +++ b/ProjectTank/MovementStrategy/MoveToCenter.cs @@ -0,0 +1,40 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace ProjectTank.MovementStrategy +{ + public class MoveToCenter : AbstractStrategy + { + protected override bool IsTargetDestination() + { + var objParams = GetObjectParameters; + if (objParams == null) return false; + + return objParams.ObjectMiddleHorizontal <= FieldWidth / 2 && + objParams.ObjectMiddleHorizontal + GetStep() >= FieldWidth / 2 && + objParams.ObjectMiddleVertical <= FieldHeight / 2 && + objParams.ObjectMiddleVertical + GetStep() >= FieldHeight / 2; + } + protected override void MoveToTarget() + { + var objParams = GetObjectParameters; + if (objParams == null) return; + + var diffX = objParams.ObjectMiddleHorizontal - FieldWidth / 2; + if (Math.Abs(diffX) > GetStep()) + { + if (diffX > 0) MoveLeft(); + else MoveRight(); + } + var diffY = objParams.ObjectMiddleVertical - FieldHeight / 2; + if (Math.Abs(diffY) > GetStep()) + { + if (diffY > 0) MoveUp(); + else MoveDown(); + } + } + } +} diff --git a/ProjectTank/MovementStrategy/MoveToRightBottomCorner.cs b/ProjectTank/MovementStrategy/MoveToRightBottomCorner.cs new file mode 100644 index 0000000..58f90fe --- /dev/null +++ b/ProjectTank/MovementStrategy/MoveToRightBottomCorner.cs @@ -0,0 +1,40 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace ProjectTank.MovementStrategy +{ + public class MoveToRightBottomCorner : AbstractStrategy + { + protected override bool IsTargetDestination() + { + var objParams = GetObjectParameters; + if (objParams == null) return false; + + return objParams.RightBorder <= FieldWidth && objParams.RightBorder + GetStep() > FieldWidth && + objParams.DownBorder <= FieldHeight && objParams.DownBorder + GetStep() > FieldHeight; + } + + protected override void MoveToTarget() + { + var objParams = GetObjectParameters; + if (objParams == null) return; + + var diffX = objParams.ObjectMiddleHorizontal - FieldWidth; + if (Math.Abs(diffX) > GetStep()) + { + if (diffX > 0) MoveLeft(); + else MoveRight(); + } + + var diffY = objParams.ObjectMiddleVertical - FieldHeight; + if (Math.Abs(diffY) > GetStep()) + { + if (diffY > 0) MoveUp(); + else MoveDown(); + } + } + } +} \ No newline at end of file diff --git a/ProjectTank/MovementStrategy/ObjectParameters.cs b/ProjectTank/MovementStrategy/ObjectParameters.cs new file mode 100644 index 0000000..1e78af8 --- /dev/null +++ b/ProjectTank/MovementStrategy/ObjectParameters.cs @@ -0,0 +1,56 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace ProjectTank.MovementStrategy +{ + /// + public class ObjectParameters + { + private readonly int _x; + private readonly int _y; + private readonly int _width; + private readonly int _height; + /// + /// Левая граница + /// + public int LeftBorder => _x; + /// + /// Верхняя граница + /// + public int TopBorder => _y; + /// + /// Правая граница + /// + public int RightBorder => _x + _width; + /// + /// Нижняя граница + /// + public int DownBorder => _y + _height; + /// + /// Середина объекта + /// + public int ObjectMiddleHorizontal => _x + _width / 2; + /// + /// Середина объекта + /// + public int ObjectMiddleVertical => _y + _height / 2; + /// + /// Конструктор + /// + /// Координата X + /// Координата Y + /// Ширина + /// Высота + public ObjectParameters(int x, int y, int width, int height) + { + _x = x; + _y = y; + _width = width; + _height = height; + } + } + +} diff --git a/ProjectTank/MovementStrategy/Status.cs b/ProjectTank/MovementStrategy/Status.cs new file mode 100644 index 0000000..783be83 --- /dev/null +++ b/ProjectTank/MovementStrategy/Status.cs @@ -0,0 +1,15 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace ProjectTank.MovementStrategy +{ + public enum Status + { + NotInit = 1, + InProgress = 2, + Finish = 3 + } +} diff --git a/ProjectTank/TankEntity.cs b/ProjectTank/TankEntity.cs deleted file mode 100644 index 77b6863..0000000 --- a/ProjectTank/TankEntity.cs +++ /dev/null @@ -1,28 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; -using System.Threading.Tasks; - -namespace ProjectTank -{ - internal class Tank - { - public int Speed { get; private set; } - public double Weight { get; private set; } - public Color BodyColor { get; private set; } - public Color AdditionalColor { get; private set; } - public bool IsAntiAircraftGun { get; private set; } - public bool IsTankMuzzle { get; private set; } - public double Step => (double)Speed * 100 / Weight; - public void Init(int speed, double weight, Color bodyColor, Color additionalColor, bool isAntiAircraftGun, bool isTankTower) - { - Speed = speed; - Weight = weight; - BodyColor = bodyColor; - AdditionalColor = additionalColor; - IsAntiAircraftGun = isAntiAircraftGun; - IsTankMuzzle = isTankTower; - } - } -} -- 2.25.1