Главная » 2D графика » Создание редактора карт в стратегиях типа WarCraft

RSS

Создание редактора карт в стратегиях типа WarCraft

Не нравитсяНравится   Рейтинг +2

Пример написан на Delphi 3 Professional, с использованием компонент библиотеки DelphiX для DirectX 6.0

Модуль MapDat

1
2
3
4
5
6
7
8
9
10
11
12
13
// Определение класса Matrix5
Type TMatrix5 = class(TObject)
private
  Matrix : array[0..4,0..4] of byte;
  Vector : array[0..24] of byte;
public
  function GetBaseIndex( ElementIndex : Integer ): Integer;
  Function GetAdditionalIndex( ElementIndex : Integer ): Integer;
  procedure Fill(X,Y : Integer);
  procedure Place(X,Y : Integer);
  procedure Culculate(X,Y : Integer; BrushIndex : Integer );
  procedure Draw(X,Y : Integer; BrushIndex : Integer );
end;

Внутри класса определены переменные в виде матрицы 5х5 и вектора. Некогда я думал, что это упростит написание программы, сейчас я думаю, что можно воспользоваться только вектором. Методы GetBaseIndex и GetAdditionalIndex мы уже рассматривали, рассмотрим остальные:

Метод Fill(X,Y : Integer); Заполняет матрицу и вектор 25-ю элементами карты. Х,Y – указывает на центральный элемент.

1
2
3
4
5
6
7
8
9
10
11
procedure TMatrix5.Fill(X,Y : Integer);
var
  i,j : Integer;
begin
  for j := 0 to 4 do
    for i := 0 to 4 do
      Matrix[i,j] := MainForm.GetElement(X - 2 + i,Y - 2 + j);
  for j :=0 to 4 do
    for i := 0 to 4 do
      Vector[j*5 + i] := Matrix[i,j];
end;

Метод Place(x,y : Integer); Выполняет процедуру обратную методу Fill. То есть кладет матрицу 5х5 на карту.

1
2
3
4
5
6
7
8
9
10
11
procedure TMatrix5.Place(X,Y : Integer);
var
  i,j : Integer;
begin
  for j := 0 to 4 do
    for i := 0 to 4 do
      Matrix[i,j] := Vector[j*5 + i];
  for j := 0 to 4 do
    for i := 0 to 4 do
      MainForm.PutElement(X - 2 + i,Y - 2 + j, Matrix[i,j] );
end;

Метод Draw(X,Y : Integer; BrushIndex : Integer);

1
2
3
4
5
procedure TMatrix5.Draw(X,Y : Integer; BrushIndex : Integer);
begin
  Self.Culculate(X,Y,BrushIndex);
  Self.Place(X,Y);
end;

Выполняет методы Culculate , а затем Place. X,Y – указывают центральный элемент в матрице 5х5, BrushIndex – индекс активной земли. (0-вода,1-трава,2-камни,3- переходный тип – земля).

Прежде чем перейти к основному методу данного модуля – Culculate, покажу вам созданные таблицы.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
const BasicTable : array[0..24,0..15] of byte = (
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
( 9, 1, 6, 8, 4, 5, 6,15, 8, 9, 1,14, 4, 5,14,16),
( 1, 1, 6,15, 5, 5, 6,15,15, 1, 1, 6, 5, 5, 6,16),
(10, 1, 2, 7,15, 5, 6, 7,15, 1,10, 2, 7,13, 6,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
( 4, 5,15, 8, 4, 5,15,15, 8, 4, 5, 8, 4, 5, 8,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
( 2, 6, 2, 7,15,15, 6, 7,15, 6, 2, 2, 7, 7, 6,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(12, 5, 7, 3, 4, 5,15, 7, 8, 4,13, 3,12,13, 8,16),
( 3,15, 7, 3, 8,15,15, 7, 8, 8, 7, 3, 3, 7, 8,16),
(11, 6, 2, 3, 8,15, 6, 7, 8,14, 2,11, 3, 7,14,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16));
 
EqualTable : array[0..24,0..15] of byte = (
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,10,16,16,12,13, 2,16, 3, 0,16,16,16,16,11, 7),
(16, 0,11,16,12,12,11, 3, 3, 0, 0,16,16,12,11, 3),
(16, 9,11,16,16, 4,14, 3,16,16, 0,16,16,12,16, 8),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,10,16,11, 0,10, 2, 2,11, 0,16,16, 0,10,11, 2),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16, 9, 0,12,16, 4, 9,12, 4,16, 0, 0,16,12, 9, 4),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,16,16,11, 9, 1,16, 2,14,16,16,16, 0,10,16, 6),
(16,16,10, 0, 9, 1, 1,10, 9,16,16, 0, 0,10, 9, 1),
(16,16,10,12,16,16, 1,13, 4,16,16, 0,16,16, 9, 5),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16),
(16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16));
 
NotEqualTable : array[0..24,0..15] of byte = (
( 9, 1, 6, 8, 4, 5, 6,15, 8, 9, 1,14, 4, 5,14,15),
( 1, 1, 6,15, 5, 5, 6,15,15, 1, 1, 6, 5, 5, 6,15),
( 1, 1, 6,15, 5, 5, 6,15,15, 1, 1, 6, 5, 5, 6,15),
( 1, 1, 6,15, 5, 5, 6,15,15, 1, 1, 6, 5, 5, 6,15),
(10, 1, 2, 7, 5, 5, 6, 7,15, 1,10, 2,13,13, 6,15),
( 4, 5,15, 8, 4, 5,15,15, 8, 4, 5, 8, 4, 5, 8,15), (23,23,23,23,23,23,23,23,23,23,23,23,23,23,23,23), (19,19,19,19,19,19,19,19,19,19,19,19,19,19,19,19), (24,24,24,24,24,24,24,24,24,24,24,24,24,24,24,24),
( 2, 6, 2, 7,15,15, 6, 7,15, 6, 2, 2, 7, 7, 6,15),
( 4, 5,15, 8, 4, 5,15,15, 8, 4, 5, 8, 4, 5, 8,15), (18,18,18,18,18,18,18,18,18,18,18,18,18,18,18,18), (16,16,16,16,16,16,16,16,16,16,16,16,16,16,16,16), (20,20,20,20,20,20,20,20,20,20,20,20,20,20,20,20),
( 2, 6, 2, 7,15,15, 6, 7,15, 6, 2, 2, 7, 7, 6,15),
( 4, 5,15, 8, 4, 5,15,15, 8, 4, 5, 8, 4, 5, 8,15), (22,22,22,22,22,22,22,22,22,22,22,22,22,22,22,22), (17,17,17,17,17,17,17,17,17,17,17,17,17,17,17,17), (21,21,21,21,21,21,21,21,21,21,21,21,21,21,21,21),
( 2, 6, 2, 7,15,15, 6, 7,15, 6, 2, 2, 7, 7, 6,15),
(12, 5, 7, 3, 4, 5,15, 7, 8, 4,15,13,12,13, 8,15),
( 3,15, 7, 3, 8,15,15, 7, 8, 8, 7, 3, 3, 7, 8,15),
( 3,15, 7, 3, 8,15,15, 7, 8, 8, 7, 3, 3, 7, 8,15),
( 3,15, 7, 3, 8,15,15, 7, 8, 8, 7, 3, 3, 7, 8,15),
(11, 6, 2, 3,15,15, 6, 7, 8,14, 2,11, 3, 7,14,15));
 
BasicTable - используется, когда мы рисуем переходным типом земли.
EqualTable - испльзуется, когда прежняя земля в ячейке равна активной.
NotEqualTable - испльзуется, когда прежняя земля в ячейке не равна активной.

Заметьте, что в таблицах иногда используется число 16, а в таблице NotEqualTable и больше. Число 16 указывает, что текстура не изменится в результате наших воздействий. Честно говоря, я просто не помню зачем я вводил числа больше 16-ти, я написал эту программу год назад. В дальнейшем в теле модуля Culculate я от этих чисел отнимаю 16, а зачем – Бог его знает. Кому охота – можете исправить, но программа работает.

Да, на первый взгляд таблицы выглядят немного устрашающе. Кто-то может спросить: Зачем громоздить такие кошмары? Неужели не найти формулу для расчета? Ведь так будет намного компактнее. Но я отвечу, что программы на ассемблере выглядят тоже страшновато, зато работают намного быстрее, чем на других языках. Может и есть формула, но я уверен, что она непростая, а стало быть работать будет намного медленнее чем простое обращение к массиву.

Страницы : 1 2 3 4