diff --git a/AccordionBus/AccordionBus/MapWithSetBusesGeneric.cs b/AccordionBus/AccordionBus/MapWithSetBusesGeneric.cs new file mode 100644 index 0000000..1fc2b82 --- /dev/null +++ b/AccordionBus/AccordionBus/MapWithSetBusesGeneric.cs @@ -0,0 +1,182 @@ +using AccordionBus; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace AccordionBus +{ + /// + /// Карта с набором объектов под нее + /// + /// + /// + internal class MapWithSetBusesGeneric + where T : class, IDrawningObject + where U : AbstractMap + { + /// + /// Ширина окна отрисовки + /// + private readonly int _pictureWidth; + /// + /// Высота окна отрисовки + /// + private readonly int _pictureHeight; + /// + /// Размер занимаемого объектом места (ширина) + /// + private readonly int _placeSizeWidth = 400; + /// + /// Размер занимаемого объектом места (высота) + /// + private readonly int _placeSizeHeight = 100; + /// + /// Набор объектов + /// + private readonly SetBusesGeneric _setBuses; + /// + /// Карта + /// + private readonly U _map; + /// + /// Конструктор + /// + /// + /// + /// + public MapWithSetBusesGeneric(int picWidth, int picHeight, U map) + { + int width = picWidth / _placeSizeWidth; + int height = picHeight / _placeSizeHeight; + _setBuses = new SetBusesGeneric(width * height); + _pictureWidth = picWidth; + _pictureHeight = picHeight; + _map = map; + } + /// + /// Перегрузка оператора сложения + /// + /// + /// + /// + public static bool operator +(MapWithSetBusesGeneric map, T bus) + { + return map._setBuses.Insert(bus); + } + /// + /// Перегрузка оператора вычитания + /// + /// + /// + /// + public static bool operator -(MapWithSetBusesGeneric map, int position) + { + return map._setBuses.Remove(position); + } + /// + /// Вывод всего набора объектов + /// + /// + public Bitmap ShowSet() + { + Bitmap bmp = new(_pictureWidth, _pictureHeight); + Graphics gr = Graphics.FromImage(bmp); + DrawBackground(gr); + DrawBuses(gr); + return bmp; + } + /// + /// Просмотр объекта на карте + /// + /// + public Bitmap ShowOnMap() + { + Shaking(); + for (int i = 0; i < _setBuses.Count; i++) + { + var bus = _setBuses.Get(i); + if (bus != null) + { + return _map.CreateMap(_pictureWidth, _pictureHeight, bus); + } + } + return new(_pictureWidth, _pictureHeight); + } + /// + /// Перемещение объекта по карте + /// + /// + /// + public Bitmap MoveObject(Direction direction) + { + if (_map != null) + { + return _map.MoveObject(direction); + } + return new(_pictureWidth, _pictureHeight); + } + /// + /// "Взбалтываем" набор, чтобы все элементы оказались в начале + /// + private void Shaking() + { + int j = _setBuses.Count - 1; + for (int i = 0; i < _setBuses.Count; i++) + { + if (_setBuses.Get(i) == null) + { + for (; j > i; j--) + { + var bus = _setBuses.Get(j); + if (bus != null) + { + _setBuses.Insert(bus, i); + _setBuses.Remove(j); + break; + } + } + if (j <= i) + { + return; + } + } + } + } + /// + /// Метод отрисовки фона + /// + /// + private void DrawBackground(Graphics g) + { + Pen pen = new(Color.White, 3); + Brush brush = new SolidBrush(Color.Gray); + g.FillRectangle(brush, 0, 0, _pictureWidth, _pictureHeight); + for (int i = 0; i < _pictureWidth / _placeSizeWidth; i++) + { + for (int j = 0; j < _pictureHeight / _placeSizeHeight + 1; ++j) + { + g.DrawLine(pen, i * _placeSizeWidth, j * _placeSizeHeight, i * _placeSizeWidth + _placeSizeWidth / 2, j * _placeSizeHeight); + } + g.DrawLine(pen, i * _placeSizeWidth, 0, i * _placeSizeWidth, (_pictureHeight / _placeSizeHeight) * _placeSizeHeight); + } + } + /// + /// Метод прорисовки объектов + /// + /// + private void DrawBuses(Graphics g) + { + int numberOfSeatsInWidth = _pictureWidth / _placeSizeWidth; + int numberOfSeatsInHeight = _pictureHeight / _placeSizeHeight; + int rightLine = (numberOfSeatsInWidth - 1) * _placeSizeWidth; + int bottomLine = (numberOfSeatsInHeight - 1) * _placeSizeHeight; + for (int i = 0; i < _setBuses.Count; i++) + { + _setBuses.Get(i)?.SetObject(rightLine - i % numberOfSeatsInWidth * _placeSizeWidth, bottomLine - i / numberOfSeatsInWidth * _placeSizeHeight, _pictureWidth, _pictureHeight); + _setBuses.Get(i)?.DrawningObject(g); + } + } + } +} \ No newline at end of file diff --git a/AccordionBus/AccordionBus/SetBusesGeneric.cs b/AccordionBus/AccordionBus/SetBusesGeneric.cs new file mode 100644 index 0000000..17ae571 --- /dev/null +++ b/AccordionBus/AccordionBus/SetBusesGeneric.cs @@ -0,0 +1,103 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace AccordionBus +{ + /// + /// Параметризованный набор объектов + /// + /// + internal class SetBusesGeneric + where T : class + { + /// + /// Массив объектов, которые храним + /// + private readonly T[] _places; + /// + /// Количество объектов в массиве + /// + public int Count => _places.Length; + /// + /// Конструктор + /// + /// + public SetBusesGeneric(int count) + { + _places = new T[count]; + } + /// + /// Добавление объекта в набор + /// + /// Добавляемый автобус + /// + public bool Insert(T bus) + { + return Insert(bus, 0); + } + /// + /// Добавление объекта в набор на конкретную позицию + /// + /// Добавляемый автобус + /// Позиция + /// + public bool Insert(T bus, int position) + { + //проверка позиции + if (position < 0 || position >= Count) + { + return false; + } + //поиск пустой позиции + int positionEmpty = position; + for (; positionEmpty < Count; positionEmpty++) + { + if (_places[positionEmpty] == null) + { + break; + } + } + if (positionEmpty == Count) + { + return false; + } + //сдвиг вправо + for (; positionEmpty > position; positionEmpty--) + { + _places[positionEmpty] = _places[positionEmpty - 1]; + } + _places[position] = bus; + return true; + } + /// + /// Удаление объекта из набора с конкретной позиции + /// + /// + /// + public bool Remove(int position) + { + if (position < 0 || position >= Count) + { + return false; + } + _places[position] = null; + return true; + } + /// + /// Получение объекта из набора по позиции + /// + /// + /// + public T Get(int position) + { + if (position < 0 || position >= Count) + { + return null; + } + return _places[position]; + } + } +} \ No newline at end of file