diff --git a/ProjStormtrooper/ProjStormtrooper/AbstractStrategy.cs b/ProjStormtrooper/ProjStormtrooper/AbstractStrategy.cs new file mode 100644 index 0000000..9bd454d --- /dev/null +++ b/ProjStormtrooper/ProjStormtrooper/AbstractStrategy.cs @@ -0,0 +1,132 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace ProjStormtrooper +{ + /// + /// Класс-стратегия перемещения объекта + /// + 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 (IsTargetDestinaion()) + { + _state = Status.Finish; + return; + } + MoveToTarget(); + } + /// + /// Перемещение влево + /// + /// Результат перемещения (true - удалось переместиться, false - неудача) + protected bool MoveLeft() => MoveTo(Direction.Left); + /// + /// Перемещение вправо + /// + /// Результат перемещения (true - удалось переместиться, false - неудача) + protected bool MoveRight() => MoveTo(Direction.Right); + /// + /// Перемещение вверх + /// + /// Результат перемещения (true - удалось переместиться, false - неудача) + protected bool MoveUp() => MoveTo(Direction.Up); + /// + /// Перемещение вниз + /// + /// Результат перемещения (true - удалось переместиться, false - неудача) + protected bool MoveDown() => MoveTo(Direction.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 IsTargetDestinaion(); + /// + /// Попытка перемещения в требуемом направлении + /// + /// Направление + /// Результат попытки (true - удалось переместиться, false - неудача) + private bool MoveTo(Direction directionType) + { + if (_state != Status.InProgress) + { + return false; + } + if (_moveableObject?.CheckCanMove(directionType) ?? false) + { + _moveableObject.MoveObject(directionType); + return true; + } + return false; + } + } +} diff --git a/ProjStormtrooper/ProjStormtrooper/Direction.cs b/ProjStormtrooper/ProjStormtrooper/Direction.cs index 79e4e6f..93ba617 100644 --- a/ProjStormtrooper/ProjStormtrooper/Direction.cs +++ b/ProjStormtrooper/ProjStormtrooper/Direction.cs @@ -6,7 +6,7 @@ using System.Threading.Tasks; namespace ProjStormtrooper { - internal enum Direction + public enum Direction { Up = 1, Down = 2, diff --git a/ProjStormtrooper/ProjStormtrooper/DrawingObjectPlane.cs b/ProjStormtrooper/ProjStormtrooper/DrawingObjectPlane.cs new file mode 100644 index 0000000..1381404 --- /dev/null +++ b/ProjStormtrooper/ProjStormtrooper/DrawingObjectPlane.cs @@ -0,0 +1,35 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace ProjStormtrooper +{ + public class DrawingObjectPlane : IMoveableObject + { + private readonly DrawingPlane? _drawingPlane = null; + public DrawingObjectPlane(DrawingPlane drawingPlane) + { + _drawingPlane = drawingPlane; + } + + public ObjectParameters? GetObjectPosition + { + get + { + if (_drawingPlane == null || _drawingPlane.EntityPlane == null) + { + return null; + } + return new ObjectParameters(_drawingPlane.GetPosX, _drawingPlane.GetPosY, _drawingPlane.GetWidth, _drawingPlane.GetHeight); + } + } + + public int GetStep => (int)(_drawingPlane?.EntityPlane?.Step ?? 0); + + public bool CheckCanMove(Direction direction) => _drawingPlane?.CanMove(direction) ?? false; + + public void MoveObject(Direction direction) => _drawingPlane?.MoveTransport(direction); + } +} diff --git a/ProjStormtrooper/ProjStormtrooper/DrawingPlane.cs b/ProjStormtrooper/ProjStormtrooper/DrawingPlane.cs new file mode 100644 index 0000000..4e3d4ac --- /dev/null +++ b/ProjStormtrooper/ProjStormtrooper/DrawingPlane.cs @@ -0,0 +1,173 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace ProjStormtrooper +{ + + public class DrawingPlane + { + public EntityPlane? EntityPlane { get; protected set; } + private int _pictureWidth; + private int _pictureHeight; + protected int _startPosX; + protected int _startPosY; + protected readonly int _planeWidth = 110; + protected readonly int _planeHeight = 110; + public int GetPosX => _startPosX; + public int GetPosY => _startPosY; + public int GetWidth => _planeWidth; + public int GetHeight => _planeHeight; + + public DrawingPlane(int speed, double weight, Color bodyColor, int width, int height) + { + if (width < _planeWidth && height < _planeHeight) + { + return; + } + _pictureWidth = width; + _pictureHeight = height; + EntityPlane = new EntityPlane(speed, weight, bodyColor); + } + + protected DrawingPlane(int speed, double weight, Color bodyColor, + int width, int height, int planeWidth, int planeHeight) + { + if (width < planeWidth && height < planeHeight) + { + return; + } + _pictureWidth = width; + _pictureHeight = height; + _planeWidth = planeWidth; + _planeHeight = planeHeight; + EntityPlane = new EntityPlane(speed, weight, bodyColor); + } + + public bool CanMove(Direction direction) + { + if (EntityPlane == null) + { + return false; + } + return direction switch + { + + Direction.Up => _startPosY - EntityPlane.Step > 0, + + Direction.Down => _startPosY + _planeHeight + EntityPlane.Step < _pictureHeight, + + Direction.Left => _startPosX - EntityPlane.Step > 0, + + Direction.Right => _startPosX + _planeWidth + EntityPlane.Step < _pictureWidth, + _ => false, + }; + } + + public void SetPosition(int x, int y) + { + if (x < 0) + { + x = 0; + } + else if (x > _pictureWidth - _planeWidth) + { + x = _pictureWidth - _planeWidth; + } + _startPosX = x; + + if (y < 0) + { + y = 0; + } + else if (y > _pictureHeight - _planeHeight) + { + y = _pictureHeight - _planeHeight; + } + _startPosY = y; + } + + public void MoveTransport(Direction direction) + { + if (!CanMove(direction) || EntityPlane == null) + { + return; + } + switch (direction) + { + + case Direction.Up: + _startPosY -= (int)EntityPlane.Step; + break; + + case Direction.Down: + _startPosY += (int)EntityPlane.Step; + break; + + case Direction.Left: + _startPosX -= (int)EntityPlane.Step; + break; + + case Direction.Right: + _startPosX += (int)EntityPlane.Step; + break; + } + } + + public virtual void DrawTransport(Graphics g) + { + if (EntityPlane == null) + { + return; + } + Pen penBlack = new Pen(Color.Black); + Brush brushBlack = new SolidBrush(Color.Black); + Brush brushBodyColor = new SolidBrush(EntityPlane.BodyColor); + + + int bodyHeight = _planeHeight / 9; + + + Point[] pointsCockPit = { + new Point(_startPosX, _startPosY + _planeHeight / 2), + new Point(_startPosX + _planeWidth / 8, _startPosY + _planeHeight / 2 - bodyHeight / 2), + new Point(_startPosX + _planeWidth / 8, _startPosY + _planeHeight / 2 + bodyHeight / 2) + }; + + g.FillPolygon(brushBlack, pointsCockPit); + + + + Point[] pointsWings = { + new Point(_startPosX + _planeWidth / 2, _startPosY), + new Point(_startPosX + _planeWidth / 2 + _planeWidth / 15, _startPosY), + new Point(_startPosX + _planeWidth / 2 + _planeWidth / 6, _startPosY + _planeHeight / 2), + new Point(_startPosX + _planeWidth / 2 + _planeWidth / 15, _startPosY + _planeHeight), + new Point(_startPosX + _planeWidth / 2 , _startPosY + _planeHeight) + }; + + g.FillPolygon(brushBodyColor, pointsWings); + g.DrawPolygon(penBlack, pointsWings); + + + + Point[] pointsTail = { + new Point(_startPosX + _planeWidth, _startPosY + _planeHeight / 2 - _planeHeight / 3), + new Point(_startPosX + _planeWidth - _planeWidth / 8, _startPosY + _planeHeight / 2 - _planeHeight / 8), + new Point(_startPosX + _planeWidth - _planeWidth / 8, _startPosY + _planeHeight / 2 + _planeHeight / 8), + new Point(_startPosX + _planeWidth, _startPosY + _planeHeight / 2 + _planeHeight / 3) + + }; + + g.FillPolygon(brushBodyColor, pointsTail); + g.DrawPolygon(penBlack, pointsTail); + + + + g.FillRectangle(brushBodyColor, _startPosX + _planeWidth / 8, _startPosY + _planeHeight / 2 - bodyHeight / 2, _planeWidth - _planeWidth / 8, bodyHeight); + g.DrawRectangle(penBlack, _startPosX + _planeWidth / 8, _startPosY + _planeHeight / 2 - bodyHeight / 2, _planeWidth - _planeWidth / 8, bodyHeight); + } + } +} diff --git a/ProjStormtrooper/ProjStormtrooper/DrawingStormtrooper.cs b/ProjStormtrooper/ProjStormtrooper/DrawingStormtrooper.cs index e51f7a5..a26f354 100644 --- a/ProjStormtrooper/ProjStormtrooper/DrawingStormtrooper.cs +++ b/ProjStormtrooper/ProjStormtrooper/DrawingStormtrooper.cs @@ -6,119 +6,43 @@ using System.Threading.Tasks; namespace ProjStormtrooper { - internal class DrawingStormtrooper + public class DrawingStormtrooper : DrawingPlane { - public EntityStormtrooper? EntityStormtrooper { get; private set; } - private int _pictureWidth; - private int _pictureHeight; - private int _startPosX; - private int _startPosY; - private readonly int _stormtrooperWidth = 110; - private readonly int _stormtrooperHeight = 110; - - public bool Init(int speed, double weight, Color bodyColor, + public DrawingStormtrooper(int speed, double weight, Color bodyColor, Color additionalColor, bool rockets, bool bombs, - int width, int height) + int width, int height) : base(speed, weight, bodyColor, width, height, 140, 90) { - if (width < _stormtrooperWidth && height < _stormtrooperHeight) + if (EntityPlane != null) { - return false; - } - _pictureWidth = width; - _pictureHeight = height; - EntityStormtrooper = new EntityStormtrooper(); - EntityStormtrooper.Init(speed, weight, bodyColor, additionalColor, rockets, bombs); - return true; - } - - public void SetPosition(int x, int y) - { - if (x < 0) - { - x = 0; - } - else if (x > _pictureWidth - _stormtrooperWidth) - { - x = _pictureWidth - _stormtrooperWidth; - } - _startPosX = x; - - if (y < 0) - { - y = 0; - } - else if (y > _pictureHeight - _stormtrooperHeight) - { - y = _pictureHeight - _stormtrooperHeight; - } - _startPosY = y; - } - - public void MoveTransport(Direction direction) - { - if (EntityStormtrooper == null) - - { - return; - } - switch (direction) - { - - case Direction.Left: - if (_startPosX - EntityStormtrooper.Step > 0) - { - _startPosX -= (int)EntityStormtrooper.Step; - } - break; - - case Direction.Up: - if (_startPosY - EntityStormtrooper.Step > 0) - { - _startPosY -= (int)EntityStormtrooper.Step; - } - break; - - case Direction.Right: - if (_startPosX + EntityStormtrooper.Step + _stormtrooperWidth < _pictureWidth) - { - _startPosX += (int)EntityStormtrooper.Step; - } - break; - - case Direction.Down: - if (_startPosY + EntityStormtrooper.Step + _stormtrooperHeight < _pictureHeight) - { - _startPosY += (int)EntityStormtrooper.Step; - } - break; + EntityPlane = new EntityStormtrooper(speed, weight, bodyColor, additionalColor, rockets, bombs); } } - public void DrawStormtrooper(Graphics g) + public override void DrawTransport(Graphics g) { - if (EntityStormtrooper == null) + if (EntityPlane is not EntityStormtrooper stormtrooper) { return; } Pen penBlack = new Pen(Color.Black); Brush brushBlack = new SolidBrush(Color.Black); - Brush brushBodyColor = new SolidBrush(EntityStormtrooper.BodyColor); - Brush brushAdditionalColor = new SolidBrush(EntityStormtrooper.AdditionalColor); + Brush brushAdditionalColor = new SolidBrush(stormtrooper.AdditionalColor); - - int bodyHeight = _stormtrooperHeight / 9; - if (EntityStormtrooper.Bombs) + int bodyHeight = _planeHeight / 9; + + + if (stormtrooper.Bombs) { Point[] pointsBombTail = { - new Point(_startPosX + _stormtrooperWidth / 2 - _stormtrooperWidth / 8 + bodyHeight * 3 - 5, - _startPosY + _stormtrooperHeight / 2 - bodyHeight / 2 - _stormtrooperHeight / 3 + bodyHeight / 2), - new Point(_startPosX + _stormtrooperWidth / 2 - _stormtrooperWidth / 8 + bodyHeight * 3 + 5, - _startPosY + _stormtrooperHeight / 2 - bodyHeight / 2 - _stormtrooperHeight / 3 + bodyHeight / 2 - 5), - new Point(_startPosX + _stormtrooperWidth / 2 - _stormtrooperWidth / 8 + bodyHeight * 3 + 5, - _startPosY + _stormtrooperHeight / 2 - bodyHeight / 2 - _stormtrooperHeight / 3 + bodyHeight / 2 + 5), - new Point(_startPosX + _stormtrooperWidth / 2 - _stormtrooperWidth / 8 + bodyHeight * 3 - 5, - _startPosY + _stormtrooperHeight / 2 - bodyHeight / 2 - _stormtrooperHeight / 3 + bodyHeight / 2) + new Point(_startPosX + _planeWidth / 2 - _planeWidth / 8 + bodyHeight * 3 - 5, + _startPosY + _planeHeight / 2 - bodyHeight / 2 - _planeHeight / 3 + bodyHeight / 2), + new Point(_startPosX + _planeWidth / 2 - _planeWidth / 8 + bodyHeight * 3 + 5, + _startPosY + _planeHeight / 2 - bodyHeight / 2 - _planeHeight / 3 + bodyHeight / 2 - 5), + new Point(_startPosX + _planeWidth / 2 - _planeWidth / 8 + bodyHeight * 3 + 5, + _startPosY + _planeHeight / 2 - bodyHeight / 2 - _planeHeight / 3 + bodyHeight / 2 + 5), + new Point(_startPosX + _planeWidth / 2 - _planeWidth / 8 + bodyHeight * 3 - 5, + _startPosY + _planeHeight / 2 - bodyHeight / 2 - _planeHeight / 3 + bodyHeight / 2) }; g.FillPolygon(brushAdditionalColor, pointsBombTail); @@ -127,7 +51,7 @@ namespace ProjStormtrooper for (int i = 0; i < pointsBombTail.Length; i++) { Point p = pointsBombTail[i]; - p.Y = _startPosY + _stormtrooperHeight - (p.Y - _startPosY); + p.Y = _startPosY + _planeHeight - (p.Y - _startPosY); pointsBombTail[i] = p; } @@ -135,30 +59,30 @@ namespace ProjStormtrooper g.DrawPolygon(penBlack, pointsBombTail); g.FillEllipse(brushAdditionalColor, - _startPosX + _stormtrooperWidth / 2 - _stormtrooperWidth / 8, - _startPosY + _stormtrooperHeight / 2 - bodyHeight / 2 - _stormtrooperHeight / 3, + _startPosX + _planeWidth / 2 - _planeWidth / 8, + _startPosY + _planeHeight / 2 - bodyHeight / 2 - _planeHeight / 3, bodyHeight * 3, bodyHeight); g.DrawEllipse(penBlack, - _startPosX + _stormtrooperWidth / 2 - _stormtrooperWidth / 8, - _startPosY + _stormtrooperHeight / 2 - bodyHeight / 2 - _stormtrooperHeight / 3, + _startPosX + _planeWidth / 2 - _planeWidth / 8, + _startPosY + _planeHeight / 2 - bodyHeight / 2 - _planeHeight / 3, bodyHeight * 3, bodyHeight); g.FillEllipse(brushAdditionalColor, - _startPosX + _stormtrooperWidth / 2 - _stormtrooperWidth / 8, - _startPosY + _stormtrooperHeight / 2 - bodyHeight / 2 + _stormtrooperHeight / 3, + _startPosX + _planeWidth / 2 - _planeWidth / 8, + _startPosY + _planeHeight / 2 - bodyHeight / 2 + _planeHeight / 3, bodyHeight * 3, bodyHeight); g.DrawEllipse(penBlack, - _startPosX + _stormtrooperWidth / 2 - _stormtrooperWidth / 8, - _startPosY + _stormtrooperHeight / 2 - bodyHeight / 2 + _stormtrooperHeight / 3, + _startPosX + _planeWidth / 2 - _planeWidth / 8, + _startPosY + _planeHeight / 2 - bodyHeight / 2 + _planeHeight / 3, bodyHeight * 3, bodyHeight); } - if (EntityStormtrooper.Rockets) + if (stormtrooper.Rockets) { int rocketWidth = bodyHeight * 4; int rocketHeight = bodyHeight / 2; @@ -166,21 +90,21 @@ namespace ProjStormtrooper Brush brushRed = new SolidBrush(Color.Red); Point[] pointsRocketCockPit = { - new Point(_startPosX + _stormtrooperWidth / 2 - _stormtrooperWidth / 5 - rocketHeight, - _startPosY + _stormtrooperHeight / 2 - bodyHeight - bodyHeight / 2 + rocketHeight / 2), - new Point(_startPosX + _stormtrooperWidth / 2 - _stormtrooperWidth / 5, - _startPosY + _stormtrooperHeight / 2 - bodyHeight - bodyHeight / 2), - new Point(_startPosX + _stormtrooperWidth / 2 - _stormtrooperWidth / 5, - _startPosY + _stormtrooperHeight / 2 - bodyHeight - bodyHeight / 2 + rocketHeight) + new Point(_startPosX + _planeWidth / 2 - _planeWidth / 5 - rocketHeight, + _startPosY + _planeHeight / 2 - bodyHeight - bodyHeight / 2 + rocketHeight / 2), + new Point(_startPosX + _planeWidth / 2 - _planeWidth / 5, + _startPosY + _planeHeight / 2 - bodyHeight - bodyHeight / 2), + new Point(_startPosX + _planeWidth / 2 - _planeWidth / 5, + _startPosY + _planeHeight / 2 - bodyHeight - bodyHeight / 2 + rocketHeight) }; Point[] pointsRocketTail = { - new Point(_startPosX + _stormtrooperWidth / 2 - _stormtrooperWidth / 5 - rocketHeight + rocketWidth - 10, - _startPosY + _stormtrooperHeight / 2 - bodyHeight - bodyHeight / 2 + rocketHeight / 2), - new Point(_startPosX + _stormtrooperWidth / 2 - _stormtrooperWidth / 5 + rocketWidth, - _startPosY + _stormtrooperHeight / 2 - bodyHeight * 2 + rocketHeight / 2), - new Point(_startPosX + _stormtrooperWidth / 2 - _stormtrooperWidth / 5 + rocketWidth, - _startPosY + _stormtrooperHeight / 2 - bodyHeight - bodyHeight / 2 + rocketHeight + bodyHeight / 2 - rocketHeight / 2) + new Point(_startPosX + _planeWidth / 2 - _planeWidth / 5 - rocketHeight + rocketWidth - 10, + _startPosY + _planeHeight / 2 - bodyHeight - bodyHeight / 2 + rocketHeight / 2), + new Point(_startPosX + _planeWidth / 2 - _planeWidth / 5 + rocketWidth, + _startPosY + _planeHeight / 2 - bodyHeight * 2 + rocketHeight / 2), + new Point(_startPosX + _planeWidth / 2 - _planeWidth / 5 + rocketWidth, + _startPosY + _planeHeight / 2 - bodyHeight - bodyHeight / 2 + rocketHeight + bodyHeight / 2 - rocketHeight / 2) }; g.FillPolygon(brushRed, pointsRocketCockPit); @@ -192,14 +116,14 @@ namespace ProjStormtrooper for (int i = 0; i < pointsRocketCockPit.Length; i++) { Point p = pointsRocketCockPit[i]; - p.Y = _startPosY + _stormtrooperHeight - (p.Y - _startPosY); + p.Y = _startPosY + _planeHeight - (p.Y - _startPosY); pointsRocketCockPit[i] = p; } for (int i = 0; i < pointsRocketTail.Length; i++) { Point p = pointsRocketTail[i]; - p.Y = _startPosY + _stormtrooperHeight - (p.Y - _startPosY); + p.Y = _startPosY + _planeHeight - (p.Y - _startPosY); pointsRocketTail[i] = p; } @@ -210,65 +134,29 @@ namespace ProjStormtrooper g.DrawPolygon(penBlack, pointsRocketTail); g.FillRectangle(brushAdditionalColor, - _startPosX + _stormtrooperWidth / 2 - _stormtrooperWidth / 5, - _startPosY + _stormtrooperHeight / 2 - bodyHeight - bodyHeight / 2, + _startPosX + _planeWidth / 2 - _planeWidth / 5, + _startPosY + _planeHeight / 2 - bodyHeight - bodyHeight / 2, rocketWidth, rocketHeight); g.DrawRectangle(penBlack, - _startPosX + _stormtrooperWidth / 2 - _stormtrooperWidth / 5, - _startPosY + _stormtrooperHeight / 2 - bodyHeight - bodyHeight / 2, + _startPosX + _planeWidth / 2 - _planeWidth / 5, + _startPosY + _planeHeight / 2 - bodyHeight - bodyHeight / 2, rocketWidth, rocketHeight); g.FillRectangle(brushAdditionalColor, - _startPosX + _stormtrooperWidth / 2 - _stormtrooperWidth / 5, - _startPosY + _stormtrooperHeight / 2 + bodyHeight / 2 + bodyHeight / 2, + _startPosX + _planeWidth / 2 - _planeWidth / 5, + _startPosY + _planeHeight / 2 + bodyHeight / 2 + bodyHeight / 2, rocketWidth, rocketHeight); g.DrawRectangle(penBlack, - _startPosX + _stormtrooperWidth / 2 - _stormtrooperWidth / 5, - _startPosY + _stormtrooperHeight / 2 + bodyHeight / 2 + bodyHeight / 2, + _startPosX + _planeWidth / 2 - _planeWidth / 5, + _startPosY + _planeHeight / 2 + bodyHeight / 2 + bodyHeight / 2, rocketWidth, rocketHeight); } - - Point[] pointsCockPit = { - new Point(_startPosX, _startPosY + _stormtrooperHeight / 2), - new Point(_startPosX + _stormtrooperWidth / 8, _startPosY + _stormtrooperHeight / 2 - bodyHeight / 2), - new Point(_startPosX + _stormtrooperWidth / 8, _startPosY + _stormtrooperHeight / 2 + bodyHeight / 2) - }; - - g.FillPolygon(brushBlack, pointsCockPit); - - - - Point[] pointsWings = { - new Point(_startPosX + _stormtrooperWidth / 2, _startPosY), - new Point(_startPosX + _stormtrooperWidth / 2 + _stormtrooperWidth / 15, _startPosY), - new Point(_startPosX + _stormtrooperWidth / 2 + _stormtrooperWidth / 6, _startPosY + _stormtrooperHeight / 2), - new Point(_startPosX + _stormtrooperWidth / 2 + _stormtrooperWidth / 15, _startPosY + _stormtrooperHeight), - new Point(_startPosX + _stormtrooperWidth / 2 , _startPosY + _stormtrooperHeight) - }; - - g.FillPolygon(brushBodyColor, pointsWings); - g.DrawPolygon(penBlack, pointsWings); - - Point[] pointsTail = { - new Point(_startPosX + _stormtrooperWidth, _startPosY + _stormtrooperHeight / 2 - _stormtrooperHeight / 3), - new Point(_startPosX + _stormtrooperWidth - _stormtrooperWidth / 8, _startPosY + _stormtrooperHeight / 2 - _stormtrooperHeight / 8), - new Point(_startPosX + _stormtrooperWidth - _stormtrooperWidth / 8, _startPosY + _stormtrooperHeight / 2 + _stormtrooperHeight / 8), - new Point(_startPosX + _stormtrooperWidth, _startPosY + _stormtrooperHeight / 2 + _stormtrooperHeight / 3) - - }; - - g.FillPolygon(brushBodyColor, pointsTail); - g.DrawPolygon(penBlack, pointsTail); - - - g.FillRectangle(brushBodyColor, _startPosX + _stormtrooperWidth / 8, _startPosY + _stormtrooperHeight / 2 - bodyHeight / 2, _stormtrooperWidth - _stormtrooperWidth / 8, bodyHeight); - g.DrawRectangle(penBlack, _startPosX + _stormtrooperWidth / 8, _startPosY + _stormtrooperHeight / 2 - bodyHeight / 2, _stormtrooperWidth - _stormtrooperWidth / 8, bodyHeight); + base.DrawTransport(g); } - } } diff --git a/ProjStormtrooper/ProjStormtrooper/EntityPlane.cs b/ProjStormtrooper/ProjStormtrooper/EntityPlane.cs new file mode 100644 index 0000000..9e82403 --- /dev/null +++ b/ProjStormtrooper/ProjStormtrooper/EntityPlane.cs @@ -0,0 +1,26 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Net.Sockets; +using System.Text; +using System.Threading.Tasks; +using static System.Reflection.Metadata.BlobBuilder; + +namespace ProjStormtrooper +{ + public class EntityPlane + { + + public int Speed { get; private set; } + public double Weight { get; private set; } + public Color BodyColor { get; private set; } + public double Step => (double)Speed * 250 / Weight; + + public EntityPlane(int speed, double weight, Color bodyColor) + { + Speed = speed; + Weight = weight; + BodyColor = bodyColor; + } + } +} diff --git a/ProjStormtrooper/ProjStormtrooper/EntityStormtrooper.cs b/ProjStormtrooper/ProjStormtrooper/EntityStormtrooper.cs index e4b0a68..097c29e 100644 --- a/ProjStormtrooper/ProjStormtrooper/EntityStormtrooper.cs +++ b/ProjStormtrooper/ProjStormtrooper/EntityStormtrooper.cs @@ -6,25 +6,18 @@ using System.Threading.Tasks; namespace ProjStormtrooper { - internal class EntityStormtrooper + public class EntityStormtrooper : EntityPlane { - 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 Bombs { get; private set; } public bool Rockets { get; private set; } - public double Step => (double)Speed * 100 / Weight; - - public void Init(int speed, double weight, Color bodyColor, Color additionalColor, bool rockets, bool bombs) + public bool Bombs { get; private set; } + + public EntityStormtrooper(int speed, double weight, Color bodyColor, + Color additionalColor, bool rockets, bool bombs) : base(speed, weight, bodyColor) { - Speed = speed; - Weight = weight; - BodyColor = bodyColor; AdditionalColor = additionalColor; Rockets = rockets; Bombs = bombs; } - } } diff --git a/ProjStormtrooper/ProjStormtrooper/IMoveableObject.cs b/ProjStormtrooper/ProjStormtrooper/IMoveableObject.cs new file mode 100644 index 0000000..f7f162f --- /dev/null +++ b/ProjStormtrooper/ProjStormtrooper/IMoveableObject.cs @@ -0,0 +1,16 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace ProjStormtrooper +{ + public interface IMoveableObject + { + ObjectParameters? GetObjectPosition { get; } + int GetStep { get; } + bool CheckCanMove(Direction direction); + void MoveObject(Direction direction); + } +} diff --git a/ProjStormtrooper/ProjStormtrooper/MoveToCenter.cs b/ProjStormtrooper/ProjStormtrooper/MoveToCenter.cs new file mode 100644 index 0000000..f226105 --- /dev/null +++ b/ProjStormtrooper/ProjStormtrooper/MoveToCenter.cs @@ -0,0 +1,55 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace ProjStormtrooper +{ + public class MoveToCenter : AbstractStrategy + { + protected override bool IsTargetDestinaion() + { + 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/ProjStormtrooper/ProjStormtrooper/MoveToRightBottom.cs b/ProjStormtrooper/ProjStormtrooper/MoveToRightBottom.cs new file mode 100644 index 0000000..9381f67 --- /dev/null +++ b/ProjStormtrooper/ProjStormtrooper/MoveToRightBottom.cs @@ -0,0 +1,38 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace ProjStormtrooper +{ + public class MoveToRightBottom : AbstractStrategy + { + protected override bool IsTargetDestinaion() + { + var objParams = GetObjectParameters; + if (objParams == null) + { + return false; + } + return objParams.RightBorder >= FieldWidth - GetStep() && objParams.DownBorder >= FieldHeight - GetStep(); + } + + protected override void MoveToTarget() + { + var objParams = GetObjectParameters; + if (objParams == null) + { + return; + } + if (objParams.RightBorder < FieldWidth - GetStep()) + { + MoveRight(); + } + if (objParams.TopBorder < FieldHeight - GetStep()) + { + MoveDown(); + } + } + } +} diff --git a/ProjStormtrooper/ProjStormtrooper/ObjectParameters.cs b/ProjStormtrooper/ProjStormtrooper/ObjectParameters.cs new file mode 100644 index 0000000..9f26abc --- /dev/null +++ b/ProjStormtrooper/ProjStormtrooper/ObjectParameters.cs @@ -0,0 +1,30 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace ProjStormtrooper +{ + 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; + + public ObjectParameters(int x, int y, int width, int height) + { + _x = x; + _y = y; + _width = width; + _height = height; + } + } +} diff --git a/ProjStormtrooper/ProjStormtrooper/Program.cs b/ProjStormtrooper/ProjStormtrooper/Program.cs index 4033df8..a1edc17 100644 --- a/ProjStormtrooper/ProjStormtrooper/Program.cs +++ b/ProjStormtrooper/ProjStormtrooper/Program.cs @@ -2,7 +2,6 @@ namespace ProjStormtrooper { internal static class Program { - [STAThread] static void Main() { diff --git a/ProjStormtrooper/ProjStormtrooper/Status.cs b/ProjStormtrooper/ProjStormtrooper/Status.cs new file mode 100644 index 0000000..b6dad5d --- /dev/null +++ b/ProjStormtrooper/ProjStormtrooper/Status.cs @@ -0,0 +1,15 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace ProjStormtrooper +{ + public enum Status + { + NotInit, + InProgress, + Finish + } +} diff --git a/ProjStormtrooper/ProjStormtrooper/Stormtrooper.Designer.cs b/ProjStormtrooper/ProjStormtrooper/Stormtrooper.Designer.cs index 767045d..e676222 100644 --- a/ProjStormtrooper/ProjStormtrooper/Stormtrooper.Designer.cs +++ b/ProjStormtrooper/ProjStormtrooper/Stormtrooper.Designer.cs @@ -30,11 +30,14 @@ { System.ComponentModel.ComponentResourceManager resources = new System.ComponentModel.ComponentResourceManager(typeof(Stormtrooper)); pictureBoxStormtrooper = new PictureBox(); - buttonCreate = new Button(); buttonDown = new Button(); buttonUp = new Button(); buttonLeft = new Button(); buttonRight = new Button(); + buttonCreateStormtrooper = new Button(); + buttonCreatePlane = new Button(); + buttonStep = new Button(); + comboBoxStrategy = new ComboBox(); ((System.ComponentModel.ISupportInitialize)pictureBoxStormtrooper).BeginInit(); SuspendLayout(); // @@ -49,17 +52,6 @@ pictureBoxStormtrooper.TabStop = false; pictureBoxStormtrooper.Click += buttonMove_Click; // - // buttonCreate - // - buttonCreate.Anchor = AnchorStyles.Bottom | AnchorStyles.Left; - buttonCreate.Location = new Point(12, 426); - buttonCreate.Name = "buttonCreate"; - buttonCreate.Size = new Size(75, 23); - buttonCreate.TabIndex = 1; - buttonCreate.Text = "Создать"; - buttonCreate.UseVisualStyleBackColor = true; - buttonCreate.Click += buttonCreate_Click; - // // buttonDown // buttonDown.Anchor = AnchorStyles.Bottom | AnchorStyles.Right; @@ -108,16 +100,65 @@ buttonRight.UseVisualStyleBackColor = true; buttonRight.Click += buttonMove_Click; // + // buttonCreateStormtrooper + // + buttonCreateStormtrooper.Anchor = AnchorStyles.Bottom | AnchorStyles.Left; + buttonCreateStormtrooper.Location = new Point(12, 428); + buttonCreateStormtrooper.Margin = new Padding(3, 2, 3, 2); + buttonCreateStormtrooper.Name = "buttonCreateStormtrooper"; + buttonCreateStormtrooper.Size = new Size(176, 22); + buttonCreateStormtrooper.TabIndex = 7; + buttonCreateStormtrooper.Text = "Создать штурмовик"; + buttonCreateStormtrooper.UseVisualStyleBackColor = true; + buttonCreateStormtrooper.Click += buttonCreateStormtrooper_Click; + // + // buttonCreatePlane + // + buttonCreatePlane.Anchor = AnchorStyles.Bottom | AnchorStyles.Left; + buttonCreatePlane.Location = new Point(194, 428); + buttonCreatePlane.Margin = new Padding(3, 2, 3, 2); + buttonCreatePlane.Name = "buttonCreatePlane"; + buttonCreatePlane.Size = new Size(176, 22); + buttonCreatePlane.TabIndex = 8; + buttonCreatePlane.Text = "Создать самолет"; + buttonCreatePlane.UseVisualStyleBackColor = true; + buttonCreatePlane.Click += buttonCreatePlane_Click_1; + // + // buttonStep + // + buttonStep.Location = new Point(790, 38); + buttonStep.Margin = new Padding(3, 2, 3, 2); + buttonStep.Name = "buttonStep"; + buttonStep.Size = new Size(82, 22); + buttonStep.TabIndex = 9; + buttonStep.Text = "Шаг"; + buttonStep.UseVisualStyleBackColor = true; + buttonStep.Click += buttonStep_Click; + // + // comboBoxStrategy + // + comboBoxStrategy.DropDownStyle = ComboBoxStyle.DropDownList; + comboBoxStrategy.FormattingEnabled = true; + comboBoxStrategy.Items.AddRange(new object[] { "MoveToCenter", "MoveToRightBottom" }); + comboBoxStrategy.Location = new Point(739, 11); + comboBoxStrategy.Margin = new Padding(3, 2, 3, 2); + comboBoxStrategy.Name = "comboBoxStrategy"; + comboBoxStrategy.Size = new Size(133, 23); + comboBoxStrategy.TabIndex = 10; + // // Stormtrooper // AutoScaleDimensions = new SizeF(7F, 15F); AutoScaleMode = AutoScaleMode.Font; ClientSize = new Size(884, 461); + Controls.Add(comboBoxStrategy); + Controls.Add(buttonStep); + Controls.Add(buttonCreatePlane); + Controls.Add(buttonCreateStormtrooper); Controls.Add(buttonRight); Controls.Add(buttonLeft); Controls.Add(buttonUp); Controls.Add(buttonDown); - Controls.Add(buttonCreate); Controls.Add(pictureBoxStormtrooper); Name = "Stormtrooper"; StartPosition = FormStartPosition.CenterScreen; @@ -130,10 +171,13 @@ #endregion private PictureBox pictureBoxStormtrooper; - private Button buttonCreate; private Button buttonDown; private Button buttonUp; private Button buttonLeft; private Button buttonRight; + private Button buttonCreateStormtrooper; + private Button buttonCreatePlane; + private Button buttonStep; + private ComboBox comboBoxStrategy; } } \ No newline at end of file diff --git a/ProjStormtrooper/ProjStormtrooper/Stormtrooper.cs b/ProjStormtrooper/ProjStormtrooper/Stormtrooper.cs index 058ed0c..44b07db 100644 --- a/ProjStormtrooper/ProjStormtrooper/Stormtrooper.cs +++ b/ProjStormtrooper/ProjStormtrooper/Stormtrooper.cs @@ -1,74 +1,118 @@ +using ProjStormtrooper; using System.ComponentModel; using System.Windows.Forms.Layout; namespace ProjStormtrooper { public partial class Stormtrooper : Form - { - private DrawingStormtrooper? _drawingStormtrooper; - + { + private DrawingPlane? _drawingPlane; + private AbstractStrategy? _abstractStrategy; + public Stormtrooper() { InitializeComponent(); } - private void Draw() { - if (_drawingStormtrooper == null) + if (_drawingPlane == null) { return; } - Bitmap bmp = new(pictureBoxStormtrooper.Width, - pictureBoxStormtrooper.Height); + Bitmap bmp = new(pictureBoxStormtrooper.Width, pictureBoxStormtrooper.Height); Graphics g = Graphics.FromImage(bmp); - _drawingStormtrooper.DrawStormtrooper(g); + _drawingPlane.DrawTransport(g); pictureBoxStormtrooper.Image = bmp; } - - private void buttonCreate_Click(object sender, EventArgs e) + + private void buttonCreateStormtrooper_Click(object sender, EventArgs e) { Random random = new(); - _drawingStormtrooper = new DrawingStormtrooper(); - _drawingStormtrooper.Init(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)), - Convert.ToBoolean(random.Next(0, 2)), - Convert.ToBoolean(random.Next(0, 2)), - pictureBoxStormtrooper.Width, pictureBoxStormtrooper.Height); - _drawingStormtrooper.SetPosition(random.Next(0, 0), - random.Next(0, 0)); + _drawingPlane = new DrawingStormtrooper( + 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)), + Convert.ToBoolean(random.Next(0, 2)), + Convert.ToBoolean(random.Next(0, 2)), + pictureBoxStormtrooper.Width, + pictureBoxStormtrooper.Height + ); + _drawingPlane.SetPosition(random.Next(10, 100), random.Next(10, 100)); Draw(); - } - + private void buttonMove_Click(object sender, EventArgs e) { - if (_drawingStormtrooper == null) + if (_drawingPlane == null) { return; } - string name = ((Button)sender)?.Name ?? string.Empty; - switch (name) + string buttonName = ((Button)sender)?.Name ?? string.Empty; + switch (buttonName) { case "buttonUp": - _drawingStormtrooper.MoveTransport(Direction.Up); + _drawingPlane.MoveTransport(Direction.Up); break; case "buttonDown": - _drawingStormtrooper.MoveTransport(Direction.Down); + _drawingPlane.MoveTransport(Direction.Down); break; case "buttonLeft": - _drawingStormtrooper.MoveTransport(Direction.Left); + _drawingPlane.MoveTransport(Direction.Left); break; case "buttonRight": - _drawingStormtrooper.MoveTransport(Direction.Right); + _drawingPlane.MoveTransport(Direction.Right); break; } Draw(); - } + private void buttonStep_Click(object sender, EventArgs e) + { + if (_drawingPlane == null) + { + return; + } + if (comboBoxStrategy.Enabled) + { + _abstractStrategy = comboBoxStrategy.SelectedIndex switch + { + 0 => new MoveToCenter(), + 1 => new MoveToRightBottom(), + _ => null, + }; + if (_abstractStrategy == null) + { + return; + } + _abstractStrategy.SetData(new DrawingObjectPlane(_drawingPlane), pictureBoxStormtrooper.Width, pictureBoxStormtrooper.Height); + comboBoxStrategy.Enabled = false; + } + if (_abstractStrategy == null) + { + return; + } + _abstractStrategy.MakeStep(); + Draw(); + if (_abstractStrategy.GetStatus() == Status.Finish) + { + comboBoxStrategy.Enabled = true; + _abstractStrategy = null; + } + } + + private void buttonCreatePlane_Click_1(object sender, EventArgs e) + { + Random random = new(); + _drawingPlane = new DrawingPlane( + random.Next(100, 300), + random.Next(1000, 3000), + Color.FromArgb(random.Next(0, 256), random.Next(0, 256), random.Next(0, 256)), + pictureBoxStormtrooper.Width, + pictureBoxStormtrooper.Height + ); + _drawingPlane.SetPosition(random.Next(10, 100), random.Next(10, 100)); + Draw(); + } } } \ No newline at end of file diff --git a/ProjStormtrooper/ProjStormtrooper/Stormtrooper.resx b/ProjStormtrooper/ProjStormtrooper/Stormtrooper.resx index bfe2378..1bda3d9 100644 --- a/ProjStormtrooper/ProjStormtrooper/Stormtrooper.resx +++ b/ProjStormtrooper/ProjStormtrooper/Stormtrooper.resx @@ -123,7 +123,7 @@ iVBORw0KGgoAAAANSUhEUgAAANQAAADuCAMAAAB24dnhAAAABGdBTUEAALGPC/xhBQAAAHtQTFRFAAAA ////7u7u7e3t9fX1+Pj48/Pz+/v79PT0fn5+UFBQ5+fnMzMzs7Oz19fXb29vjY2NtLS00tLSpaWlHh4e vLy8U1NTOzs7CgoKTExMysrK4eHhLy8vFBQUNzc3a2trk5OTXV1denp6JycnnJycIyMjWlpaREREw8PD - TPw7owAAAAlwSFlzAAAOwAAADsABataJCQAACpZJREFUeF7tnel2ozgQhQNiceI4e2dzMr1MT3e//xNO + TPw7owAAAAlwSFlzAAAOvgAADr4B6kKxwAAACpZJREFUeF7tnel2ozgQhQNiceI4e2dzMr1MT3e//xNO lbgFRVo2SyQWH30/cuIbTOmmMCoJgc/SNDVJjaGXlgJCkpSimQxKkmS1lifJmWfObYhchwAbSKkpoSQJ lJaLaApKNDWcaMqjqVZEtMUbMVMxU8vMVK11m0rxO+EyBSVNlSkoaRrOFALYEKDOVNqYKqC0TPEPI2h7 QmMvh2Ja/7wApjiEPiyEJmwBxSgrKRRjKlMwq3JWH3QqZ+7DPIQpCnHgWAeu/EAhPmsqC5KpmU3FTPUj @@ -176,7 +176,7 @@ iVBORw0KGgoAAAANSUhEUgAAANQAAADuCAMAAAB24dnhAAAABGdBTUEAALGPC/xhBQAAAHtQTFRFAAAA ////7u7u7e3t9fX1+Pj48/Pz+/v79PT0fn5+UFBQ5+fnMzMzs7Oz19fXb29vjY2NtLS00tLSpaWlHh4e vLy8U1NTOzs7CgoKTExMysrK4eHhLy8vFBQUNzc3a2trk5OTXV1denp6JycnnJycIyMjWlpaREREw8PD - TPw7owAAAAlwSFlzAAAOwAAADsABataJCQAACthJREFUeF7tnet62ygURSXr5tS5p0kTO22nTWam7/+E + TPw7owAAAAlwSFlzAAAOvgAADr4B6kKxwAAACthJREFUeF7tnet62ygURSXr5tS5p0kTO22nTWam7/+E c4ANHNlYxjLIyMP60a/aUYJWkMwRwk6xMJSGCsmiRVCWjc6qGklZ1ibrkJRli2hRISDEZtu9rRuWOZro HE3YZhskvAnbLBI0O5VUc1W8V0sEhKOJ2UmVv4qi+FghIBxNzEyqKp/IqSjeEBCOJmYmVf4lnYriH7Oj o4l5SZXPcCqKn0jmL/X8CiXiHpmjiVlJPX6HkARWjibmJHV7DR1wI1NHE95SjmaRoFmXlPnpXArJYsGk @@ -231,7 +231,7 @@ iVBORw0KGgoAAAANSUhEUgAAAO4AAADUCAMAAACs0e/bAAAABGdBTUEAALGPC/xhBQAAAHtQTFRFAAAA ////7u7u7e3t9fX1+Pj48/Pz+/v79PT0fn5+UFBQ5+fnMzMzs7Oz19fXb29vjY2NtLS00tLSpaWlHh4e vLy8U1NTOzs7CgoKTExMysrK4eHhLy8vFBQUNzc3a2trk5OTXV1denp6JycnnJycIyMjWlpaREREw8PD - TPw7owAAAAlwSFlzAAAOwAAADsABataJCQAACkhJREFUeF7lnQ17ozYWhSMEiNq7aZNt2k4yu/3Ybjv/ + TPw7owAAAAlwSFlzAAAOvgAADr4B6kKxwAAACkhJREFUeF7lnQ17ozYWhSMEiNq7aZNt2k4yu/3Ybjv/ /xfukThCF1s2AmMHiTdPnxmfcXz9Ai4XIcOTGtCVh4FSZshaJko1PtMNE6XqITNMlGoZVZoB6B/Xx1Zk jyrreLyuVs/fq43r6tXq6ubl6Uuq7nplidT1yLoeWdcj63pEXSZa1sXrvPzydBjpeu5Z1vPEPwH/DTCQ 1cI7qJnE30GoFt5BqIYHPzw9QTeUeFBZ8sS1DJiAYfuSdRmN6vpM1GUkty8mbvuytk6X0YPKeh6pi7X2 @@ -283,7 +283,7 @@ iVBORw0KGgoAAAANSUhEUgAAAO4AAADUCAMAAACs0e/bAAAABGdBTUEAALGPC/xhBQAAAHtQTFRFAAAA ////7u7u7e3t9fX1+Pj48/Pz+/v79PT0fn5+UFBQ5+fnMzMzs7Oz19fXb29vjY2NtLS00tLSpaWlHh4e vLy8U1NTOzs7CgoKTExMysrK4eHhLy8vFBQUNzc3a2trk5OTXV1denp6JycnnJycIyMjWlpaREREw8PD - TPw7owAAAAlwSFlzAAAOwAAADsABataJCQAACPxJREFUeF7lnXtjmjAUxcMbq9W2a31Uu9a22/r9P+Fu + TPw7owAAAAlwSFlzAAAOvgAADr4B6kKxwAAACPxJREFUeF7lnXtjmjAUxcMbq9W2a31Uu9a22/r9P+Fu wklycay+ECH3+MfWQ+TwQ4RLDKAipyS2ghFFhfNyOFGUWS/J4ERR6rwCThTlsOIEBgmO8T4xyy5j4+vh blaV12XsFXFv1MdUe13GXhVXTR7I6zL2urhKPcnCfXkShavUD2+iUdC4jBeNeoCbXA5XzbK8ejsaXTCW 48Lhq7SAE8clHMqFE8csF04cN+R6jGZcNSrNPDuIjVXihGkkGAlbuQWcJEnh6BVu5Zcgh5OwFR7DqUUw