From 5f133aba81780a5903e8afea9afa75f6aeb094b4 Mon Sep 17 00:00:00 2001
From: jsalmon3 <>
Date: Sat, 4 Oct 2003 04:26:50 +0000
Subject: [PATCH] Minimap size is configurable

---
 src/editor/editloop.cpp    |  8 ++--
 src/include/stratagus.h    |  3 --
 src/include/ui.h           |  2 +
 src/map/minimap.cpp        | 77 ++++++++++++++++++++------------------
 src/stratagus/mainloop.cpp |  2 +-
 src/ui/mouse.cpp           | 12 +++---
 src/ui/script_ui.cpp       | 36 +++++++++++++-----
 src/ui/ui.cpp              | 13 ++++---
 8 files changed, 88 insertions(+), 65 deletions(-)

diff --git a/src/editor/editloop.cpp b/src/editor/editloop.cpp
index cea6bec40..88a45d6ed 100644
--- a/src/editor/editloop.cpp
+++ b/src/editor/editloop.cpp
@@ -1578,8 +1578,8 @@ local void EditorCallbackMouse(int x, int y)
     //
     //	Minimap
     //
-    if (x >= TheUI.MinimapPosX && x < TheUI.MinimapPosX + MINIMAP_W &&
-	    y >= TheUI.MinimapPosY && y < TheUI.MinimapPosY + MINIMAP_H) {
+    if (x >= TheUI.MinimapPosX && x < TheUI.MinimapPosX + TheUI.MinimapW &&
+	    y >= TheUI.MinimapPosY && y < TheUI.MinimapPosY + TheUI.MinimapH) {
 	CursorOn = CursorOnMinimap;
     }
 
@@ -1731,8 +1731,8 @@ local void EditorCallbackMouse(int x, int y)
     //
     //  Minimap
     //
-    if (x >= TheUI.MinimapPosX && x < TheUI.MinimapPosX + MINIMAP_W &&
-	    y >= TheUI.MinimapPosY && y < TheUI.MinimapPosY + MINIMAP_H) {
+    if (x >= TheUI.MinimapPosX && x < TheUI.MinimapPosX + TheUI.MinimapW &&
+	    y >= TheUI.MinimapPosY && y < TheUI.MinimapPosY + TheUI.MinimapH) {
 	CursorOn = CursorOnMinimap;
 	return;
     }
diff --git a/src/include/stratagus.h b/src/include/stratagus.h
index 7d98d333a..a5d449b72 100644
--- a/src/include/stratagus.h
+++ b/src/include/stratagus.h
@@ -356,9 +356,6 @@ extern char NameLine[];
 #define MAXMAP_W	50		/// Maximum map width in tiles on screen
 #define MAXMAP_H	40		/// Maximum map height in tiles
 
-#define MINIMAP_W	128		/// Minimap width in pixels
-#define MINIMAP_H	128		/// Minimap height in pixels
-
     /// Scrolling area (<= 15 y)
 #define SCROLL_UP	15
     /// Scrolling area (>= VideoHeight-16 y)
diff --git a/src/include/ui.h b/src/include/ui.h
index abd65398b..1dcb2fb13 100644
--- a/src/include/ui.h
+++ b/src/include/ui.h
@@ -261,6 +261,8 @@ typedef struct _ui_ {
     GraphicConfig MinimapPanel;		/// minimap panel background
     int		MinimapPanelX;		/// minimap panel screen X position
     int		MinimapPanelY;		/// minimap panel screen Y position
+    int		MinimapW;		/// minimap screen Width
+    int		MinimapH;		/// minimap screen Height
     int		MinimapPosX;		/// minimap screen X position
     int		MinimapPosY;		/// minimap screen Y position
     int		ViewportCursorColor;	/// minimap cursor color
diff --git a/src/map/minimap.cpp b/src/map/minimap.cpp
index 51a56c75b..3f071d533 100644
--- a/src/map/minimap.cpp
+++ b/src/map/minimap.cpp
@@ -54,8 +54,8 @@
 
 local Graphic* MinimapTerrainGraphic;	/// generated minimap terrain
 local Graphic* MinimapGraphic;		/// generated minimap
-local int Minimap2MapX[MINIMAP_W];	/// fast conversion table
-local int Minimap2MapY[MINIMAP_H];	/// fast conversion table
+local int* Minimap2MapX;		/// fast conversion table
+local int* Minimap2MapY;		/// fast conversion table
 local int Map2MinimapX[MaxMapWidth];	/// fast conversion table
 local int Map2MinimapY[MaxMapHeight];	/// fast conversion table
 
@@ -109,7 +109,7 @@ global void UpdateMinimapXY(int tx, int ty)
     //	Pixel 7,6 7,14, 15,6 15,14 are taken for the minimap picture.
     //
     ty *= TheMap.Width;
-    for (my = MinimapY; my < MINIMAP_H - MinimapY; ++my) {
+    for (my = MinimapY; my < TheUI.MinimapH - MinimapY; ++my) {
 	y = Minimap2MapY[my];
 	if (y < ty) {
 	    continue;
@@ -118,7 +118,7 @@ global void UpdateMinimapXY(int tx, int ty)
 	    break;
 	}
 
-	for (mx = MinimapX; mx < MINIMAP_W - MinimapX; ++mx) {
+	for (mx = MinimapX; mx < TheUI.MinimapW - MinimapX; ++mx) {
 	    int tile;
 
 	    x = Minimap2MapX[mx];
@@ -130,7 +130,7 @@ global void UpdateMinimapXY(int tx, int ty)
 	    }
 
 	    tile = TheMap.Fields[x + y].Tile;
-	    ((unsigned char*)MinimapTerrainGraphic->Frames)[mx + my * MINIMAP_W] =
+	    ((unsigned char*)MinimapTerrainGraphic->Frames)[mx + my * TheUI.MinimapW] =
 		TheMap.Tiles[tile][7 + (mx % scale) * 8 + (6 + (my % scale) * 8) * TileSizeX];
 	}
     }
@@ -156,12 +156,12 @@ global void UpdateMinimapTerrain(void)
     //
     //	Pixel 7,6 7,14, 15,6 15,14 are taken for the minimap picture.
     //
-    for (my = MinimapY; my < MINIMAP_H - MinimapY; ++my) {
-	for (mx = MinimapX; mx < MINIMAP_W - MinimapX; ++mx) {
+    for (my = MinimapY; my < TheUI.MinimapH - MinimapY; ++my) {
+	for (mx = MinimapX; mx < TheUI.MinimapW - MinimapX; ++mx) {
 	    int tile;
 
 	    tile = TheMap.Fields[Minimap2MapX[mx] + Minimap2MapY[my]].Tile;
-	    ((unsigned char*)MinimapTerrainGraphic->Frames)[mx + my * MINIMAP_W] =
+	    ((unsigned char*)MinimapTerrainGraphic->Frames)[mx + my * TheUI.MinimapW] =
 		TheMap.Tiles[tile][7 + (mx % scale) * 8 + (6 + (my % scale) * 8) * TileSizeX];
 	}
     }
@@ -181,12 +181,12 @@ global void CreateMinimap(void)
     } else {
 	n = TheMap.Height;
     }
-    MinimapScale = (MINIMAP_W * MINIMAP_FAC) / n;
+    MinimapScale = (TheUI.MinimapW * MINIMAP_FAC) / n;
 
-    MinimapX = ((MINIMAP_W * MINIMAP_FAC) / MinimapScale - TheMap.Width) / 2;
-    MinimapY = ((MINIMAP_H * MINIMAP_FAC) / MinimapScale - TheMap.Height) / 2;
-    MinimapX = (MINIMAP_W - (TheMap.Width * MinimapScale) / MINIMAP_FAC) / 2;
-    MinimapY = (MINIMAP_H - (TheMap.Height * MinimapScale) / MINIMAP_FAC) / 2;
+    MinimapX = ((TheUI.MinimapW * MINIMAP_FAC) / MinimapScale - TheMap.Width) / 2;
+    MinimapY = ((TheUI.MinimapH * MINIMAP_FAC) / MinimapScale - TheMap.Height) / 2;
+    MinimapX = (TheUI.MinimapW - (TheMap.Width * MinimapScale) / MINIMAP_FAC) / 2;
+    MinimapY = (TheUI.MinimapH - (TheMap.Height * MinimapScale) / MINIMAP_FAC) / 2;
 
     DebugLevel0Fn("MinimapScale %d(%d), X off %d, Y off %d\n" _C_
 	MinimapScale / MINIMAP_FAC _C_ MinimapScale _C_ MinimapX _C_ MinimapY);
@@ -196,10 +196,12 @@ global void CreateMinimap(void)
     //
     // FIXME: this needs to be recalculated during map load - the map size
     // might have changed!
-    for (n = MinimapX; n < MINIMAP_W - MinimapX; ++n) {
+    Minimap2MapX = calloc(sizeof(int), TheUI.MinimapW * TheUI.MinimapH);
+    Minimap2MapY = calloc(sizeof(int), TheUI.MinimapW * TheUI.MinimapH);
+    for (n = MinimapX; n < TheUI.MinimapW - MinimapX; ++n) {
 	Minimap2MapX[n] = ((n - MinimapX) * MINIMAP_FAC) / MinimapScale;
     }
-    for (n = MinimapY; n < MINIMAP_H - MinimapY; ++n) {
+    for (n = MinimapY; n < TheUI.MinimapH - MinimapY; ++n) {
 	Minimap2MapY[n] = (((n - MinimapY) * MINIMAP_FAC) / MinimapScale) * TheMap.Width;
     }
     for (n = 0; n < TheMap.Width; ++n) {
@@ -209,11 +211,11 @@ global void CreateMinimap(void)
 	Map2MinimapY[n] = (n * MinimapScale) / MINIMAP_FAC;
     }
 
-    MinimapTerrainGraphic = NewGraphic(8, MINIMAP_W, MINIMAP_H);
-    memset(MinimapTerrainGraphic->Frames, 0, MINIMAP_W * MINIMAP_H);
-    MinimapGraphic = NewGraphic(8, MINIMAP_W, MINIMAP_H);
+    MinimapTerrainGraphic = NewGraphic(8, TheUI.MinimapW, TheUI.MinimapH);
+    memset(MinimapTerrainGraphic->Frames, 0, TheUI.MinimapW * TheUI.MinimapH);
+    MinimapGraphic = NewGraphic(8, TheUI.MinimapW, TheUI.MinimapH);
     MinimapGraphic->Pixels = VideoCreateNewPalette(GlobalPalette);
-    memset(MinimapGraphic->Frames, 0, MINIMAP_W * MINIMAP_H);
+    memset(MinimapGraphic->Frames, 0, TheUI.MinimapW * TheUI.MinimapH);
 
     UpdateMinimapTerrain();
 }
@@ -231,8 +233,10 @@ global void DestroyMinimap(void)
     }
     VideoSaveFree(MinimapGraphic);
     MinimapGraphic = NULL;
-    memset(Minimap2MapX, 0, MINIMAP_W * sizeof(int));
-    memset(Minimap2MapY, 0, MINIMAP_H * sizeof(int));
+    free(Minimap2MapX);
+    Minimap2MapX = NULL;
+    free(Minimap2MapY);
+    Minimap2MapY = NULL;
 }
 
 /**
@@ -263,20 +267,20 @@ global void UpdateMinimap(void)
     // FIXME: make the image really use colorkey
     // FIXME: I think this is only necessary on each map size change?
     //        Or maybe if you disable displaying terrain, too?
-    memset(MinimapGraphic->Frames, 0, MINIMAP_W * MINIMAP_H);
+    memset(MinimapGraphic->Frames, 0, TheUI.MinimapW * TheUI.MinimapH);
 
     //
     //	Draw the terrain
     //
     if (MinimapWithTerrain) {
-	for (my = 0; my < MINIMAP_H; ++my) {
-	    for (mx = 0; mx < MINIMAP_W; ++mx) {
+	for (my = 0; my < TheUI.MinimapH; ++my) {
+	    for (mx = 0; mx < TheUI.MinimapW; ++mx) {
 		if (IsMapFieldVisible(ThisPlayer, Minimap2MapX[mx], Minimap2MapY[my] / TheMap.Width) ||
 			(IsMapFieldExplored(ThisPlayer,Minimap2MapX[mx], Minimap2MapY[my] / TheMap.Width) &&
 			    ((mx & 1) == (my & 1))) ||
 			ReplayRevealMap) {
-		    ((unsigned char*)MinimapGraphic->Frames)[mx + my * MINIMAP_W] =
-			((unsigned char*)MinimapTerrainGraphic->Frames)[mx + my * MINIMAP_W];
+		    ((unsigned char*)MinimapGraphic->Frames)[mx + my * TheUI.MinimapW] =
+			((unsigned char*)MinimapTerrainGraphic->Frames)[mx + my * TheUI.MinimapW];
 		}
 	    }
 	}
@@ -314,18 +318,18 @@ global void UpdateMinimap(void)
 	    mx = 1 + MinimapX + Map2MinimapX[(*table)->X];
 	    my = 1 + MinimapY + Map2MinimapY[(*table)->Y];
 	    w = Map2MinimapX[type->TileWidth];
-	    if (mx + w >= MINIMAP_W) {	// clip right side
-		w = MINIMAP_W - mx;
+	    if (mx + w >= TheUI.MinimapW) {	// clip right side
+		w = TheUI.MinimapW - mx;
 	    }
 	    h0 = Map2MinimapY[type->TileHeight];
-	    if (my + h0 >= MINIMAP_H) {	// clip bottom side
-		h0 = MINIMAP_H - my;
+	    if (my + h0 >= TheUI.MinimapH) {	// clip bottom side
+		h0 = TheUI.MinimapH - my;
 	    }
 	    while (w-- >= 0) {
 		h = h0;
 		while (h-- >= 0) {
 		    ((unsigned char*)MinimapGraphic->Frames)[
-			mx + w + (my + h) * MINIMAP_W] = color;
+			mx + w + (my + h) * TheUI.MinimapW] = color;
 		}
 	    }
 	}
@@ -384,18 +388,18 @@ global void UpdateMinimap(void)
 	mx = 1 + MinimapX + Map2MinimapX[unit->X];
 	my = 1 + MinimapY + Map2MinimapY[unit->Y];
 	w = Map2MinimapX[type->TileWidth];
-	if (mx + w >= MINIMAP_W) {		// clip right side
-	    w = MINIMAP_W - mx;
+	if (mx + w >= TheUI.MinimapW) {		// clip right side
+	    w = TheUI.MinimapW - mx;
 	}
 	h0 = Map2MinimapY[type->TileHeight];
-	if (my + h0 >= MINIMAP_H) {	// clip bottom side
-	    h0 = MINIMAP_H - my;
+	if (my + h0 >= TheUI.MinimapH) {	// clip bottom side
+	    h0 = TheUI.MinimapH - my;
 	}
 	while (w-- >= 0) {
 	    h = h0;
 	    while (h-- >= 0) {
 		((unsigned char*)MinimapGraphic->Frames)[
-		    mx + w + (my + h) * MINIMAP_W] = color;
+		    mx + w + (my + h) * TheUI.MinimapW] = color;
 	    }
 	}
     }
@@ -447,7 +451,6 @@ global void DrawMinimapCursor(int vx, int vy)
     int i;
 
     // Determine and save region below minimap cursor
-    // FIXME: position of the minimap in the graphic is hardcoded (24x2)
     OldMinimapCursorX = x =
 	TheUI.MinimapPosX + MinimapX + (vx * MinimapScale) / MINIMAP_FAC;
     OldMinimapCursorY = y =
diff --git a/src/stratagus/mainloop.cpp b/src/stratagus/mainloop.cpp
index fa328fdff..5d35373d8 100644
--- a/src/stratagus/mainloop.cpp
+++ b/src/stratagus/mainloop.cpp
@@ -689,7 +689,7 @@ global void UpdateDisplay(void)
 	    // FIXME: Redraws too much of the minimap
 	    InvalidateAreaAndCheckCursor(
 		     TheUI.MinimapPosX,TheUI.MinimapPosY
-		    ,MINIMAP_W,MINIMAP_H);
+		    ,TheUI.MinimapW,TheUI.MinimapH);
 	}
 	if( MustRedraw&RedrawInfoPanel ) {
 	    InvalidateAreaAndCheckCursor(
diff --git a/src/ui/mouse.cpp b/src/ui/mouse.cpp
index 84f476b4d..54cdae555 100644
--- a/src/ui/mouse.cpp
+++ b/src/ui/mouse.cpp
@@ -481,8 +481,8 @@ local void HandleMouseOn(int x, int y)
     //
     //	Minimap
     //
-    if (x >= TheUI.MinimapPosX && x < TheUI.MinimapPosX + MINIMAP_W &&
-	    y >= TheUI.MinimapPosY && y < TheUI.MinimapPosY + MINIMAP_H) {
+    if (x >= TheUI.MinimapPosX && x < TheUI.MinimapPosX + TheUI.MinimapW &&
+	    y >= TheUI.MinimapPosY && y < TheUI.MinimapPosY + TheUI.MinimapH) {
 	CursorOn = CursorOnMinimap;
 	return;
     }
@@ -579,16 +579,16 @@ global void RestrictCursorToMinimap(void)
 {
     if (CursorX < TheUI.MinimapPosX) {
 	CursorStartX = TheUI.MinimapPosX;
-    } else if (CursorX >= TheUI.MinimapPosX + MINIMAP_W) {
-	CursorStartX = TheUI.MinimapPosX + MINIMAP_W - 1;
+    } else if (CursorX >= TheUI.MinimapPosX + TheUI.MinimapW) {
+	CursorStartX = TheUI.MinimapPosX + TheUI.MinimapW - 1;
     } else {
 	CursorStartX = CursorX;
     }
 
     if (CursorY < TheUI.MinimapPosY) {
 	CursorStartY = TheUI.MinimapPosY;
-    } else if (CursorY >= TheUI.MinimapPosY + MINIMAP_H) {
-	CursorStartY = TheUI.MinimapPosY + MINIMAP_H - 1;
+    } else if (CursorY >= TheUI.MinimapPosY + TheUI.MinimapW) {
+	CursorStartY = TheUI.MinimapPosY + TheUI.MinimapH - 1;
     } else {
 	CursorStartY = CursorY;
     }
diff --git a/src/ui/script_ui.cpp b/src/ui/script_ui.cpp
index da76370e3..eacb3ff11 100644
--- a/src/ui/script_ui.cpp
+++ b/src/ui/script_ui.cpp
@@ -1643,17 +1643,35 @@ local SCM CclDefineUI(SCM list)
 	    ui->MenuButtonGraphic.File = SCM_PopNewStr(&sublist);
 	    ui->MenuButtonGraphicX = SCM_PopInt(&sublist);
 	    ui->MenuButtonGraphicY = SCM_PopInt(&sublist);
-	} else if (gh_eq_p(value, gh_symbol2scm("minimap-panel"))) {
+	} else if (gh_eq_p(value, gh_symbol2scm("minimap"))) {
 	    sublist = gh_car(list);
 	    list = gh_cdr(list);
-	    ui->MinimapPanel.File = SCM_PopNewStr(&sublist);
-	    ui->MinimapPanelX = SCM_PopInt(&sublist);
-	    ui->MinimapPanelY = SCM_PopInt(&sublist);
-	} else if (gh_eq_p(value, gh_symbol2scm("minimap-pos"))) {
-	    sublist = gh_car(list);
-	    list = gh_cdr(list);
-	    ui->MinimapPosX = SCM_PopInt(&sublist);
-	    ui->MinimapPosY = SCM_PopInt(&sublist);
+	    while (!gh_null_p(sublist)) {
+		value = gh_car(sublist);
+		sublist = gh_cdr(sublist);
+		if (gh_eq_p(value, gh_symbol2scm("file"))) {
+		    value = gh_car(sublist);
+		    sublist = gh_cdr(sublist);
+		    ui->MinimapPanel.File = gh_scm2newstr(value, NULL);
+		} else if (gh_eq_p(value, gh_symbol2scm("panel-pos"))) {
+		    value = gh_car(sublist);
+		    sublist = gh_cdr(sublist);
+		    ui->MinimapPanelX = gh_scm2int(gh_car(value));
+		    ui->MinimapPanelY = gh_scm2int(gh_car(gh_cdr(value)));
+		} else if (gh_eq_p(value, gh_symbol2scm("pos"))) {
+		    value = gh_car(sublist);
+		    sublist = gh_cdr(sublist);
+		    ui->MinimapPosX = gh_scm2int(gh_car(value));
+		    ui->MinimapPosY = gh_scm2int(gh_car(gh_cdr(value)));
+		} else if (gh_eq_p(value, gh_symbol2scm("size"))) {
+		    value = gh_car(sublist);
+		    sublist = gh_cdr(sublist);
+		    ui->MinimapW = gh_scm2int(gh_car(value));
+		    ui->MinimapH = gh_scm2int(gh_car(gh_cdr(value)));
+		} else {
+		    errl("Unsupported tag", value);
+		}
+	    }
 	} else if (gh_eq_p(value, gh_symbol2scm("status-line"))) {
 	    sublist = gh_car(list);
 	    list = gh_cdr(list);
diff --git a/src/ui/ui.cpp b/src/ui/ui.cpp
index 5261ce077..282011b31 100644
--- a/src/ui/ui.cpp
+++ b/src/ui/ui.cpp
@@ -372,12 +372,15 @@ local void SaveUi(CLFile* file, const UI* ui)
 	ui->MenuButtonGraphic.File, ui->MenuButtonGraphicX,
 	ui->MenuButtonGraphicY);
 
-    CLprintf(file, "  ; Minimap background\n");
-    CLprintf(file, "  'minimap-panel (list \"%s\" %d %d)\n",
-	ui->MinimapPanel.File, ui->MinimapPanelX, ui->MinimapPanelY);
-    CLprintf(file, "  ; Minimap position\n");
-    CLprintf(file, "  'minimap-pos (list %d %d)\n",
+    CLprintf(file, "  ; Minimap\n");
+    CLprintf(file, "  'minimap-panel (list\n");
+    CLprintf(file, "    'file \"%s\"\n", ui->MinimapPanel.File);
+    CLprintf(file, "    'panel-pos (%d %d)\n",
+	ui->MinimapPanelX, ui->MinimapPanelY);
+    CLprintf(file, "    'pos (%d %d)\n",
 	ui->MinimapPosX, ui->MinimapPosY);
+    CLprintf(file, "    'size (%d %d))\n",
+	ui->MinimapW, ui->MinimapH);
 
     CLprintf(file, "\n  'status-line '(");
     CLprintf(file, "\n    file \"%s\"",ui->StatusLine.File);