TrinityCore
Loading...
Searching...
No Matches
GridMap.cpp
Go to the documentation of this file.
1/*
2 * This file is part of the TrinityCore Project. See AUTHORS file for Copyright information
3 *
4 * This program is free software; you can redistribute it and/or modify it
5 * under the terms of the GNU General Public License as published by the
6 * Free Software Foundation; either version 2 of the License, or (at your
7 * option) any later version.
8 *
9 * This program is distributed in the hope that it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
12 * more details.
13 *
14 * You should have received a copy of the GNU General Public License along
15 * with this program. If not, see <http://www.gnu.org/licenses/>.
16 */
17
18#include "GridMap.h"
19#include "DB2Stores.h"
20#include "GridDefines.h"
21#include "Log.h"
22#include <G3D/Plane.h>
23#include <G3D/Ray.h>
24
25// *****************************
26// Grid function
27// *****************************
29{
30 _flags = 0;
31 // Area data
32 _gridArea = 0;
33 _areaMap = nullptr;
34 // Height level data
38 m_V9 = nullptr;
39 m_V8 = nullptr;
40 _minHeightPlanes = nullptr;
41 // Liquid data
44 _liquidOffX = 0;
45 _liquidOffY = 0;
46 _liquidWidth = 0;
47 _liquidHeight = 0;
49 _liquidEntry = nullptr;
50 _liquidFlags = nullptr;
51 _liquidMap = nullptr;
52 _holes = nullptr;
53}
54
59
61{
62 // Unload old data if exist
63 unloadData();
64
65 map_fileheader header;
66 // Not return error if file not found
67 FILE* in = fopen(filename, "rb");
68 if (!in)
70
71 if (fread(&header, sizeof(header), 1, in) != 1)
72 {
73 fclose(in);
75 }
76
77 if (header.mapMagic == MapMagic && header.versionMagic == MapVersionMagic)
78 {
79 // load up area data
80 if (header.areaMapOffset && !loadAreaData(in, header.areaMapOffset, header.areaMapSize))
81 {
82 TC_LOG_ERROR("maps", "Error loading map area data\n");
83 fclose(in);
85 }
86 // load up height data
87 if (header.heightMapOffset && !loadHeightData(in, header.heightMapOffset, header.heightMapSize))
88 {
89 TC_LOG_ERROR("maps", "Error loading map height data\n");
90 fclose(in);
92 }
93 // load up liquid data
94 if (header.liquidMapOffset && !loadLiquidData(in, header.liquidMapOffset, header.liquidMapSize))
95 {
96 TC_LOG_ERROR("maps", "Error loading map liquids data\n");
97 fclose(in);
99 }
100 // loadup holes data (if any. check header.holesOffset)
101 if (header.holesSize && !loadHolesData(in, header.holesOffset, header.holesSize))
102 {
103 TC_LOG_ERROR("maps", "Error loading map holes data\n");
104 fclose(in);
106 }
107 fclose(in);
108 return LoadResult::Ok;
109 }
110
111 TC_LOG_ERROR("maps", "Map file '{}' is from an incompatible map version ({} v{}), {} v{} is expected. Please pull your source, recompile tools and recreate maps using the updated mapextractor, then replace your old map files with new files. If you still have problems search on forum for error TCE00018.",
112 filename, std::string_view(header.mapMagic.data(), 4), header.versionMagic, std::string_view(MapMagic.data(), 4), MapVersionMagic);
113 fclose(in);
115}
116
118{
119 delete[] _areaMap;
120 delete[] m_V9;
121 delete[] m_V8;
122 delete[] _minHeightPlanes;
123 delete[] _liquidEntry;
124 delete[] _liquidFlags;
125 delete[] _liquidMap;
126 delete[] _holes;
127 _areaMap = nullptr;
128 m_V9 = nullptr;
129 m_V8 = nullptr;
130 _minHeightPlanes = nullptr;
131 _liquidEntry = nullptr;
132 _liquidFlags = nullptr;
133 _liquidMap = nullptr;
134 _holes = nullptr;
136}
137
138bool GridMap::loadAreaData(FILE* in, uint32 offset, uint32 /*size*/)
139{
140 map_areaHeader header;
141 fseek(in, offset, SEEK_SET);
142
143 if (fread(&header, sizeof(header), 1, in) != 1 || header.areaMagic != MapAreaMagic)
144 return false;
145
146 _gridArea = header.gridArea;
148 {
149 _areaMap = new uint16[16 * 16];
150 if (fread(_areaMap, sizeof(uint16), 16*16, in) != 16*16)
151 return false;
152 }
153 return true;
154}
155
156bool GridMap::loadHeightData(FILE* in, uint32 offset, uint32 /*size*/)
157{
158 map_heightHeader header;
159 fseek(in, offset, SEEK_SET);
160
161 if (fread(&header, sizeof(header), 1, in) != 1 || header.heightMagic != MapHeightMagic)
162 return false;
163
164 _gridHeight = header.gridHeight;
166 {
168 {
169 m_uint16_V9 = new uint16 [129*129];
170 m_uint16_V8 = new uint16 [128*128];
171 if (fread(m_uint16_V9, sizeof(uint16), 129*129, in) != 129*129 ||
172 fread(m_uint16_V8, sizeof(uint16), 128*128, in) != 128*128)
173 return false;
174 _gridIntHeightMultiplier = (header.gridMaxHeight - header.gridHeight) / 65535;
176 }
178 {
179 m_uint8_V9 = new uint8 [129*129];
180 m_uint8_V8 = new uint8 [128*128];
181 if (fread(m_uint8_V9, sizeof(uint8), 129*129, in) != 129*129 ||
182 fread(m_uint8_V8, sizeof(uint8), 128*128, in) != 128*128)
183 return false;
184 _gridIntHeightMultiplier = (header.gridMaxHeight - header.gridHeight) / 255;
186 }
187 else
188 {
189 m_V9 = new float [129*129];
190 m_V8 = new float [128*128];
191 if (fread(m_V9, sizeof(float), 129*129, in) != 129*129 ||
192 fread(m_V8, sizeof(float), 128*128, in) != 128*128)
193 return false;
195 }
196 }
197 else
199
201 {
202 std::array<int16, 9> maxHeights;
203 std::array<int16, 9> minHeights;
204 if (fread(maxHeights.data(), sizeof(int16), maxHeights.size(), in) != maxHeights.size() ||
205 fread(minHeights.data(), sizeof(int16), minHeights.size(), in) != minHeights.size())
206 return false;
207
208 static uint32 constexpr indices[8][3] =
209 {
210 { 3, 0, 4 },
211 { 0, 1, 4 },
212 { 1, 2, 4 },
213 { 2, 5, 4 },
214 { 5, 8, 4 },
215 { 8, 7, 4 },
216 { 7, 6, 4 },
217 { 6, 3, 4 }
218 };
219
220 static float constexpr boundGridCoords[9][2] =
221 {
222 { 0.0f, 0.0f },
223 { 0.0f, -266.66666f },
224 { 0.0f, -533.33331f },
225 { -266.66666f, 0.0f },
226 { -266.66666f, -266.66666f },
227 { -266.66666f, -533.33331f },
228 { -533.33331f, 0.0f },
229 { -533.33331f, -266.66666f },
230 { -533.33331f, -533.33331f }
231 };
232
233 _minHeightPlanes = new G3D::Plane[8];
234 for (uint32 quarterIndex = 0; quarterIndex < 8; ++quarterIndex)
235 _minHeightPlanes[quarterIndex] = G3D::Plane(
236 G3D::Vector3(boundGridCoords[indices[quarterIndex][0]][0], boundGridCoords[indices[quarterIndex][0]][1], minHeights[indices[quarterIndex][0]]),
237 G3D::Vector3(boundGridCoords[indices[quarterIndex][1]][0], boundGridCoords[indices[quarterIndex][1]][1], minHeights[indices[quarterIndex][1]]),
238 G3D::Vector3(boundGridCoords[indices[quarterIndex][2]][0], boundGridCoords[indices[quarterIndex][2]][1], minHeights[indices[quarterIndex][2]])
239 );
240 }
241
242 return true;
243}
244
245bool GridMap::loadLiquidData(FILE* in, uint32 offset, uint32 /*size*/)
246{
247 map_liquidHeader header;
248 fseek(in, offset, SEEK_SET);
249
250 if (fread(&header, sizeof(header), 1, in) != 1 || header.liquidMagic != MapLiquidMagic)
251 return false;
252
255 _liquidOffX = header.offsetX;
256 _liquidOffY = header.offsetY;
257 _liquidWidth = header.width;
258 _liquidHeight = header.height;
259 _liquidLevel = header.liquidLevel;
260
262 {
263 _liquidEntry = new uint16[16*16];
264 if (fread(_liquidEntry, sizeof(uint16), 16*16, in) != 16*16)
265 return false;
266
268 if (fread(_liquidFlags, sizeof(map_liquidHeaderTypeFlags), 16*16, in) != 16*16)
269 return false;
270 }
272 {
274 if (fread(_liquidMap, sizeof(float), _liquidWidth*_liquidHeight, in) != (uint32(_liquidWidth) * uint32(_liquidHeight)))
275 return false;
276 }
277 return true;
278}
279
280bool GridMap::loadHolesData(FILE* in, uint32 offset, uint32 /*size*/)
281{
282 if (fseek(in, offset, SEEK_SET) != 0)
283 return false;
284
285 _holes = new uint8[16 * 16 * 8];
286 if (fread(_holes, sizeof(uint8), 16 * 16 * 8, in) != 16 * 16 * 8)
287 return false;
288
289 return true;
290}
291
292uint16 GridMap::getArea(float x, float y) const
293{
294 if (!_areaMap)
295 return _gridArea;
296
297 x = 16 * (CENTER_GRID_ID - x/SIZE_OF_GRIDS);
298 y = 16 * (CENTER_GRID_ID - y/SIZE_OF_GRIDS);
299 int lx = (int)x & 15;
300 int ly = (int)y & 15;
301 return _areaMap[lx*16 + ly];
302}
303
304float GridMap::getHeightFromFlat(float /*x*/, float /*y*/) const
305{
306 return _gridHeight;
307}
308
309float GridMap::getHeightFromFloat(float x, float y) const
310{
311 if (!m_V8 || !m_V9)
312 return _gridHeight;
313
316
317 int x_int = (int)x;
318 int y_int = (int)y;
319 x -= x_int;
320 y -= y_int;
321 x_int&=(MAP_RESOLUTION - 1);
322 y_int&=(MAP_RESOLUTION - 1);
323
324 if (isHole(x_int, y_int))
325 return INVALID_HEIGHT;
326
327 // Height stored as: h5 - its v8 grid, h1-h4 - its v9 grid
328 // +--------------> X
329 // | h1-------h2 Coordinates is:
330 // | | \ 1 / | h1 0, 0
331 // | | \ / | h2 0, 1
332 // | | 2 h5 3 | h3 1, 0
333 // | | / \ | h4 1, 1
334 // | | / 4 \ | h5 1/2, 1/2
335 // | h3-------h4
336 // V Y
337 // For find height need
338 // 1 - detect triangle
339 // 2 - solve linear equation from triangle points
340 // Calculate coefficients for solve h = a*x + b*y + c
341
342 float a, b, c;
343 // Select triangle:
344 if (x+y < 1)
345 {
346 if (x > y)
347 {
348 // 1 triangle (h1, h2, h5 points)
349 float h1 = m_V9[(x_int)*129 + y_int];
350 float h2 = m_V9[(x_int+1)*129 + y_int];
351 float h5 = 2 * m_V8[x_int*128 + y_int];
352 a = h2-h1;
353 b = h5-h1-h2;
354 c = h1;
355 }
356 else
357 {
358 // 2 triangle (h1, h3, h5 points)
359 float h1 = m_V9[x_int*129 + y_int ];
360 float h3 = m_V9[x_int*129 + y_int+1];
361 float h5 = 2 * m_V8[x_int*128 + y_int];
362 a = h5 - h1 - h3;
363 b = h3 - h1;
364 c = h1;
365 }
366 }
367 else
368 {
369 if (x > y)
370 {
371 // 3 triangle (h2, h4, h5 points)
372 float h2 = m_V9[(x_int+1)*129 + y_int ];
373 float h4 = m_V9[(x_int+1)*129 + y_int+1];
374 float h5 = 2 * m_V8[x_int*128 + y_int];
375 a = h2 + h4 - h5;
376 b = h4 - h2;
377 c = h5 - h4;
378 }
379 else
380 {
381 // 4 triangle (h3, h4, h5 points)
382 float h3 = m_V9[(x_int)*129 + y_int+1];
383 float h4 = m_V9[(x_int+1)*129 + y_int+1];
384 float h5 = 2 * m_V8[x_int*128 + y_int];
385 a = h4 - h3;
386 b = h3 + h4 - h5;
387 c = h5 - h4;
388 }
389 }
390 // Calculate height
391 return a * x + b * y + c;
392}
393
394float GridMap::getHeightFromUint8(float x, float y) const
395{
396 if (!m_uint8_V8 || !m_uint8_V9)
397 return _gridHeight;
398
401
402 int x_int = (int)x;
403 int y_int = (int)y;
404 x -= x_int;
405 y -= y_int;
406 x_int&=(MAP_RESOLUTION - 1);
407 y_int&=(MAP_RESOLUTION - 1);
408
409 if (isHole(x_int, y_int))
410 return INVALID_HEIGHT;
411
412 int32 a, b, c;
413 uint8 *V9_h1_ptr = &m_uint8_V9[x_int*128 + x_int + y_int];
414 if (x+y < 1)
415 {
416 if (x > y)
417 {
418 // 1 triangle (h1, h2, h5 points)
419 int32 h1 = V9_h1_ptr[ 0];
420 int32 h2 = V9_h1_ptr[129];
421 int32 h5 = 2 * m_uint8_V8[x_int*128 + y_int];
422 a = h2-h1;
423 b = h5-h1-h2;
424 c = h1;
425 }
426 else
427 {
428 // 2 triangle (h1, h3, h5 points)
429 int32 h1 = V9_h1_ptr[0];
430 int32 h3 = V9_h1_ptr[1];
431 int32 h5 = 2 * m_uint8_V8[x_int*128 + y_int];
432 a = h5 - h1 - h3;
433 b = h3 - h1;
434 c = h1;
435 }
436 }
437 else
438 {
439 if (x > y)
440 {
441 // 3 triangle (h2, h4, h5 points)
442 int32 h2 = V9_h1_ptr[129];
443 int32 h4 = V9_h1_ptr[130];
444 int32 h5 = 2 * m_uint8_V8[x_int*128 + y_int];
445 a = h2 + h4 - h5;
446 b = h4 - h2;
447 c = h5 - h4;
448 }
449 else
450 {
451 // 4 triangle (h3, h4, h5 points)
452 int32 h3 = V9_h1_ptr[ 1];
453 int32 h4 = V9_h1_ptr[130];
454 int32 h5 = 2 * m_uint8_V8[x_int*128 + y_int];
455 a = h4 - h3;
456 b = h3 + h4 - h5;
457 c = h5 - h4;
458 }
459 }
460 // Calculate height
461 return (float)((a * x) + (b * y) + c)*_gridIntHeightMultiplier + _gridHeight;
462}
463
464float GridMap::getHeightFromUint16(float x, float y) const
465{
466 if (!m_uint16_V8 || !m_uint16_V9)
467 return _gridHeight;
468
471
472 int x_int = (int)x;
473 int y_int = (int)y;
474 x -= x_int;
475 y -= y_int;
476 x_int&=(MAP_RESOLUTION - 1);
477 y_int&=(MAP_RESOLUTION - 1);
478
479 if (isHole(x_int, y_int))
480 return INVALID_HEIGHT;
481
482 int32 a, b, c;
483 uint16 *V9_h1_ptr = &m_uint16_V9[x_int*128 + x_int + y_int];
484 if (x+y < 1)
485 {
486 if (x > y)
487 {
488 // 1 triangle (h1, h2, h5 points)
489 int32 h1 = V9_h1_ptr[ 0];
490 int32 h2 = V9_h1_ptr[129];
491 int32 h5 = 2 * m_uint16_V8[x_int*128 + y_int];
492 a = h2-h1;
493 b = h5-h1-h2;
494 c = h1;
495 }
496 else
497 {
498 // 2 triangle (h1, h3, h5 points)
499 int32 h1 = V9_h1_ptr[0];
500 int32 h3 = V9_h1_ptr[1];
501 int32 h5 = 2 * m_uint16_V8[x_int*128 + y_int];
502 a = h5 - h1 - h3;
503 b = h3 - h1;
504 c = h1;
505 }
506 }
507 else
508 {
509 if (x > y)
510 {
511 // 3 triangle (h2, h4, h5 points)
512 int32 h2 = V9_h1_ptr[129];
513 int32 h4 = V9_h1_ptr[130];
514 int32 h5 = 2 * m_uint16_V8[x_int*128 + y_int];
515 a = h2 + h4 - h5;
516 b = h4 - h2;
517 c = h5 - h4;
518 }
519 else
520 {
521 // 4 triangle (h3, h4, h5 points)
522 int32 h3 = V9_h1_ptr[ 1];
523 int32 h4 = V9_h1_ptr[130];
524 int32 h5 = 2 * m_uint16_V8[x_int*128 + y_int];
525 a = h4 - h3;
526 b = h3 + h4 - h5;
527 c = h5 - h4;
528 }
529 }
530 // Calculate height
531 return (float)((a * x) + (b * y) + c)*_gridIntHeightMultiplier + _gridHeight;
532}
533
534bool GridMap::isHole(int row, int col) const
535{
536 if (!_holes)
537 return false;
538
539 int cellRow = row / 8; // 8 squares per cell
540 int cellCol = col / 8;
541 int holeRow = row % 8;
542 int holeCol = col % 8;
543
544 return (_holes[cellRow * 16 * 8 + cellCol * 8 + holeRow] & (1 << holeCol)) != 0;
545}
546
547float GridMap::getMinHeight(float x, float y) const
548{
549 if (!_minHeightPlanes)
550 return -500.0f;
551
553
554 int32 doubleGridX = int32(std::floor(-(x - MAP_HALFSIZE) / CENTER_GRID_OFFSET));
555 int32 doubleGridY = int32(std::floor(-(y - MAP_HALFSIZE) / CENTER_GRID_OFFSET));
556
557 float gx = x - (int32(gridCoord.x_coord) - CENTER_GRID_ID + 1) * SIZE_OF_GRIDS;
558 float gy = y - (int32(gridCoord.y_coord) - CENTER_GRID_ID + 1) * SIZE_OF_GRIDS;
559
560 uint32 quarterIndex = 0;
561 if (doubleGridY & 1)
562 {
563 if (doubleGridX & 1)
564 quarterIndex = 4 + (gx <= gy);
565 else
566 quarterIndex = 2 + ((-SIZE_OF_GRIDS - gx) > gy);
567 }
568 else if (doubleGridX & 1)
569 quarterIndex = 6 + ((-SIZE_OF_GRIDS - gx) <= gy);
570 else
571 quarterIndex = gx > gy;
572
573 G3D::Ray ray = G3D::Ray::fromOriginAndDirection(G3D::Vector3(gx, gy, 0.0f), G3D::Vector3::unitZ());
574 return ray.intersection(_minHeightPlanes[quarterIndex]).z;
575}
576
577float GridMap::getLiquidLevel(float x, float y) const
578{
579 if (!_liquidMap)
580 return _liquidLevel;
581
584
585 int cx_int = ((int)x & (MAP_RESOLUTION-1)) - _liquidOffY;
586 int cy_int = ((int)y & (MAP_RESOLUTION-1)) - _liquidOffX;
587
588 if (cx_int < 0 || cx_int >=_liquidHeight)
589 return INVALID_HEIGHT;
590 if (cy_int < 0 || cy_int >=_liquidWidth)
591 return INVALID_HEIGHT;
592
593 return _liquidMap[cx_int*_liquidWidth + cy_int];
594}
595
596constexpr float GROUND_LEVEL_OFFSET_HACK = 0.02f; // due to floating point precision issues, we have to resort to a small hack to fix inconsistencies in liquids
597
598// Get water state on map
599ZLiquidStatus GridMap::GetLiquidStatus(float x, float y, float z, Optional<map_liquidHeaderTypeFlags> ReqLiquidType, LiquidData* data, float collisionHeight) const
600{
601 // Check water type (if no water return)
603 return LIQUID_MAP_NO_WATER;
604
605 // Get cell
608
609 int x_int = (int)cx & (MAP_RESOLUTION-1);
610 int y_int = (int)cy & (MAP_RESOLUTION-1);
611
612 // Check water type in cell
613 int idx=(x_int>>3)*16 + (y_int>>3);
616 if (sLiquidTypeStore.HasRecord(entry))
617 {
619 if (entry < 21)
620 {
621 if (AreaTableEntry const* area = sAreaTableStore.LookupEntry(getArea(x, y)))
622 {
623 uint32 overrideLiquid = area->LiquidTypeID[(entry - 1) & 3];
624 if (!overrideLiquid && area->ParentAreaID)
625 {
626 area = sAreaTableStore.LookupEntry(area->ParentAreaID);
627 if (area)
628 overrideLiquid = area->LiquidTypeID[(entry - 1) & 3];
629 }
630
631 if (sLiquidTypeStore.HasRecord(overrideLiquid))
632 entry = overrideLiquid;
633 }
634 }
635
637 }
638
640 return LIQUID_MAP_NO_WATER;
641
642 // Check req liquid type mask
643 if (ReqLiquidType && (*ReqLiquidType & type) == map_liquidHeaderTypeFlags::NoWater)
644 return LIQUID_MAP_NO_WATER;
645
646 // Check water level:
647 // Check water height map
648 int lx_int = x_int - _liquidOffY;
649 int ly_int = y_int - _liquidOffX;
650 if (lx_int < 0 || lx_int >=_liquidHeight)
651 return LIQUID_MAP_NO_WATER;
652 if (ly_int < 0 || ly_int >=_liquidWidth)
653 return LIQUID_MAP_NO_WATER;
654
655 // Get water level
656 float liquid_level = _liquidMap ? _liquidMap[lx_int*_liquidWidth + ly_int] : _liquidLevel;
657 // Get ground level (sub 0.02 for fix some errors)
658 float ground_level = getHeight(x, y);
659
660 // Check water level and ground level
661 if (liquid_level < (ground_level - GROUND_LEVEL_OFFSET_HACK) || z < (ground_level - GROUND_LEVEL_OFFSET_HACK))
662 return LIQUID_MAP_NO_WATER;
663
664 // All ok in water -> store data
665 if (data)
666 {
667 data->entry = entry;
668 data->type_flags = type;
669 data->level = liquid_level;
670 data->depth_level = ground_level;
671 }
672
673 // For speed check as int values
674 float delta = liquid_level - z;
675
676 uint32 status = LIQUID_MAP_ABOVE_WATER; // Above water
677
678 if (delta > collisionHeight) // Under water
679 status = LIQUID_MAP_UNDER_WATER;
680 else if (delta > 0.0f) // In water
681 status = LIQUID_MAP_IN_WATER;
682 else if (delta > -0.1f) // Walk on water
683 status = LIQUID_MAP_WATER_WALK;
684
685 if (status != LIQUID_MAP_ABOVE_WATER)
686 if (std::fabs(ground_level - z) <= GROUND_HEIGHT_TOLERANCE)
687 status |= LIQUID_MAP_OCEAN_FLOOR;
688
689 return static_cast<ZLiquidStatus>(status);
690}
DB2Storage< LiquidTypeEntry > sLiquidTypeStore("LiquidType.db2", &LiquidTypeLoadInfo::Instance)
DB2Storage< AreaTableEntry > sAreaTableStore("AreaTable.db2", &AreaTableLoadInfo::Instance)
uint8_t uint8
Definition Define.h:156
int16_t int16
Definition Define.h:151
int32_t int32
Definition Define.h:150
uint16_t uint16
Definition Define.h:155
uint32_t uint32
Definition Define.h:154
#define MAP_RESOLUTION
Definition GridDefines.h:55
#define SIZE_OF_GRIDS
Definition GridDefines.h:40
#define CENTER_GRID_ID
Definition GridDefines.h:41
#define CENTER_GRID_OFFSET
Definition GridDefines.h:43
#define MAP_HALFSIZE
Definition GridDefines.h:58
#define INVALID_HEIGHT
Definition GridDefines.h:61
constexpr float GROUND_LEVEL_OFFSET_HACK
Definition GridMap.cpp:596
#define TC_LOG_ERROR(filterType__, message__,...)
Definition Log.h:190
uint32 const MapVersionMagic
u_map_magic const MapAreaMagic
u_map_magic const MapLiquidMagic
u_map_magic const MapHeightMagic
u_map_magic const MapMagic
ZLiquidStatus
Definition MapDefines.h:133
@ LIQUID_MAP_UNDER_WATER
Definition MapDefines.h:138
@ LIQUID_MAP_OCEAN_FLOOR
Definition MapDefines.h:139
@ LIQUID_MAP_NO_WATER
Definition MapDefines.h:134
@ LIQUID_MAP_IN_WATER
Definition MapDefines.h:137
@ LIQUID_MAP_ABOVE_WATER
Definition MapDefines.h:135
@ LIQUID_MAP_WATER_WALK
Definition MapDefines.h:136
map_liquidHeaderTypeFlags
Definition MapDefines.h:97
std::optional< T > Optional
Optional helper class to wrap optional values within.
Definition Optional.h:25
float const GROUND_HEIGHT_TOLERANCE
static uint32 GetLiquidFlags(uint32 liquidType)
constexpr bool HasFlag(T flag) const
Definition EnumFlag.h:106
LoadResult
Definition GridMap.h:87
LoadResult loadData(char const *filename)
Definition GridMap.cpp:60
bool loadAreaData(FILE *in, uint32 offset, uint32 size)
Definition GridMap.cpp:138
float getHeightFromFlat(float x, float y) const
Definition GridMap.cpp:304
void unloadData()
Definition GridMap.cpp:117
float getMinHeight(float x, float y) const
Definition GridMap.cpp:547
bool isHole(int row, int col) const
Definition GridMap.cpp:534
uint8 * m_uint8_V8
Definition GridMap.h:43
GridMap()
Definition GridMap.cpp:28
float _liquidLevel
Definition GridMap.h:54
uint16 * m_uint16_V8
Definition GridMap.h:42
~GridMap()
Definition GridMap.cpp:55
uint16 getArea(float x, float y) const
Definition GridMap.cpp:292
uint16 * _liquidEntry
Definition GridMap.h:55
float getHeightFromFloat(float x, float y) const
Definition GridMap.cpp:309
float getHeightFromUint16(float x, float y) const
Definition GridMap.cpp:464
uint8 _liquidOffY
Definition GridMap.h:62
map_liquidHeaderTypeFlags * _liquidFlags
Definition GridMap.h:56
uint16 _liquidGlobalEntry
Definition GridMap.h:59
map_liquidHeaderTypeFlags _liquidGlobalFlags
Definition GridMap.h:60
uint8 _liquidOffX
Definition GridMap.h:61
uint8 * m_uint8_V9
Definition GridMap.h:37
float * _liquidMap
Definition GridMap.h:57
uint32 _flags
Definition GridMap.h:32
bool loadHolesData(FILE *in, uint32 offset, uint32 size)
Definition GridMap.cpp:280
uint8 _liquidHeight
Definition GridMap.h:64
uint16 * _areaMap
Definition GridMap.h:51
float _gridIntHeightMultiplier
Definition GridMap.h:48
uint8 _liquidWidth
Definition GridMap.h:63
float getLiquidLevel(float x, float y) const
Definition GridMap.cpp:577
float * m_V9
Definition GridMap.h:35
G3D::Plane * _minHeightPlanes
Definition GridMap.h:45
uint16 _gridArea
Definition GridMap.h:58
uint16 * m_uint16_V9
Definition GridMap.h:36
float getHeightFromUint8(float x, float y) const
Definition GridMap.cpp:394
float getHeight(float x, float y) const
Definition GridMap.h:97
bool loadHeightData(FILE *in, uint32 offset, uint32 size)
Definition GridMap.cpp:156
uint8 * _holes
Definition GridMap.h:66
float _gridHeight
Definition GridMap.h:47
GetHeightPtr _gridGetHeight
Definition GridMap.h:76
ZLiquidStatus GetLiquidStatus(float x, float y, float z, Optional< map_liquidHeaderTypeFlags > ReqLiquidType, LiquidData *data=nullptr, float collisionHeight=2.03128f) const
Definition GridMap.cpp:599
bool loadLiquidData(FILE *in, uint32 offset, uint32 size)
Definition GridMap.cpp:245
float * m_V8
Definition GridMap.h:41
GridCoord ComputeGridCoordSimple(float x, float y)
uint32 x_coord
uint32 y_coord
uint32 entry
Definition MapDefines.h:148
EnumFlag< map_liquidHeaderTypeFlags > type_flags
Definition MapDefines.h:147
float depth_level
Definition MapDefines.h:150
float level
Definition MapDefines.h:149
EnumFlag< map_areaHeaderFlags > flags
Definition MapDefines.h:64
uint16 gridArea
Definition MapDefines.h:65
u_map_magic areaMagic
Definition MapDefines.h:63
u_map_magic mapMagic
Definition MapDefines.h:40
uint32 holesSize
Definition MapDefines.h:50
uint32 liquidMapSize
Definition MapDefines.h:48
uint32 areaMapOffset
Definition MapDefines.h:43
uint32 heightMapSize
Definition MapDefines.h:46
uint32 heightMapOffset
Definition MapDefines.h:45
uint32 holesOffset
Definition MapDefines.h:49
uint32 versionMagic
Definition MapDefines.h:41
uint32 liquidMapOffset
Definition MapDefines.h:47
uint32 areaMapSize
Definition MapDefines.h:44
EnumFlag< map_heightHeaderFlags > flags
Definition MapDefines.h:82
u_map_magic heightMagic
Definition MapDefines.h:81
u_map_magic liquidMagic
Definition MapDefines.h:121
EnumFlag< map_liquidHeaderFlags > flags
Definition MapDefines.h:122
EnumFlag< map_liquidHeaderTypeFlags > liquidFlags
Definition MapDefines.h:123