1 /*
2 * This file is part of Dune Legacy.
3 *
4 * Dune Legacy is free software: you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation, either version 2 of the License, or
7 * (at your option) any later version.
8 *
9 * Dune Legacy is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
13 *
14 * You should have received a copy of the GNU General Public License
15 * along with Dune Legacy. If not, see <http://www.gnu.org/licenses/>.
16 */
17
18
19
20 #include <string.h>
21 #include <stdlib.h>
22 #include <SDL.h>
23
24 #include "MapSeed.h"
25
26 // global seed value
27 static Uint32 Seed;
28
29 // a point that has 2 coordinates
30 typedef struct {
31 Uint16 x;
32 Uint16 y;
33 } Point;
34
35 // some values
36 const Uint8 BoolArray[] = {0,1,0,0,1,1,1,1,0,0,1,1,1,1,0,0,0,0,1,0,0};
37
38 // some offsets
39 const Sint8 OffsetArray1[]={
40 0,-1,1,-16,16,
41 -17,17,-15,15,
42 -2, 2,-32,32,
43 -4, 4,-64,64,
44 -30,30,-34,34
45 };
46
47 // some more offsets
48 const Uint8 OffsetArray2[]={
49 0,0,4,0,4,0,4,4,0,0,0,4,0,4,4,4,0,0,0,2,0,
50 2,0,4,0,0,2,0,2,0,4,0,4,0,4,2,4,2,4,4,0,4,
51 2,4,2,4,4,4,0,0,4,4,2,0,2,2,0,0,2,2,4,0,2,
52 2,0,2,2,2,2,2,4,2,2,2,0,4,2,2,4,4,2,2,2,4,
53 0,0,4,0,4,0,4,4,0,0,0,4,0,4,4,4,0,0,0,2,0,
54 2,0,4,0,0,2,0,2,0,4,0,4,0,4,2,4,2,4,4,0,4,
55 2,4,2,4,4,4,4,0,0,4,2,0,2,2,0,0,2,2,4,0,2,
56 2,0,2,2,2,2,2,4,2,2,2,0,4,2,2,4,4,2,2,2,4
57 };
58
59 // TileTypes
60 const Sint16 TileTypes[] = {
61 220, 221, 222, 229, 230, 231, 213, 214, 215, 223, 224, 225, 232, 233, 234, 216,
62 217, 218, 226, 227, 228, 235, 236, 237, 219, 217, 218, 226, 227, 228, 235, 236,
63 237, 238, 239, 244, 245, 125, 240, 246, 247, 241, 242, 248, 249, 241, 243, 248,
64 249, 241, 242, 248, 250, 241, 243, 248, 250, 251, 252, 253, 258, 259, 260, 223,
65 224, 225, 232, 233, 234, 254, 255, 256, 261, 262, 263, 257, 255, 256, 261, 262,
66 263, 254, 255, 256, 261, 264, 265, 257, 255, 256, 261, 264, 265, 254, 255, 256,
67 261, 266, 267, 257, 255, 256, 261, 266, 267, 210, 268, 269, 273, 274, 275, 223,
68 224, 225, 232, 233, 234, 270, 271, 272, 276, 277, 278, 270, 271, 272, 279, 277,
69 278, 270, 271, 272, 276, 277, 278, 270, 271, 272, 279, 277, 278, 270, 271, 272,
70 276, 277, 278, 270, 271, 272, 279, 277, 278, 238, 239, 244, 245, 125, 240, 246,
71 247, 280, 281, 282, 283, 280, 281, 282, 284, 238, 239, 244, 245, 125, 240, 246,
72 247, 285, 286, 288, 289, 287, 286, 290, 289, 143, 291, 295, 296, 125, 240, 246,
73 247, 292, 293, 297, 298, 294, 293, 297, 298, 238, 239, 244, 245, 125, 240, 246,
74 247, 299, 300, 301, 302, 299, 300, 301, 303, 238, 239, 244, 245, 125, 240, 246,
75 247, 304, 305, 306, 307, 304, 305, 306, 308, 210, 211, 212, 220, 221, 222, 229,
76 230, 231, 213, 214, 215, 223, 313, 225, 232, 233, 234, 309, 310, 311, 314, 315,
77 316, 319, 320, 321, 312, 310, 311, 314, 315, 316, 319, 320, 321, 309, 310, 311
78 };
79
80 // sinus[index] = 127 * sin(pi * index/128)
81 static const Sint8 sinus[256] = {
82 0, 3, 6, 9, 12, 15, 18, 21, 24, 27, 30, 33, 36, 39, 42, 45,
83 48, 51, 54, 57, 59, 62, 65, 67, 70, 73, 75, 78, 80, 82, 85, 87,
84 89, 91, 94, 96, 98, 100, 101, 103, 105, 107, 108, 110, 111, 113, 114, 116,
85 117, 118, 119, 120, 121, 122, 123, 123, 124, 125, 125, 126, 126, 126, 126, 126,
86 127, 126, 126, 126, 126, 126, 125, 125, 124, 123, 123, 122, 121, 120, 119, 118,
87 117, 116, 114, 113, 112, 110, 108, 107, 105, 103, 102, 100, 98, 96, 94, 91,
88 89, 87, 85, 82, 80, 78, 75, 73, 70, 67, 65, 62, 59, 57, 54, 51,
89 48, 45, 42, 39, 36, 33, 30, 27, 24, 21, 18, 15, 12, 9, 6, 3,
90 0, -3, -6, -9, -12, -15, -18, -21, -24, -27, -30, -33, -36, -39, -42, -45,
91 -48, -51, -54, -57, -59, -62, -65, -67, -70, -73, -75, -78, -80, -82, -85, -87,
92 -89, -91, -94, -96, -98, -100, -102, -103, -105, -107, -108, -110, -111, -113, -114, -116,
93 -117, -118, -119, -120, -121, -122, -123, -123, -124, -125, -125, -126, -126, -126, -126, -126,
94 -126, -126, -126, -126, -126, -126, -125, -125, -124, -123, -123, -122, -121, -120, -119, -118,
95 -117, -116, -114, -113, -112, -110, -108, -107, -105, -103, -102, -100, -98, -96, -94, -91,
96 -89, -87, -85, -82, -80, -78, -75, -73, -70, -67, -65, -62, -59, -57, -54, -51,
97 -48, -45, -42, -39, -36, -33, -30, -27, -24, -21, -18, -15, -12, -9, -6, -3
98 };
99
100 /**
101 Converts a 2d coordinate to a 1d.
102 \param Xcoord The coordinate in x-direction
103 \param Ycoord The coordinate in y-direction
104 \return The 1-dimensional coordinate
105 */
MapArray2DToMapArray1D(Sint16 Xcoord,Sint16 Ycoord)106 static Sint16 MapArray2DToMapArray1D(Sint16 Xcoord,Sint16 Ycoord) {
107 return Xcoord | (Ycoord << 6);
108 }
109
110 /**
111 Converts a 2d coordinate to a 1d. This function is basically the same
112 as MapArray2DToMapArray1D() but limits the Xcoord to (0-63).
113 \param Xcoord The coordinate in x-direction
114 \param Ycoord The coordinate in y-direction
115 \return The 1-dimensional coordinate
116 */
MapArray2DToMapArray1D_OOB(Sint16 Xcoord,Sint16 Ycoord)117 static Sint16 MapArray2DToMapArray1D_OOB(Sint16 Xcoord,Sint16 Ycoord) {
118 return MapArray2DToMapArray1D(Xcoord & 0x3F,Ycoord);
119 }
120
121
122 /**
123 This function smooth the map in the local neighbourhood of index.
124 \param index The position which should be smoothed
125 \param pMapArray Pointer to the map that should be smoothed
126 \return none
127 */
SmoothNeighbourhood(Sint16 index,Uint32 * pMapArray)128 static void SmoothNeighbourhood(Sint16 index, Uint32* pMapArray) {
129 Sint16 TileType;
130 Sint16 Xcoord;
131 Sint16 Ycoord;
132 Sint16 Pos;
133
134 TileType = (Sint16) pMapArray[index];
135
136 if(TileType == 8) {
137 pMapArray[index] = 9;
138 SmoothNeighbourhood(index,pMapArray);
139 } else if (TileType == 9) {
140 for(Ycoord = -1; Ycoord <= 1; Ycoord++) {
141 for(Xcoord = -1; Xcoord <= 1; Xcoord++) {
142 Pos = MapArray2DToMapArray1D( (index & 0x3F)+Xcoord,((index >> 6) & 0x3F)+Ycoord);
143 if(Pos < 0)
144 continue;
145 if(Pos >= 64*64)
146 continue;
147
148 if(BoolArray[pMapArray[Pos]] == 1) {
149 pMapArray[index] = 8;
150 continue;
151 } else {
152 if(pMapArray[Pos] == 9)
153 continue;
154
155 pMapArray[Pos]=8;
156 }
157 }
158 }
159 } else {
160 if(BoolArray[TileType] == 0) {
161 pMapArray[index] = 8;
162 }
163 }
164 }
165
166 /**
167 Creates new random value.
168 \return The new random value
169 */
SeedRand()170 static Uint16 SeedRand() {
171 Uint8 a;
172 Uint8 carry;
173 Uint8 old_carry;
174
175 // little endian is more useful for this algorithm
176 Seed = SDL_SwapLE32(Seed);
177 Uint8* pSeed = (Uint8*) &Seed;
178
179 // shift right
180 a = pSeed[0];
181 a = a >> 1;
182
183 // shift right in carry
184 carry = a & 0x01;
185 a = a >> 1;
186
187 // rotate left through carry
188 old_carry = carry;
189 carry = (pSeed[2] & 0x80) >> 7;
190 pSeed[2] = pSeed[2] << 1;
191 pSeed[2] = pSeed[2] | old_carry;
192
193 // rotate left through carry
194 old_carry = carry;
195 carry = (pSeed[1] & 0x80) >> 7;
196 pSeed[1] = pSeed[1] << 1;
197 pSeed[1] = pSeed[1] | old_carry;
198
199 // invert carry
200 carry = (carry == 1 ? 0 : 1);
201
202 // subtract with carry
203 a = ((Uint16) a) - (((Uint16) pSeed[0]) + ((Uint16) carry));
204
205 // shift right
206 carry = a & 0x01;
207 // a = a >> 1; //< Not needed anymore
208
209 // rotate right through carry
210 pSeed[0] = (pSeed[0] >> 1) | (carry << 7);
211
212 // xor
213 a = pSeed[0] ^ pSeed[1];
214
215 // convert back to native endianess
216 Seed = SDL_SwapLE32(Seed);
217
218 return ((Uint16) a);
219
220 }
221
222 /**
223 Creates a random map.
224 \param Para_Seed Seed of the map
225 \param pResultMap Should be Uint16[64*64]
226 */
createMapWithSeed(Uint32 Para_Seed,Uint16 * pResultMap)227 void createMapWithSeed(Uint32 Para_Seed,Uint16 *pResultMap)
228 {
229 Uint8 Array4x4TerrainGrid[16*16+16+1];
230 Uint32 MapArray[65*65];
231 Point point;
232 Uint16 randNum;
233 Uint16 randNum2;
234 Uint16 randNum3;
235 Sint16 index;
236 Sint16 i,j;
237 Sint16 Xcoord;
238 Sint16 Ycoord;
239 Uint16 max;
240 Sint16 Point1;
241 Sint16 Point2;
242 Uint16 pos;
243
244 Uint16 curMapRow[0x80];
245 Uint16 oldMapRow[0x80];
246 Uint32 Area[3][3];
247
248 Seed = Para_Seed;
249
250 // clear map
251 memset(MapArray,0,sizeof(MapArray));
252
253 for(i = 0; i < 16*16+16 ; i++) {
254 Array4x4TerrainGrid[i] = SeedRand() & 0x0F;
255 if(Array4x4TerrainGrid[i] <= 0x0A)
256 continue;
257
258 Array4x4TerrainGrid[i] = 0x0A;
259 }
260
261 for(i = SeedRand() & 0x0F;i >= 0 ;i--) {
262 randNum = SeedRand() & 0xFF;
263 for(j = 0; j < 21; j++) {
264 index = randNum + OffsetArray1[j];
265 index = index >= 0 ? index : 0;
266 index = index <= (16*16+16) ? index : (16*16+16);
267 Array4x4TerrainGrid[index] = ((Uint16) Array4x4TerrainGrid[index] + (SeedRand() & 0x0F)) & 0x0F;
268 }
269 }
270
271 for(i = SeedRand() & 0x03; i >= 0; i--) {
272 randNum = SeedRand() & 0xFF;
273 for(j = 0; j < 21; j++) {
274 index = randNum + OffsetArray1[j];
275 index = index >= 0 ? index : 0;
276 index = index <= (16*16+16) ? index : (16*16+16);
277 Array4x4TerrainGrid[index] = SeedRand() & 0x03;
278 }
279 }
280
281 for(Ycoord = 0; Ycoord < 64; Ycoord+=4) {
282 for(Xcoord = 0; Xcoord < 64; Xcoord+=4) {
283 MapArray[MapArray2DToMapArray1D(Xcoord,Ycoord)] = Array4x4TerrainGrid[Ycoord*4+Xcoord/4];
284 }
285 }
286
287 for(Ycoord = 0; Ycoord < 64; Ycoord+=4) {
288 for(Xcoord = 0; Xcoord < 64; Xcoord+=4) {
289 for(i = (Xcoord % 8 == 0 ? 21 : 0) ; (Xcoord % 8 == 0 ? 21 : 0) + 21 > i; i++) {
290 Point1 = MapArray2DToMapArray1D(Xcoord + OffsetArray2[4*i],Ycoord + OffsetArray2[4*i+1]);
291 Point2 = MapArray2DToMapArray1D(Xcoord + OffsetArray2[4*i+2],Ycoord + OffsetArray2[4*i+3]);
292 pos = (Point1 + Point2) / 2;
293
294 if(pos >= 64*64)
295 continue;
296
297 Point1 = MapArray2DToMapArray1D_OOB(Xcoord + OffsetArray2[4*i],Ycoord + OffsetArray2[4*i+1]);
298 Point2 = MapArray2DToMapArray1D_OOB(Xcoord + OffsetArray2[4*i+2],Ycoord + OffsetArray2[4*i+3]);
299
300 MapArray[pos] = (MapArray[Point1] + MapArray[Point2] + 1) / 2;
301 }
302
303 }
304 }
305
306 memset(curMapRow,0,sizeof(curMapRow));
307
308 // apply box-filter to the map
309 for(Ycoord = 0; Ycoord < 64; Ycoord++) {
310
311 // save the old row
312 memcpy(oldMapRow,curMapRow,sizeof(curMapRow));
313 for(i = 0;i < 64; i++) {
314 curMapRow[i] = (Uint16) MapArray[Ycoord*64+i];
315 }
316
317 for(Xcoord = 0; Xcoord < 64; Xcoord++) {
318
319 Area[0][0] = ((Xcoord > 0) && (Ycoord > 0)) ? oldMapRow[Xcoord-1] : curMapRow[Xcoord];
320 Area[1][0] = (Ycoord > 0) ? oldMapRow[Xcoord] : curMapRow[Xcoord];
321 Area[2][0] = ((Xcoord < 63) && (Ycoord > 0)) ? oldMapRow[Xcoord+1] : curMapRow[Xcoord];
322
323 Area[0][1] = (Xcoord > 0) ? curMapRow[Xcoord-1] : curMapRow[Xcoord];
324 Area[1][1] = curMapRow[Xcoord];
325 Area[2][1] = (Xcoord < 63) ? curMapRow[Xcoord+1] : curMapRow[Xcoord];
326
327 Area[0][2] = ((Xcoord > 0) && (Ycoord < 63)) ? MapArray[(Ycoord+1)*64 + Xcoord-1] : curMapRow[Xcoord];
328 Area[1][2] = (Ycoord < 63) ? MapArray[(Ycoord+1)*64 + Xcoord] : curMapRow[Xcoord];
329 Area[2][2] = ((Xcoord < 63) && (Ycoord < 63)) ? MapArray[(Ycoord+1)*64 + Xcoord+1] : curMapRow[Xcoord];
330
331 MapArray[Ycoord*64 + Xcoord] = ( Area[0][0] + Area[1][0] + Area[2][0]
332 + Area[0][1] + Area[1][1] + Area[1][2]
333 + Area[0][2] + Area[2][1] + Area[2][2] )/9;
334 }
335 }
336
337 randNum = SeedRand() & 0x0F;
338 randNum = (randNum < 8 ? 8 : randNum);
339 randNum = (randNum > 0x0C ? 0x0C : randNum);
340 point.y = (SeedRand() & 0x03) - 1;
341 point.y = ( (randNum-3) < point.y ? randNum-3 : point.y);
342
343 for(i = 0; i < 64*64; i++) {
344 point.x = (Uint16) MapArray[i];
345
346 if( (randNum+4) < point.x) {
347 MapArray[i] = 0x06;
348 } else if(point.x >= randNum) {
349 MapArray[i] = 0x04;
350 } else if(point.x <= point.y) {
351 MapArray[i] = 0x02;
352 } else {
353 MapArray[i] = 0x00;
354 }
355 }
356
357 for(i = SeedRand() & 0x2F; i != 0; i--) {
358 point.y = SeedRand() & 0x3F;
359 point.x = SeedRand() & 0x3F;
360 index = MapArray2DToMapArray1D(point.x,point.y);
361
362 if(BoolArray[MapArray[index]] == 1) {
363 i++;
364 continue;
365 }
366
367
368 randNum = SeedRand() & 0x1F;
369 for(j=0; j < randNum; j++) {
370 max = SeedRand() & 0x3F;
371
372 if(max == 0) {
373 pos = index;
374 } else {
375 point.y = ((index << 2) & 0xFF00) | 0x80;
376 point.x = ((index & 0x3F) << 8) | 0x80;
377
378 randNum2 = SeedRand() & 0xFF;
379
380 while(randNum2 > max)
381 randNum2 = randNum2 >> 1;
382
383 randNum3 = SeedRand() & 0xFF;
384
385 point.x = point.x + (((sinus[randNum3] * randNum2) >> 7) << 4);
386 point.y = point.y + ((((-1) * sinus[(randNum3+64) % 256] * randNum2) >> 7) << 4);
387
388
389 if(/*(point.x < 0) || */(point.x > 0x4000) || /*(point.y < 0) ||*/ (point.y > 0x4000)) {
390 pos = index;
391 } else {
392 pos = ((point.y & 0xFF00) >> 2) | (point.x >> 8);
393 }
394 }
395
396 if(pos >= 64*64) {
397 j--;
398 continue;
399 }
400
401 /*
402 if(pos < 0) {
403 j--;
404 continue;
405 }*/
406
407 SmoothNeighbourhood(pos,MapArray);
408 }
409 }
410
411
412 //smoothing
413 for(i = 0; i < 64; i++) {
414 curMapRow[i] = (Uint16) MapArray[i];
415 }
416
417 for(Ycoord = 0; Ycoord < 64; Ycoord++) {
418 memcpy(oldMapRow,curMapRow,sizeof(curMapRow));
419
420 for(i = 0; i < 64; i++) {
421 curMapRow[i] = (Uint16) MapArray[Ycoord*64+i];
422 }
423
424 for(Xcoord = 0; Xcoord < 64; Xcoord++) {
425
426 Area[1][0] = (Ycoord > 0) ? oldMapRow[Xcoord] : MapArray[Ycoord*64+Xcoord];
427 Area[0][1] = (Xcoord > 0) ? curMapRow[Xcoord-1] : MapArray[Ycoord*64+Xcoord];
428 Area[1][1] = MapArray[Ycoord*64+Xcoord];
429 Area[2][1] = (Xcoord < 63) ? curMapRow[Xcoord+1] : MapArray[Ycoord*64+Xcoord];
430 Area[1][2] = (Ycoord < 63) ? MapArray[(Ycoord+1)*64+Xcoord] : MapArray[Ycoord*64+Xcoord];
431
432 MapArray[Ycoord*64+Xcoord] = 0;
433
434 switch(Area[1][1]) {
435
436 case 4:
437 if( (Area[1][0] == 4) || (Area[1][0] == 6) )
438 MapArray[Ycoord*64+Xcoord] |= 0x01;
439
440 if( (Area[2][1] == 4) || (Area[2][1] == 6) )
441 MapArray[Ycoord*64+Xcoord] |= 0x02;
442
443 if( (Area[1][2] == 4) || (Area[1][2] == 6) )
444 MapArray[Ycoord*64+Xcoord] |= 0x04;
445
446 if( (Area[0][1] == 4) || (Area[0][1] == 6) )
447 MapArray[Ycoord*64+Xcoord] |= 0x08;
448
449 break;
450
451 case 8:
452 if( (Area[1][0] == 8) || (Area[1][0] == 9) )
453 MapArray[Ycoord*64+Xcoord] |= 0x01;
454
455 if( (Area[2][1] == 8) || (Area[2][1] == 9) )
456 MapArray[Ycoord*64+Xcoord] |= 0x02;
457
458 if( (Area[1][2] == 8) || (Area[1][2] == 9) )
459 MapArray[Ycoord*64+Xcoord] |= 0x04;
460
461 if( (Area[0][1] == 8) || (Area[0][1] == 9) )
462 MapArray[Ycoord*64+Xcoord] |= 0x08;
463
464 break;
465
466 default:
467 if(Area[1][0] == Area[1][1])
468 MapArray[Ycoord*64+Xcoord] |= 0x01;
469
470 if(Area[2][1] == Area[1][1])
471 MapArray[Ycoord*64+Xcoord] |= 0x02;
472
473 if(Area[1][2] == Area[1][1])
474 MapArray[Ycoord*64+Xcoord] |= 0x04;
475
476 if(Area[0][1] == Area[1][1])
477 MapArray[Ycoord*64+Xcoord] |= 0x08;
478
479 break;
480 }
481
482 if(Area[1][1] == 0)
483 MapArray[Ycoord*64+Xcoord] = 0;
484
485 if(Area[1][1] == 4)
486 MapArray[Ycoord*64+Xcoord]++;
487
488 if(Area[1][1] == 2)
489 MapArray[Ycoord*64+Xcoord] += 0x11;
490
491 if(Area[1][1] == 6)
492 MapArray[Ycoord*64+Xcoord] += 0x21;
493
494 if(Area[1][1] == 8)
495 MapArray[Ycoord*64+Xcoord] += 0x31;
496
497 if(Area[1][1] == 9)
498 MapArray[Ycoord*64+Xcoord] += 0x41;
499 }
500 }
501
502 //create resulting array
503 for(i = 0; i < 64*64; i++) {
504 MapArray[i] = (MapArray[i] & 0xFE00) | ((MapArray[i] <= 85) ? (MapArray[i]+127) : TileTypes[MapArray[i]-85]) | 0xF800;
505 pResultMap[i] = MapArray[i] & 0x1FF;
506 }
507 }
508
createMapWithSeed(Uint32 Para_Seed,int mapscale)509 MapData createMapWithSeed(Uint32 Para_Seed, int mapscale) {
510 Uint16 SeedMap[64*64];
511 createMapWithSeed(Para_Seed,SeedMap);
512
513 int sizeX = 0;
514 int sizeY = 0;
515 int logicalOffsetX = 0;
516 int logicalOffsetY = 0;
517
518 switch(mapscale) {
519 case 0: {
520 sizeX = 62;
521 sizeY = 62;
522 logicalOffsetX = 1;
523 logicalOffsetY = 1;
524 } break;
525
526 case 1: {
527 sizeX = 32;
528 sizeY = 32;
529 logicalOffsetX = 16;
530 logicalOffsetY = 16;
531 } break;
532
533 case 2:
534 default: {
535 sizeX = 21;
536 sizeY = 21;
537 logicalOffsetX = 11;
538 logicalOffsetY = 11;
539 } break;
540 }
541
542 MapData mapData(sizeX, sizeY);
543
544 for(int y = 0; y < sizeY; y++) {
545 for(int x = 0; x < sizeX; x++) {
546
547 TERRAINTYPE terrainType = Terrain_Sand;
548
549 unsigned char seedmaptype = SeedMap[(y+logicalOffsetY)*64+x+logicalOffsetX] >> 4;
550 switch(seedmaptype) {
551 case 0x7: {
552 // Normal sand
553 terrainType = Terrain_Sand;
554 } break;
555
556 case 0x2:
557 case 0x8: {
558 // Rock or building
559 terrainType = Terrain_Rock;
560 } break;
561
562 case 0x9: {
563 // Sand dunes
564 terrainType = Terrain_Dunes;
565 } break;
566
567 case 0xa: {
568 // Mountain
569 terrainType = Terrain_Mountain;
570 } break;
571
572 case 0xb: {
573 // Spice
574 terrainType = Terrain_Spice;
575 } break;
576
577 case 0xc: {
578 // Thick spice
579 terrainType = Terrain_ThickSpice;
580 } break;
581 }
582
583 mapData(x,y) = terrainType;
584 }
585 }
586
587 return mapData;
588 }
589