From 43fc15476a4f92fee51b00ca1f36ec31edd41bf6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Petr=20Mr=C3=A1zek?= Date: Sun, 15 May 2011 00:26:44 +0200 Subject: [PATCH] Added ability to set trees on fire. --- library/ContextShared.cpp | 33 +++++++++--- library/DFTypes_C.cpp | 4 +- library/include/dfhack-c/DFTypes_C.h | 4 +- library/include/dfhack-c/modules/Maps_C.h | 2 +- .../include/dfhack-c/modules/Vegetation_C.h | 2 +- library/include/dfhack/modules/Maps.h | 2 +- library/include/dfhack/modules/Vegetation.h | 23 ++++++-- library/modules/Maps.cpp | 7 +-- library/modules/Maps_C.cpp | 52 +++++++++---------- library/modules/Vegetation.cpp | 14 ++++- library/modules/Vegetation_C.cpp | 14 ++--- library/private/ContextShared.h | 1 + tools/examples/treedump.cpp | 40 +++++++------- tools/playground/CMakeLists.txt | 3 ++ tools/supported/prospector.cpp | 8 +-- 15 files changed, 128 insertions(+), 81 deletions(-) diff --git a/library/ContextShared.cpp b/library/ContextShared.cpp index 840acec64..566f6db6c 100644 --- a/library/ContextShared.cpp +++ b/library/ContextShared.cpp @@ -17,6 +17,8 @@ DFContextShared::DFContextShared() // init modules allModules.clear(); memset(&(s_mods), 0, sizeof(s_mods)); + namesInited = false; + namesFailed = false; } DFContextShared::~DFContextShared() @@ -31,18 +33,35 @@ DFContextShared::~DFContextShared() bool DFContextShared::InitReadNames() { - OffsetGroup * OG = offset_descriptor->getGroup("name"); - name_firstname_offset = OG->getOffset("first"); - name_nickname_offset = OG->getOffset("nick"); - name_words_offset = OG->getOffset("second_words"); - name_parts_offset = OG->getOffset("parts_of_speech"); - name_language_offset = OG->getOffset("language"); - name_set_offset = OG->getOffset("has_name"); + try + { + OffsetGroup * OG = offset_descriptor->getGroup("name"); + name_firstname_offset = OG->getOffset("first"); + name_nickname_offset = OG->getOffset("nick"); + name_words_offset = OG->getOffset("second_words"); + name_parts_offset = OG->getOffset("parts_of_speech"); + name_language_offset = OG->getOffset("language"); + name_set_offset = OG->getOffset("has_name"); + } + catch(exception & e) + { + namesFailed = true; + return false; + } + namesInited = true; return true; } void DFContextShared::readName(t_name & name, uint32_t address) { + if(namesFailed) + { + return; + } + if(!namesInited) + { + if(!InitReadNames()) return; + } p->readSTLString(address + name_firstname_offset , name.first_name, 128); p->readSTLString(address + name_nickname_offset , name.nickname, 128); p->read(address + name_words_offset, 7*4, (uint8_t *)name.words); diff --git a/library/DFTypes_C.cpp b/library/DFTypes_C.cpp index 33919904b..22ee57089 100644 --- a/library/DFTypes_C.cpp +++ b/library/DFTypes_C.cpp @@ -84,7 +84,7 @@ int (*alloc_feature_buffer_callback)(t_feature**, uint32_t) = NULL; int (*alloc_hotkey_buffer_callback)(t_hotkey**, uint32_t) = NULL; int (*alloc_screen_buffer_callback)(t_screen**, uint32_t) = NULL; -int (*alloc_tree_buffer_callback)(t_tree**, uint32_t) = NULL; +int (*alloc_tree_buffer_callback)(dfh_plant**, uint32_t) = NULL; int (*alloc_memrange_buffer_callback)(t_memrange**, uint32_t*, uint32_t) = NULL; @@ -115,7 +115,7 @@ REG_MACRO(MatglossOther, t_matglossOther**, alloc_matgloss_other_buffer_callback REG_MACRO(Feature, t_feature**, alloc_feature_buffer_callback) REG_MACRO(Hotkey, t_hotkey**, alloc_hotkey_buffer_callback) REG_MACRO(Screen, t_screen**, alloc_screen_buffer_callback) -REG_MACRO(Tree, t_tree**, alloc_tree_buffer_callback) +REG_MACRO(Tree, dfh_plant**, alloc_tree_buffer_callback) REG_MACRO(CustomWorkshop, t_customWorkshop**, alloc_customWorkshop_buffer_callback) REG_MACRO(Material, t_material**, alloc_material_buffer_callback) diff --git a/library/include/dfhack-c/DFTypes_C.h b/library/include/dfhack-c/DFTypes_C.h index 0d806bb8d..4cff7a6b3 100644 --- a/library/include/dfhack-c/DFTypes_C.h +++ b/library/include/dfhack-c/DFTypes_C.h @@ -59,7 +59,7 @@ DFHACK_EXPORT extern int (*alloc_feature_buffer_callback)(t_feature**, uint32_t) DFHACK_EXPORT extern int (*alloc_hotkey_buffer_callback)(t_hotkey**, uint32_t); DFHACK_EXPORT extern int (*alloc_screen_buffer_callback)(t_screen**, uint32_t); -DFHACK_EXPORT extern int (*alloc_tree_buffer_callback)(t_tree**, uint32_t); +DFHACK_EXPORT extern int (*alloc_tree_buffer_callback)(dfh_plant**, uint32_t); DFHACK_EXPORT extern int (*alloc_memrange_buffer_callback)(t_memrange**, uint32_t*, uint32_t); @@ -81,7 +81,7 @@ DFHACK_EXPORT void RegisterFeatureBufferCallback(int (*funcptr)(t_feature**, uin DFHACK_EXPORT void RegisterHotkeyBufferCallback(int (*funcptr)(t_hotkey**, uint32_t)); DFHACK_EXPORT void RegisterScreenBufferCallback(int (*funcptr)(t_screen**, uint32_t)); -DFHACK_EXPORT void RegisterTreeBufferCallback(int (*funcptr)(t_tree**, uint32_t)); +DFHACK_EXPORT void RegisterTreeBufferCallback(int (*funcptr)(dfh_plant**, uint32_t)); DFHACK_EXPORT void RegisterMemRangeBufferCallback(int (*funcptr)(t_memrange**, uint32_t*, uint32_t)); diff --git a/library/include/dfhack-c/modules/Maps_C.h b/library/include/dfhack-c/modules/Maps_C.h index bb605936d..518a3623f 100644 --- a/library/include/dfhack-c/modules/Maps_C.h +++ b/library/include/dfhack-c/modules/Maps_C.h @@ -93,7 +93,7 @@ typedef struct DFHACK_EXPORT int Maps_ReadAllVeins(DFHackObject* maps, uint32_t x, uint32_t y, uint32_t z, c_allveins* vein_struct); -DFHACK_EXPORT t_tree* Maps_ReadVegetation(DFHackObject* maps, uint32_t x, uint32_t y, uint32_t z); +DFHACK_EXPORT dfh_plant* Maps_ReadVegetation(DFHackObject* maps, uint32_t x, uint32_t y, uint32_t z); #ifdef __cplusplus } diff --git a/library/include/dfhack-c/modules/Vegetation_C.h b/library/include/dfhack-c/modules/Vegetation_C.h index acc00d7a1..8fbaf99b9 100644 --- a/library/include/dfhack-c/modules/Vegetation_C.h +++ b/library/include/dfhack-c/modules/Vegetation_C.h @@ -36,7 +36,7 @@ extern "C" { DFHACK_EXPORT int Vegetation_Start(DFHackObject* veg, uint32_t* numTrees); DFHACK_EXPORT int Vegetation_Finish(DFHackObject* veg); -DFHACK_EXPORT int Vegetation_Read(DFHackObject* veg, const uint32_t index, t_tree* shrubbery); +DFHACK_EXPORT int Vegetation_Read(DFHackObject* veg, const uint32_t index, dfh_plant* shrubbery); #ifdef __cplusplus } diff --git a/library/include/dfhack/modules/Maps.h b/library/include/dfhack/modules/Maps.h index 031b13fe4..9fa5b1322 100644 --- a/library/include/dfhack/modules/Maps.h +++ b/library/include/dfhack/modules/Maps.h @@ -638,7 +638,7 @@ namespace DFHack std::vector* constructions = 0 ); /// read all plants in this block - bool ReadVegetation(uint32_t x, uint32_t y, uint32_t z, std::vector* plants); + bool ReadVegetation(uint32_t x, uint32_t y, uint32_t z, std::vector* plants); private: struct Private; Private *d; diff --git a/library/include/dfhack/modules/Vegetation.h b/library/include/dfhack/modules/Vegetation.h index 9984d7cf2..5760401a3 100644 --- a/library/include/dfhack/modules/Vegetation.h +++ b/library/include/dfhack/modules/Vegetation.h @@ -8,12 +8,13 @@ #include "dfhack/DFExport.h" #include "dfhack/DFModule.h" +#include "dfhack/DFTypes.h" namespace DFHack { /** * \ingroup grp_vegetation */ - struct t_tree + struct t_plant { // +0x3C #pragma pack(push, 1) @@ -36,13 +37,24 @@ namespace DFHack uint32_t unknown_1; // +0x48 uint16_t temperature_1; // +0x4C uint16_t temperature_2; // +0x4E - maybe fraction? - uint32_t mystery_flag; // 0x50: yes, just one - uint32_t unknown_2; // 0x54 + uint32_t is_burning; // 0x50: yes, just one flag + uint32_t hitpoints; // 0x54 uint32_t unknown_3; // 0x58 // a vector is here + }; + /** + * Plant object read from the game + * \ingroup grp_vegetation + */ + struct dfh_plant + { + /// name of the plant + t_name name; + /// data with static size/address + t_plant sdata; + /// address where the plant was read from uint32_t address; }; - class DFContextShared; /** * The Vegetation module @@ -55,7 +67,8 @@ namespace DFHack Vegetation(DFContextShared * d); ~Vegetation(); bool Start(uint32_t & numTrees); - bool Read (const uint32_t index, t_tree & shrubbery); + bool Read (const uint32_t index, dfh_plant & shrubbery); + bool Write (dfh_plant & shrubbery); bool Finish(); private: diff --git a/library/modules/Maps.cpp b/library/modules/Maps.cpp index f3f188a0b..f17a1a41d 100644 --- a/library/modules/Maps.cpp +++ b/library/modules/Maps.cpp @@ -1210,7 +1210,7 @@ bool Maps::ReadGlobalFeatures( std::vector & features) return false; } -bool Maps::ReadVegetation(uint32_t x, uint32_t y, uint32_t z, std::vector* plants) +bool Maps::ReadVegetation(uint32_t x, uint32_t y, uint32_t z, std::vector* plants) { if(!d->hasVeggies || !d->Started) return false; @@ -1218,14 +1218,15 @@ bool Maps::ReadVegetation(uint32_t x, uint32_t y, uint32_t z, std::vectorclear(); Private::t_offsets &off = d->offsets; DfVector vegptrs(d->owner, addr + off.vegvector); for(size_t i = 0; i < vegptrs.size(); i++) { - d->owner->read (vegptrs[i] + off.tree_desc_offset, sizeof (t_tree), (uint8_t *) &shrubbery); + d->d->readName(shrubbery.name,vegptrs[i]); + d->owner->read (vegptrs[i] + off.tree_desc_offset, sizeof (t_plant), (uint8_t *) &shrubbery.sdata); shrubbery.address = vegptrs[i]; plants->push_back(shrubbery); } diff --git a/library/modules/Maps_C.cpp b/library/modules/Maps_C.cpp index 7d17e5c78..94ed834e9 100644 --- a/library/modules/Maps_C.cpp +++ b/library/modules/Maps_C.cpp @@ -31,6 +31,7 @@ using namespace std; #include "dfhack-c/DFTypes_C.h" #include "dfhack-c/modules/Maps_C.h" +#include #ifdef __cplusplus extern "C" { @@ -672,32 +673,31 @@ int Maps_ReadAllVeins(DFHackObject* maps, uint32_t x, uint32_t y, uint32_t z, c_ return -1; } -t_tree* Maps_ReadVegetation(DFHackObject* maps, uint32_t x, uint32_t y, uint32_t z) -{ - if(maps == NULL) - return NULL; - else - { - std::vector plants; - bool result = ((DFHack::Maps*)maps)->ReadVegetation(x, y, z, &plants); - t_tree* buf = NULL; - - if(!result || plants.size() <= 0) - return NULL; - else - { - ((*alloc_tree_buffer_callback)(&buf, plants.size())); - - if(buf == NULL) - return NULL; - - copy(plants.begin(), plants.end(), buf); - - return buf; - } - } - - return NULL; +//FIXME: doesn't copy out the address and name variables! +dfh_plant* Maps_ReadVegetation(DFHackObject* maps, uint32_t x, uint32_t y, uint32_t z) +{ + if(maps == NULL) + return NULL; + else + { + std::vector plants; + dfh_plant* buf = NULL; + bool result = ((DFHack::Maps*)maps)->ReadVegetation(x, y, z, &plants); + if(!result || plants.size() <= 0) + { + return NULL; + } + else + { + ((*alloc_tree_buffer_callback)(&buf, plants.size())); + if(buf == NULL) + return NULL; + copy(plants.begin(), plants.end(), buf); + return buf; + } + } + + return NULL; } #ifdef __cplusplus diff --git a/library/modules/Vegetation.cpp b/library/modules/Vegetation.cpp index 46f2636ee..eb662da60 100644 --- a/library/modules/Vegetation.cpp +++ b/library/modules/Vegetation.cpp @@ -88,18 +88,28 @@ bool Vegetation::Start(uint32_t & numplants) } -bool Vegetation::Read (const uint32_t index, t_tree & shrubbery) +bool Vegetation::Read (const uint32_t index, dfh_plant & shrubbery) { if(!d->Started) return false; // read pointer from vector at position uint32_t temp = d->p_veg->at (index); // read from memory - d->owner->read (temp + d->tree_desc_offset, sizeof (t_tree), (uint8_t *) &shrubbery); + d->d->readName(shrubbery.name,temp); + d->owner->read (temp + d->tree_desc_offset, sizeof (t_plant), (uint8_t *) &shrubbery.sdata); shrubbery.address = temp; return true; } +bool Vegetation::Write (dfh_plant & shrubbery) +{ + if(!d->Started) + return false; + d->owner->write (shrubbery.address + d->tree_desc_offset, sizeof (t_plant), (uint8_t *) &shrubbery.sdata); + return true; +} + + bool Vegetation::Finish() { if(d->p_veg) diff --git a/library/modules/Vegetation_C.cpp b/library/modules/Vegetation_C.cpp index 848a24a95..58607dca6 100644 --- a/library/modules/Vegetation_C.cpp +++ b/library/modules/Vegetation_C.cpp @@ -57,14 +57,14 @@ int Vegetation_Finish(DFHackObject* veg) return -1; } -int Vegetation_Read(DFHackObject* veg, const uint32_t index, t_tree* shrubbery) +int Vegetation_Read(DFHackObject* veg, const uint32_t index, dfh_plant* shrubbery) { - if(veg != NULL) - { - return ((DFHack::Vegetation*)veg)->Read(index, *shrubbery); - } - - return -1; + if(veg != NULL) + { + return ((DFHack::Vegetation*)veg)->Read(index, *shrubbery); + } + + return -1; } #ifdef __cplusplus diff --git a/library/private/ContextShared.h b/library/private/ContextShared.h index f8b24491e..4a248d0b3 100644 --- a/library/private/ContextShared.h +++ b/library/private/ContextShared.h @@ -66,6 +66,7 @@ namespace DFHack uint32_t name_language_offset; uint32_t name_set_offset; bool namesInited; + bool namesFailed; ProcessEnumerator* pm; Process* p; diff --git a/tools/examples/treedump.cpp b/tools/examples/treedump.cpp index f75aa39f9..79d08819d 100644 --- a/tools/examples/treedump.cpp +++ b/tools/examples/treedump.cpp @@ -26,31 +26,31 @@ using namespace std; // a vector is here uint32_t address; */ -void print_tree( DFHack::Context * DF , DFHack::t_tree & tree) +void print_tree( DFHack::Context * DF , DFHack::dfh_plant & tree) { DFHack::Materials * mat = DF->getMaterials(); - - printf("%d:%d = ",tree.type,tree.material); - if(tree.type == 1 || tree.type == 3) + DFHack::t_plant & tdata = tree.sdata; + printf("%d:%d = ",tdata.type,tdata.material); + if(tdata.watery) { cout << "near-water "; } - cout << mat->organic[tree.material].id << " "; - if(tree.type == 0 || tree.type == 1) + cout << mat->organic[tdata.material].id << " "; + if(!tdata.is_shrub) { cout << "tree"; } - if(tree.type == 2 || tree.type == 3) + else { cout << "shrub"; } cout << endl; - printf("unknown_1: 0x%08x\n", tree.unknown_1); - printf("temperature_1: %d\n", tree.temperature_1); - printf("temperature_2: %d\n", tree.temperature_2); - printf("mystery_flag: %d\n", tree.mystery_flag); - printf("unknown_2: 0x%08x\n", tree.unknown_2); - printf("unknown_3: 0x%08x\n", tree.unknown_3); + printf("unknown_1: 0x%08x\n", tdata.unknown_1); + printf("temperature_1: %d\n", tdata.temperature_1); + printf("temperature_2: %d\n", tdata.temperature_2); + printf("On fire: %d\n", tdata.is_burning); + printf("hitpoints: 0x%08x\n", tdata.hitpoints); + printf("unknown_3: 0x%08x\n", tdata.unknown_3); printf("Address: 0x%x\n", tree.address); hexdump(DF,tree.address,13*16); } @@ -97,9 +97,9 @@ int main (int numargs, const char ** args) cout << "----==== Trees ====----" << endl; for(uint32_t i =0; i < numVegs; i++) { - DFHack::t_tree tree; + DFHack::dfh_plant tree; v->Read(i,tree); - printf("%d/%d/%d, %d:%d\n",tree.x,tree.y,tree.z,tree.type,tree.material); + printf("%d/%d/%d, %d:%d\n",tree.sdata.x,tree.sdata.y,tree.sdata.z,tree.sdata.type,tree.sdata.material); } } else @@ -107,14 +107,14 @@ int main (int numargs, const char ** args) // new method, gets the vector of trees in a block. can show farm plants if(mps->Start()) { - vector alltrees; + vector alltrees; if(mps->ReadVegetation(x/16,y/16,z,&alltrees)) { for(int i = 0 ; i < alltrees.size(); i++) { - DFHack::t_tree & tree = alltrees[i]; + DFHack::dfh_plant & tree = alltrees[i]; // you could take the tree coords from the struct and % them with 16 for use in loops over the whole block - if(tree.x == x && tree.y == y && tree.z == z) + if(tree.sdata.x == x && tree.sdata.y == y && tree.sdata.z == z) { cout << "----==== Tree at "<< x << "/" << y << "/" << z << " ====----" << endl; print_tree(DF, tree); @@ -126,9 +126,9 @@ int main (int numargs, const char ** args) // old method, gets the tree from the global vegetation vector. can't show farm plants for(uint32_t i =0; i < numVegs; i++) { - DFHack::t_tree tree; + DFHack::dfh_plant tree; v->Read(i,tree); - if(tree.x == x && tree.y == y && tree.z == z) + if(tree.sdata.x == x && tree.sdata.y == y && tree.sdata.z == z) { cout << "----==== Tree at "<< dec << x << "/" << y << "/" << z << " ====----" << endl; print_tree(DF, tree); diff --git a/tools/playground/CMakeLists.txt b/tools/playground/CMakeLists.txt index 06006bc96..d63dd8ef4 100644 --- a/tools/playground/CMakeLists.txt +++ b/tools/playground/CMakeLists.txt @@ -19,6 +19,9 @@ ENDIF() # a creature mood dump hack. has hardcoded offsets DFHACK_TOOL(dfmoodump moodump.cpp) +# burn trees to ashes +DFHACK_TOOL(dfimmolate immolate.cpp) + # bauxite - turn all mechanisms into bauxite mechanisms # Author: Alex Legg # FIXME: turned off. there is no reliable Items module. diff --git a/tools/supported/prospector.cpp b/tools/supported/prospector.cpp index 0370dec7c..e543adc60 100644 --- a/tools/supported/prospector.cpp +++ b/tools/supported/prospector.cpp @@ -23,7 +23,7 @@ typedef std::vector< pair > MatSorter; typedef std::vector FeatureList; typedef std::vector FeatureListPointer; typedef std::map FeatureMap; -typedef std::vector PlantList; +typedef std::vector PlantList; bool parseOptions(int argc, char **argv, bool &showHidden, bool &showPlants, bool &showSlade, bool &showTemple) @@ -316,15 +316,15 @@ int main(int argc, char *argv[]) { for (PlantList::const_iterator it = plants.begin(); it != plants.end(); it++) { - DFHack::t_tree plant = *it; + const DFHack::t_plant & plant = (*it).sdata; DFHack::DFCoord loc(plant.x, plant.y); loc = loc % 16; if (showHidden || !b->DesignationAt(loc).bits.hidden) { if(plant.is_shrub) - plantMats[it->material]++; + plantMats[plant.material]++; else - treeMats[it->material]++; + treeMats[plant.material]++; } } }