TrinityCore
Loading...
Searching...
No Matches
wdtfile.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 "wdtfile.h"
19#include "adtfile.h"
20#include "Errors.h"
21#include "Memory.h"
22#include "model.h"
23#include "StringFormat.h"
24#include "Util.h"
25#include "vmapexport.h"
26#include "wmo.h"
27#include <algorithm>
28#include <cstdio>
29
30extern std::shared_ptr<CASC::Storage> CascStorage;
31
32WDTFile::WDTFile(uint32 fileDataId, std::string const& description, std::string mapName, bool cache)
33 : _file(CascStorage, fileDataId, description), _header(), _adtInfo(), _mapName(std::move(mapName)),
34 _adtCache(cache ? std::make_unique<ADTCache>() : nullptr)
35{
36}
37
38WDTFile::~WDTFile() = default;
39
41{
42 if (_file.isEof())
43 return false;
44
45 char fourcc[4];
46 uint32 size;
47
48 std::string dirname = Trinity::StringFormat("{}/dir_bin/{:04}", szWorkDirWmo, mapId);
49 auto dirfile = Trinity::make_unique_ptr_with_deleter<&::fclose>(fopen(dirname.c_str(), "ab"));
50 if (!dirfile)
51 {
52 printf("Can't open dirfile!'%s'\n", dirname.c_str());
53 return false;
54 }
55
56 while (!_file.isEof())
57 {
58 _file.read(fourcc,4);
59 _file.read(&size, 4);
60
61 std::ranges::reverse(fourcc);
62
63 size_t nextpos = _file.getPos() + size;
64
65 if (!memcmp(fourcc, "MPHD", 4))
66 {
67 ASSERT(size == sizeof(WDT::MPHD));
68 _file.read(&_header, sizeof(WDT::MPHD));
69 }
70 else if (!memcmp(fourcc, "MAIN", 4))
71 {
72 ASSERT(size == sizeof(WDT::MAIN));
73 _file.read(&_adtInfo, sizeof(WDT::MAIN));
74 }
75 else if (!memcmp(fourcc, "MAID", 4))
76 {
77 ASSERT(size == sizeof(WDT::MAID));
78 _adtFileDataIds = std::make_unique<WDT::MAID>();
79 _file.read(_adtFileDataIds.get(), sizeof(WDT::MAID));
80 }
81 else if (!memcmp(fourcc, "MWMO", 4))
82 {
83 // global map objects
84 if (size)
85 {
86 char* p = _file.getPointer();
87 _file.seekRelative(size);
88 char* end = _file.getPointer();
89 while (p < end)
90 {
91 std::size_t length = std::ranges::distance(p, CStringSentinel.Checked(end));
92 _wmoNames.emplace_back(p, length);
93
94 p += length + 1;
95 }
96 }
97 }
98 else if (!memcmp(fourcc, "MODF", 4))
99 {
100 // global wmo instance data
101 if (size)
102 {
103 uint32 mapObjectCount = size / sizeof(ADT::MODF);
104 for (uint32 i = 0; i < mapObjectCount; ++i)
105 {
106 ADT::MODF mapObjDef;
107 _file.read(&mapObjDef, sizeof(ADT::MODF));
108
109 std::string fileName;
110 if (mapObjDef.Flags & 0x8)
111 fileName = Trinity::StringFormat("FILE{:08X}.xxx", mapObjDef.Id);
112 else
113 fileName = _wmoNames[mapObjDef.Id];
114
115 if (ExtractedModelData const* extracted = ExtractSingleWmo(fileName))
116 {
117 if (extracted->HasCollision())
118 MapObject::Extract(mapObjDef, fileName.c_str(), true, mapId, mapId, dirfile.get(), nullptr);
119
120 if (extracted->Doodads)
121 Doodad::ExtractSet(*extracted->Doodads, mapObjDef, true, mapId, mapId, dirfile.get(), nullptr);
122 }
123 }
124 }
125 }
126 _file.seek((int)nextpos);
127 }
128
129 _file.close();
130 return true;
131}
132
133ADTFile* WDTFile::GetMap(int32 x, int32 y, bool createIfMissing)
134{
135 if (!(x >= 0 && y >= 0 && x < 64 && y < 64))
136 return nullptr;
137
138 if (_adtCache && _adtCache->file[x][y])
139 return _adtCache->file[x][y].get();
140
141 if (!(_adtInfo.Data[y][x].Flag & 1))
142 return nullptr;
143
144 if (!createIfMissing)
145 return nullptr;
146
147 ADTFile* adt;
148 std::string name = Trinity::StringFormat(R"(World\Maps\{}\{}_{}_{}_obj0.adt)", _mapName, _mapName, x, y);
149 if (_header.Flags & 0x200)
150 adt = new ADTFile(_adtFileDataIds->Data[y][x].Obj0ADT, name, _adtCache != nullptr);
151 else
152 adt = new ADTFile(name, _adtCache != nullptr);
153
154 if (_adtCache)
155 _adtCache->file[x][y].reset(adt);
156
157 return adt;
158}
159
161{
162 if (_adtCache)
163 return;
164
165 delete adt;
166}
int32_t int32
Definition Define.h:150
uint32_t uint32
Definition Define.h:154
#define ASSERT
Definition Errors.h:80
struct CStringSentinel_T CStringSentinel
void seekRelative(int offset)
Definition cascfile.cpp:105
bool isEof()
Definition cascfile.h:45
char * getPointer()
Definition cascfile.h:44
void seek(int offset)
Definition cascfile.cpp:99
size_t read(void *dest, size_t bytes)
Definition cascfile.cpp:80
size_t getPos()
Definition cascfile.h:42
void close()
Definition cascfile.cpp:111
void FreeADT(ADTFile *adt)
Definition wdtfile.cpp:160
WDT::MAIN _adtInfo
Definition wdtfile.h:81
WDT::MPHD _header
Definition wdtfile.h:80
std::vector< std::string > _wmoNames
Definition wdtfile.h:84
WDTFile(uint32 fileDataId, std::string const &description, std::string mapName, bool cache)
Definition wdtfile.cpp:32
bool init(uint32 mapId)
Definition wdtfile.cpp:40
ADTFile * GetMap(int32 x, int32 y, bool createIfMissing)
Definition wdtfile.cpp:133
CASCFile _file
Definition wdtfile.h:79
std::string _mapName
Definition wdtfile.h:83
std::unique_ptr< ADTCache > _adtCache
Definition wdtfile.h:89
std::unique_ptr< WDT::MAID > _adtFileDataIds
Definition wdtfile.h:82
void ExtractSet(WMODoodadData const &doodadData, ADT::MODF const &wmo, bool isGlobalWmo, uint32 mapID, uint32 originalMapId, FILE *pDirfile, std::vector< ADTOutputCache > *dirfileCache)
Definition model.cpp:211
void Extract(ADT::MODF const &mapObjDef, char const *WmoInstName, bool isGlobalWmo, uint32 mapID, uint32 originalMapId, FILE *pDirfile, std::vector< ADTOutputCache > *dirfileCache)
std::string StringFormat(FormatString< Args... > fmt, Args &&... args) noexcept
Default TC string format function.
STL namespace.
uint16 Flags
Definition adtfile.h:45
uint32 Id
Definition adtfile.h:40
constexpr CStringBoundedSentinel< Iterator > Checked(Iterator end) const
Definition Util.h:394
struct WDT::MAIN::SMAreaInfo Data[64][64]
uint32 Flags
Definition wdtfile.h:33
ExtractedModelData const * ExtractSingleWmo(std::string &fname)
char const * szWorkDirWmo
std::shared_ptr< CASC::Storage > CascStorage
Definition System.cpp:51