diff --git a/cmake/unix.cmake b/cmake/unix.cmake index 7dbd2f99f..94dc55689 100644 --- a/cmake/unix.cmake +++ b/cmake/unix.cmake @@ -243,7 +243,7 @@ endif() if (NOT NO_COTIRE) set_target_properties(slade PROPERTIES - COTIRE_CXX_PREFIX_HEADER_INIT "common.h" + COTIRE_CXX_PREFIX_HEADER_INIT "Application/Main.h" # Enable multithreaded unity builds by default # because otherwise probably no one would realize how COTIRE_UNITY_SOURCE_MAXIMUM_NUMBER_OF_INCLUDES -j diff --git a/cmake/win_msvc.cmake b/cmake/win_msvc.cmake index c3bd55a4e..09fa75a69 100644 --- a/cmake/win_msvc.cmake +++ b/cmake/win_msvc.cmake @@ -78,7 +78,7 @@ set_target_properties(slade ) # Precompiled Header -target_precompile_headers(slade PRIVATE "common.h") +target_precompile_headers(slade PRIVATE "Application/Main.h") # Link target_link_libraries(slade diff --git a/src/.clang-format b/src/.clang-format index 9bc21f056..b976c2f1f 100644 --- a/src/.clang-format +++ b/src/.clang-format @@ -62,3 +62,9 @@ TabWidth: 4 UseTab: ForContinuationAndIndentation PenaltyReturnTypeOnItsOwnLine: 1000 PenaltyBreakAssignment: 1000 + +AlignConsecutiveShortCaseStatements: + Enabled: true + AcrossEmptyLines: true + AcrossComments: true + AlignCaseColons: false diff --git a/src/Application/App.cpp b/src/Application/App.cpp index 2d0fd39f9..d97b7f9ab 100644 --- a/src/Application/App.cpp +++ b/src/Application/App.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -33,7 +33,8 @@ #include "Main.h" #include "App.h" #include "Archive/ArchiveManager.h" -#include "Game/Configuration.h" +#include "Game/Game.h" +#include "Game/SpecialPreset.h" #include "General/Clipboard.h" #include "General/ColourConfiguration.h" #include "General/Console.h" @@ -60,12 +61,17 @@ #include "UI/WxUtils.h" #include "Utility/StringUtils.h" #include "Utility/Tokenizer.h" +#include #include #include #ifdef __WXOSX__ #include #endif +#ifndef _WIN32 +#undef _WINDOWS_ // Undefine _WINDOWS_ that has been defined by FreeImage +#endif + using namespace slade; @@ -748,12 +754,12 @@ string app::path(string_view filename, Dir dir) { switch (dir) { - case Dir::User: return fmt::format("{}{}{}", dir_user, dir_separator, filename); - case Dir::Data: return fmt::format("{}{}{}", dir_data, dir_separator, filename); + case Dir::User: return fmt::format("{}{}{}", dir_user, dir_separator, filename); + case Dir::Data: return fmt::format("{}{}{}", dir_data, dir_separator, filename); case Dir::Executable: return fmt::format("{}{}{}", dir_app, dir_separator, filename); - case Dir::Resources: return fmt::format("{}{}{}", dir_res, dir_separator, filename); - case Dir::Temp: return fmt::format("{}{}{}", dir_temp, dir_separator, filename); - default: return string{ filename }; + case Dir::Resources: return fmt::format("{}{}{}", dir_res, dir_separator, filename); + case Dir::Temp: return fmt::format("{}{}{}", dir_temp, dir_separator, filename); + default: return string{ filename }; } } diff --git a/src/common.h b/src/Application/Common.h similarity index 89% rename from src/common.h rename to src/Application/Common.h index f44cc0c54..49d104d3b 100644 --- a/src/common.h +++ b/src/Application/Common.h @@ -1,5 +1,6 @@ -#ifndef COMMON_H -#define COMMON_H + +#ifndef __COMMON_H__ +#define __COMMON_H__ // wxWidgets ------------------------------------------------------------------- @@ -102,21 +103,6 @@ // Other Libraries ------------------------------------------------------------- -// Fluidsynth -#ifndef NO_FLUIDSYNTH -#include -#endif - -// SFML -#include - -// Freeimage -#define FREEIMAGE_LIB -#include -#ifndef _WIN32 -#undef _WINDOWS_ // Undefine _WINDOWS_ that has been defined by FreeImage -#endif - // fmt #include @@ -134,6 +120,7 @@ #include #include #include +#include #include -#endif // COMMON_H +#endif // __COMMON_H__ diff --git a/src/Application/Main.h b/src/Application/Main.h index d93eefe5f..a1aa34f5d 100644 --- a/src/Application/Main.h +++ b/src/Application/Main.h @@ -2,8 +2,7 @@ #ifndef __MAIN_H__ #define __MAIN_H__ -#include "common.h" -#include "common2.h" +#include "Common.h" #if defined _MSC_VER && _MSC_VER < 1900 #define _CRT_SECURE_NO_WARNINGS 1 diff --git a/src/Application/SLADEWxApp.cpp b/src/Application/SLADEWxApp.cpp index 256427fb8..6f96dc896 100644 --- a/src/Application/SLADEWxApp.cpp +++ b/src/Application/SLADEWxApp.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -71,7 +71,7 @@ string sc_rev; #ifdef DEBUG bool debug = true; #else -bool debug = false; +bool debug = false; #endif int win_version_major = 0; @@ -442,7 +442,7 @@ bool SLADEWxApp::OnInit() #ifdef __WINDOWS__ wxApp::SetAppName("SLADE3"); #else - wxApp::SetAppName("slade3"); + wxApp::SetAppName("slade3"); #endif // Handle exceptions using wxDebug stuff, but only in release mode @@ -457,11 +457,11 @@ bool SLADEWxApp::OnInit() // Should be constant, wxWidgets Cocoa backend scales everything under the hood const double ui_scale = 1.0; #else // !__APPLE__ - // Calculate scaling factor (from system ppi) - wxMemoryDC dc; - double ui_scale = static_cast(dc.GetPPI().x) / 96.0; - if (ui_scale < 1.) - ui_scale = 1.; + // Calculate scaling factor (from system ppi) + wxMemoryDC dc; + double ui_scale = static_cast(dc.GetPPI().x) / 96.0; + if (ui_scale < 1.) + ui_scale = 1.; #endif // __APPLE__ // Get Windows version diff --git a/src/Archive/Archive.cpp b/src/Archive/Archive.cpp index e6f5786b1..e3b31b5fa 100644 --- a/src/Archive/Archive.cpp +++ b/src/Archive/Archive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -36,6 +36,7 @@ #include "Utility/FileUtils.h" #include "Utility/Parser.h" #include "Utility/StringUtils.h" +#include #include using namespace slade; @@ -72,8 +73,7 @@ class EntryRenameUS : public UndoStep bool doUndo() override { // Get entry parent dir - const auto dir = archive_->dirAtPath(entry_path_); - if (dir) + if (const auto dir = archive_->dirAtPath(entry_path_)) { // Rename entry const auto entry = dir->entryAt(entry_index_); @@ -86,8 +86,7 @@ class EntryRenameUS : public UndoStep bool doRedo() override { // Get entry parent dir - const auto dir = archive_->dirAtPath(entry_path_); - if (dir) + if (const auto dir = archive_->dirAtPath(entry_path_)) { // Rename entry const auto entry = dir->entryAt(entry_index_); @@ -151,15 +150,17 @@ class EntrySwapUS : public UndoStep { public: EntrySwapUS(const ArchiveDir* dir, unsigned index1, unsigned index2) : - archive_{ dir->archive() }, path_{ dir->path() }, index1_{ index1 }, index2_{ index2 } + archive_{ dir->archive() }, + path_{ dir->path() }, + index1_{ index1 }, + index2_{ index2 } { } bool doSwap() const { // Get parent dir - auto dir = archive_->dirAtPath(path_); - if (dir) + if (const auto dir = archive_->dirAtPath(path_)) return dir->swapEntries(index1_, index2_); return false; } @@ -196,8 +197,7 @@ class EntryCreateDeleteUS : public UndoStep bool createEntry() const { // Get parent dir - const auto dir = archive_->dirAtPath(path_); - if (dir) + if (const auto dir = archive_->dirAtPath(path_)) { archive_->addEntry(std::make_shared(*entry_copy_), index_, dir); return true; @@ -223,7 +223,9 @@ class DirCreateDeleteUS : public UndoStep { public: DirCreateDeleteUS(bool created, ArchiveDir* dir) : - created_{ created }, archive_{ dir->archive() }, path_{ dir->path() } + created_{ created }, + archive_{ dir->archive() }, + path_{ dir->path() } { strutil::removePrefixIP(path_, '/'); @@ -282,7 +284,7 @@ class DirCreateDeleteUS : public UndoStep // ----------------------------------------------------------------------------- // -// Archive::MapDesc Class Functions +// MapDesc Struct Functions // // ----------------------------------------------------------------------------- @@ -291,7 +293,7 @@ class DirCreateDeleteUS : public UndoStep // Returns a list of all data entries (eg. LINEDEFS, TEXTMAP) for the map. // If [include_head] is true, the map header entry is also added // ----------------------------------------------------------------------------- -vector Archive::MapDesc::entries(const Archive& parent, bool include_head) const +vector MapDesc::entries(const Archive& parent, bool include_head) const { vector list; @@ -313,7 +315,7 @@ vector Archive::MapDesc::entries(const Archive& parent, bool incl // ----------------------------------------------------------------------------- // Sets the appropriate 'MapFormat' extra property in all entries for the map // ----------------------------------------------------------------------------- -void Archive::MapDesc::updateMapFormatHints() const +void MapDesc::updateMapFormatHints() const { // Get parent archive Archive* parent = nullptr; @@ -326,13 +328,13 @@ void Archive::MapDesc::updateMapFormatHints() const string fmt_name; switch (format) { - case MapFormat::Doom: fmt_name = "doom"; break; - case MapFormat::Hexen: fmt_name = "hexen"; break; - case MapFormat::Doom64: fmt_name = "doom64"; break; - case MapFormat::UDMF: fmt_name = "udmf"; break; + case MapFormat::Doom: fmt_name = "doom"; break; + case MapFormat::Hexen: fmt_name = "hexen"; break; + case MapFormat::Doom64: fmt_name = "doom64"; break; + case MapFormat::UDMF: fmt_name = "udmf"; break; case MapFormat::Doom32X: fmt_name = "doom32x"; break; case MapFormat::Unknown: - default: fmt_name = "unknown"; break; + default: fmt_name = "unknown"; break; } // Set format hint in map entries @@ -747,7 +749,7 @@ void Archive::entryStateChanged(ArchiveEntry* entry) // ----------------------------------------------------------------------------- // Adds the directory structure starting from [start] to [list] // ----------------------------------------------------------------------------- -void Archive::putEntryTreeAsList(vector& list, ArchiveDir* start) const +void Archive::putEntryTreeAsList(vector& list, const ArchiveDir* start) const { // If no start dir is specified, use the root dir if (!start) @@ -766,7 +768,7 @@ void Archive::putEntryTreeAsList(vector& list, ArchiveDir* start) // ----------------------------------------------------------------------------- // Adds the directory structure starting from [start] to [list] // ----------------------------------------------------------------------------- -void Archive::putEntryTreeAsList(vector>& list, ArchiveDir* start) const +void Archive::putEntryTreeAsList(vector>& list, const ArchiveDir* start) const { // If no start dir is specified, use the root dir if (!start) @@ -1429,12 +1431,11 @@ ArchiveEntry* Archive::findFirst(SearchOptions& options) { for (unsigned a = 0; a < dir->numSubdirs(); a++) { - auto opt = options; - opt.dir = dir->subdirAt(a).get(); - const auto match = findFirst(opt); + auto opt = options; + opt.dir = dir->subdirAt(a).get(); // If a match was found in this subdir, return it - if (match) + if (const auto match = findFirst(opt)) return match; } } @@ -1499,12 +1500,11 @@ ArchiveEntry* Archive::findLast(SearchOptions& options) { for (int a = static_cast(dir->numSubdirs()) - 1; a >= 0; a--) { - auto opt = options; - opt.dir = dir->subdirAt(a).get(); - const auto match = findLast(opt); + auto opt = options; + opt.dir = dir->subdirAt(a).get(); // If a match was found in this subdir, return it - if (match) + if (const auto match = findLast(opt)) return match; } } diff --git a/src/Archive/Archive.h b/src/Archive/Archive.h index 857bbede0..f8f34b9e3 100644 --- a/src/Archive/Archive.h +++ b/src/Archive/Archive.h @@ -2,7 +2,7 @@ #include "ArchiveDir.h" #include "ArchiveEntry.h" -#include "General/Defs.h" +#include "MapDesc.h" namespace slade { @@ -25,26 +25,6 @@ struct ArchiveFormat class Archive { public: - struct MapDesc - { - string name; - weak_ptr head; - weak_ptr end; // The last entry of the map data - MapFormat format; // See MapTypes enum - bool archive; // True if head is an archive (for maps in zips) - - vector unk; // Unknown map lumps (must be preserved for UDMF compliance) - - MapDesc() - { - archive = false; - format = MapFormat::Unknown; - } - - vector entries(const Archive& parent, bool include_head = false) const; - void updateMapFormatHints() const; - }; - static bool save_backup; Archive(string_view format = ""); @@ -92,10 +72,10 @@ class Archive virtual unsigned numEntries(); virtual void close(); void entryStateChanged(ArchiveEntry* entry); - void putEntryTreeAsList(vector& list, ArchiveDir* start = nullptr) const; - void putEntryTreeAsList(vector>& list, ArchiveDir* start = nullptr) const; - bool canSave() const { return parent_.lock() || on_disk_; } - virtual bool paste(ArchiveDir* tree, unsigned position = 0xFFFFFFFF, shared_ptr base = nullptr); + void putEntryTreeAsList(vector& list, const ArchiveDir* start = nullptr) const; + void putEntryTreeAsList(vector>& list, const ArchiveDir* start = nullptr) const; + bool canSave() const { return parent_.lock() || on_disk_; } + virtual bool paste(ArchiveDir* tree, unsigned position = 0xFFFFFFFF, shared_ptr base = nullptr); virtual bool importDir(string_view directory, bool ignore_hidden = false, shared_ptr base = nullptr); virtual bool hasFlatHack() { return false; } diff --git a/src/Archive/ArchiveDir.cpp b/src/Archive/ArchiveDir.cpp index b1a68bc89..a405d8a3c 100644 --- a/src/Archive/ArchiveDir.cpp +++ b/src/Archive/ArchiveDir.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -71,7 +71,8 @@ void buildDirList(vector>& list, ArchiveDir const* dir) // ArchiveDir class constructor // ----------------------------------------------------------------------------- ArchiveDir::ArchiveDir(string_view name, const shared_ptr& parent, Archive* archive) : - archive_{ archive }, parent_dir_{ parent } + archive_{ archive }, + parent_dir_{ parent } { // Init dir entry dir_entry_ = std::make_unique(name); @@ -261,7 +262,7 @@ shared_ptr ArchiveDir::sharedEntry(string_view name, bool cut_ext) // Returns a shared pointer to [entry] in this directory, or null if no entries // match // ----------------------------------------------------------------------------- -shared_ptr ArchiveDir::sharedEntry(ArchiveEntry* entry) const +shared_ptr ArchiveDir::sharedEntry(const ArchiveEntry* entry) const { // Find entry for (auto& e : entries_) @@ -684,7 +685,7 @@ shared_ptr ArchiveDir::entryAtPath(const shared_ptr& r // ----------------------------------------------------------------------------- bool ArchiveDir::merge( shared_ptr& target, - ArchiveDir* dir, + const ArchiveDir* dir, unsigned position, ArchiveEntry::State state, vector>* created_dirs, @@ -755,7 +756,7 @@ shared_ptr ArchiveDir::getOrCreateSubdir( // added (directory entries for subdirs will still be added). It should only // really be set to false if [root] is an actual root directory and has no name // ----------------------------------------------------------------------------- -void ArchiveDir::entryTreeAsList(ArchiveDir* root, vector>& list, bool include_dir_entry) +void ArchiveDir::entryTreeAsList(const ArchiveDir* root, vector>& list, bool include_dir_entry) { if (include_dir_entry) list.push_back(root->dir_entry_); @@ -771,7 +772,7 @@ void ArchiveDir::entryTreeAsList(ArchiveDir* root, vector ArchiveDir::getShared(ArchiveDir* dir) +shared_ptr ArchiveDir::getShared(const ArchiveDir* dir) { if (!dir) return nullptr; diff --git a/src/Archive/ArchiveDir.h b/src/Archive/ArchiveDir.h index edbb3dd74..b0945a7ae 100644 --- a/src/Archive/ArchiveDir.h +++ b/src/Archive/ArchiveDir.h @@ -31,7 +31,7 @@ class ArchiveDir shared_ptr sharedEntryAt(unsigned index) const; ArchiveEntry* entry(string_view name, bool cut_ext = false) const; shared_ptr sharedEntry(string_view name, bool cut_ext = false) const; - shared_ptr sharedEntry(ArchiveEntry* entry) const; + shared_ptr sharedEntry(const ArchiveEntry* entry) const; unsigned numEntries(bool inc_subdirs = false) const; int entryIndex(ArchiveEntry* entry, size_t startfrom = 0) const; vector> allEntries() const; @@ -64,7 +64,7 @@ class ArchiveDir static shared_ptr entryAtPath(const shared_ptr& root, string_view path); static bool merge( shared_ptr& target, - ArchiveDir* dir, + const ArchiveDir* dir, unsigned position = -1, ArchiveEntry::State state = ArchiveEntry::State::New, vector>* created_dirs = nullptr, @@ -74,10 +74,10 @@ class ArchiveDir string_view path, vector>* created_dirs = nullptr); static void entryTreeAsList( - ArchiveDir* root, + const ArchiveDir* root, vector>& list, bool include_dir_entry = false); - static shared_ptr getShared(ArchiveDir* dir); + static shared_ptr getShared(const ArchiveDir* dir); static shared_ptr findDirByDirEntry(shared_ptr dir_root, const ArchiveEntry& entry); private: diff --git a/src/Archive/ArchiveEntry.cpp b/src/Archive/ArchiveEntry.cpp index a14b9686d..972c821e3 100644 --- a/src/Archive/ArchiveEntry.cpp +++ b/src/Archive/ArchiveEntry.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -76,7 +76,10 @@ unsigned maxEntrySizeBytes() // ArchiveEntry class constructor // ----------------------------------------------------------------------------- ArchiveEntry::ArchiveEntry(string_view name, uint32_t size) : - name_{ name }, upper_name_{ name }, data_{ size }, type_{ EntryType::unknownType() } + name_{ name }, + upper_name_{ name }, + data_{ size }, + type_{ EntryType::unknownType() } { strutil::upperIP(upper_name_); } @@ -178,7 +181,7 @@ ArchiveEntry* ArchiveEntry::prevEntry() // Returns the parent ArchiveDir's shared pointer to this entry, or // nullptr if this entry has no parent // ----------------------------------------------------------------------------- -shared_ptr ArchiveEntry::getShared() +shared_ptr ArchiveEntry::getShared() const { return parent_ ? parent_->sharedEntry(this) : nullptr; } @@ -262,7 +265,7 @@ void ArchiveEntry::formatName(const ArchiveFormat& format) // Remove \ or / if the format supports folders if (format.supports_dirs && (name_.find('/') != string::npos || name_.find('\\') != string::npos)) - name_ = misc::lumpNameToFileName(name_); + name_ = misc::lumpNameToFileName(name_); // Remove extension if the format doesn't have them if (!format.names_extensions) @@ -566,7 +569,7 @@ bool ArchiveEntry::write(const void* data, uint32_t size) // ----------------------------------------------------------------------------- // Reads data from the entry MemChunk // ----------------------------------------------------------------------------- -bool ArchiveEntry::read(void* buf, uint32_t size) +bool ArchiveEntry::read(void* buf, uint32_t size) const { return data_.read(buf, size); } diff --git a/src/Archive/ArchiveEntry.h b/src/Archive/ArchiveEntry.h index 5c1f59223..c1ded9788 100644 --- a/src/Archive/ArchiveEntry.h +++ b/src/Archive/ArchiveEntry.h @@ -58,7 +58,7 @@ class ArchiveEntry Encryption encryption() const { return encrypted_; } ArchiveEntry* nextEntry(); ArchiveEntry* prevEntry(); - shared_ptr getShared(); + shared_ptr getShared() const; int index(); // Modifiers (won't change entry state, except setState of course :P) @@ -95,8 +95,8 @@ class ArchiveEntry // Data access bool write(const void* data, uint32_t size); - bool read(void* buf, uint32_t size); - bool seek(uint32_t offset, uint32_t start) { return data_.seek(offset, start); } + bool read(void* buf, uint32_t size) const; + bool seek(uint32_t offset, uint32_t start) const { return data_.seek(offset, start); } uint32_t currentPos() const { return data_.currentPos(); } // Data on disk diff --git a/src/Archive/ArchiveManager.cpp b/src/Archive/ArchiveManager.cpp index 9d0d5a873..d0b769b7a 100644 --- a/src/Archive/ArchiveManager.cpp +++ b/src/Archive/ArchiveManager.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -225,7 +225,7 @@ bool ArchiveManager::addArchive(shared_ptr archive) shared_ptr ArchiveManager::getArchive(int index) { // Check that index is valid - if (index < 0 || index >= (int)open_archives_.size()) + if (index < 0 || index >= static_cast(open_archives_.size())) return nullptr; else return open_archives_[index].archive; @@ -253,7 +253,7 @@ shared_ptr ArchiveManager::getArchive(string_view filename) // Returns the archive opened from the given parent entry // (nullptr if it doesn't exist) // ---------------------------------------------------------------------------- -shared_ptr ArchiveManager::getArchive(ArchiveEntry* parent) +shared_ptr ArchiveManager::getArchive(const ArchiveEntry* parent) { for (unsigned a = 0; a < open_archives_.size(); ++a) { @@ -573,7 +573,7 @@ shared_ptr ArchiveManager::newArchive(string_view format) bool ArchiveManager::closeArchive(int index) { // Check for invalid index - if (index < 0 || index >= (int)open_archives_.size()) + if (index < 0 || index >= static_cast(open_archives_.size())) return false; // Announce archive closing @@ -597,11 +597,9 @@ bool ArchiveManager::closeArchive(int index) } // Remove ourselves from our parent's open-child list - auto parent = open_archives_[index].archive->parentEntry(); - if (parent) + if (auto parent = open_archives_[index].archive->parentEntry()) { - auto gp = parent->parent(); - if (gp) + if (auto gp = parent->parent()) { int pi = archiveIndex(gp); if (pi >= 0) @@ -641,7 +639,7 @@ bool ArchiveManager::closeArchive(int index) bool ArchiveManager::closeArchive(string_view filename) { // Go through all open archives - for (int a = 0; a < (int)open_archives_.size(); a++) + for (int a = 0; a < static_cast(open_archives_.size()); a++) { // If the filename matches, remove it if (open_archives_[a].archive->filename() == filename) @@ -656,10 +654,10 @@ bool ArchiveManager::closeArchive(string_view filename) // Closes the specified archive and removes it from the list, if it exists in // the list. Returns false if it doesn't exist, else true // ----------------------------------------------------------------------------- -bool ArchiveManager::closeArchive(Archive* archive) +bool ArchiveManager::closeArchive(const Archive* archive) { // Go through all open archives - for (int a = 0; a < (int)open_archives_.size(); a++) + for (int a = 0; a < static_cast(open_archives_.size()); a++) { // If the archive exists in the list, remove it if (open_archives_[a].archive.get() == archive) @@ -684,14 +682,14 @@ void ArchiveManager::closeAll() // Returns the index in the list of the given archive, or -1 if the archive // doesn't exist in the list // ----------------------------------------------------------------------------- -int ArchiveManager::archiveIndex(Archive* archive) +int ArchiveManager::archiveIndex(const Archive* archive) const { // Go through all open archives for (size_t a = 0; a < open_archives_.size(); a++) { // If the archive we're looking for is this one, return the index if (open_archives_[a].archive.get() == archive) - return (int)a; + return static_cast(a); } // If we get to here the archive wasn't found, so return -1 @@ -702,7 +700,7 @@ int ArchiveManager::archiveIndex(Archive* archive) // Returns all open archives that live inside this one, recursively. // ----------------------------------------------------------------------------- // This is the recursive bit, separate from the public entry point -void ArchiveManager::getDependentArchivesInternal(Archive* archive, vector>& vec) +void ArchiveManager::getDependentArchivesInternal(const Archive* archive, vector>& vec) { int ai = archiveIndex(archive); @@ -715,7 +713,7 @@ void ArchiveManager::getDependentArchivesInternal(Archive* archive, vector> ArchiveManager::getDependentArchives(Archive* archive) +vector> ArchiveManager::getDependentArchives(const Archive* archive) { vector> vec; getDependentArchivesInternal(archive, vec); @@ -757,7 +755,7 @@ string ArchiveManager::getArchiveExtensionsString() const // ----------------------------------------------------------------------------- // Returns true if [archive] is set to be used as a resource, false otherwise // ----------------------------------------------------------------------------- -bool ArchiveManager::archiveIsResource(Archive* archive) +bool ArchiveManager::archiveIsResource(const Archive* archive) const { int index = archiveIndex(archive); if (index < 0) @@ -789,7 +787,7 @@ void ArchiveManager::setArchiveResource(Archive* archive, bool resource) // Returns a vector of all open archives. // If [resources_only] is true, only includes archives marked as resources // ----------------------------------------------------------------------------- -vector> ArchiveManager::allArchives(bool resource_only) +vector> ArchiveManager::allArchives(bool resource_only) const { vector> ret; @@ -804,7 +802,7 @@ vector> ArchiveManager::allArchives(bool resource_only) // Returns a shared_ptr to the given [archive], or nullptr if it isn't open in // the archive manager // ----------------------------------------------------------------------------- -shared_ptr ArchiveManager::shareArchive(Archive* const archive) +shared_ptr ArchiveManager::shareArchive(const Archive* const archive) { if (archive == base_resource_archive_.get()) return base_resource_archive_; @@ -851,11 +849,11 @@ void ArchiveManager::removeBaseResourcePath(unsigned index) return; // Unload base resource if removed is open - if (index == (unsigned)base_resource) + if (index == static_cast(base_resource)) openBaseResource(-1); // Modify base_resource cvar if needed - else if (base_resource > (signed)index) + else if (base_resource > static_cast(index)) base_resource = base_resource - 1; // Remove the path @@ -894,7 +892,7 @@ bool ArchiveManager::openBaseResource(int index) } // Check index - if (index < 0 || (unsigned)index >= base_resource_paths_.size()) + if (index < 0 || static_cast(index) >= base_resource_paths_.size()) { base_resource = -1; signals_.base_res_current_cleared(); @@ -930,7 +928,7 @@ bool ArchiveManager::openBaseResource(int index) // Returns the first entry matching [name] in the resource archives. // Resource archives = open archives -> base resource archives. // ----------------------------------------------------------------------------- -ArchiveEntry* ArchiveManager::getResourceEntry(string_view name, Archive* ignore) +ArchiveEntry* ArchiveManager::getResourceEntry(string_view name, const Archive* ignore) const { // Go through all open archives for (auto& open_archive : open_archives_) @@ -944,8 +942,7 @@ ArchiveEntry* ArchiveManager::getResourceEntry(string_view name, Archive* ignore continue; // Try to find the entry in the archive - auto entry = open_archive.archive->entry(name); - if (entry) + if (auto entry = open_archive.archive->entry(name)) return entry; } @@ -959,7 +956,7 @@ ArchiveEntry* ArchiveManager::getResourceEntry(string_view name, Archive* ignore // ----------------------------------------------------------------------------- // Searches for an entry matching [options] in the resource archives // ----------------------------------------------------------------------------- -ArchiveEntry* ArchiveManager::findResourceEntry(Archive::SearchOptions& options, Archive* ignore) +ArchiveEntry* ArchiveManager::findResourceEntry(Archive::SearchOptions& options, const Archive* ignore) const { // Go through all open archives for (auto& open_archive : open_archives_) @@ -973,8 +970,7 @@ ArchiveEntry* ArchiveManager::findResourceEntry(Archive::SearchOptions& options, continue; // Try to find the entry in the archive - auto entry = open_archive.archive->findLast(options); - if (entry) + if (auto entry = open_archive.archive->findLast(options)) return entry; } @@ -988,7 +984,8 @@ ArchiveEntry* ArchiveManager::findResourceEntry(Archive::SearchOptions& options, // ----------------------------------------------------------------------------- // Searches for entries matching [options] in the resource archives // ----------------------------------------------------------------------------- -vector ArchiveManager::findAllResourceEntries(Archive::SearchOptions& options, Archive* ignore) +vector ArchiveManager::findAllResourceEntries(Archive::SearchOptions& options, const Archive* ignore) + const { vector ret; @@ -1063,7 +1060,7 @@ void ArchiveManager::addRecentFile(string_view path) recent_files_.insert(recent_files_.begin(), file_path); // Keep it trimmed - while (recent_files_.size() > (unsigned)max_recent_files) + while (recent_files_.size() > static_cast(max_recent_files)) recent_files_.pop_back(); // Announce @@ -1174,7 +1171,7 @@ bool ArchiveManager::deleteBookmark(unsigned index) // ----------------------------------------------------------------------------- // Removes any bookmarked entries in [archive] from the list // ----------------------------------------------------------------------------- -bool ArchiveManager::deleteBookmarksInArchive(Archive* archive) +bool ArchiveManager::deleteBookmarksInArchive(const Archive* archive) { // Go through bookmarks bool removed = false; @@ -1205,7 +1202,7 @@ bool ArchiveManager::deleteBookmarksInArchive(Archive* archive) // ----------------------------------------------------------------------------- // Removes any bookmarked entries in [node] from the list // ----------------------------------------------------------------------------- -bool ArchiveManager::deleteBookmarksInDir(ArchiveDir* node) +bool ArchiveManager::deleteBookmarksInDir(const ArchiveDir* node) { auto archive = node->archive(); bool removed = deleteBookmark(node->dirEntry()); @@ -1277,7 +1274,7 @@ void ArchiveManager::deleteAllBookmarks() // ----------------------------------------------------------------------------- // Returns the bookmarked entry at [index] // ----------------------------------------------------------------------------- -ArchiveEntry* ArchiveManager::getBookmark(unsigned index) +ArchiveEntry* ArchiveManager::getBookmark(unsigned index) const { // Check index if (index >= bookmarks_.size()) @@ -1289,7 +1286,7 @@ ArchiveEntry* ArchiveManager::getBookmark(unsigned index) // ----------------------------------------------------------------------------- // Returns true if [entry] exists in the bookmarks list // ----------------------------------------------------------------------------- -bool slade::ArchiveManager::isBookmarked(ArchiveEntry* entry) +bool slade::ArchiveManager::isBookmarked(const ArchiveEntry* entry) const { for (const auto& bm : bookmarks_) if (bm.lock().get() == entry) diff --git a/src/Archive/ArchiveManager.h b/src/Archive/ArchiveManager.h index 69a7bbc07..8e013e108 100644 --- a/src/Archive/ArchiveManager.h +++ b/src/Archive/ArchiveManager.h @@ -17,24 +17,24 @@ class ArchiveManager bool validResDir(string_view dir) const; shared_ptr getArchive(int index); shared_ptr getArchive(string_view filename); - shared_ptr getArchive(ArchiveEntry* parent); + shared_ptr getArchive(const ArchiveEntry* parent); shared_ptr openArchive(string_view filename, bool manage = true, bool silent = false); shared_ptr openArchive(ArchiveEntry* entry, bool manage = true, bool silent = false); shared_ptr openDirArchive(string_view dir, bool manage = true, bool silent = false); shared_ptr newArchive(string_view format); bool closeArchive(int index); bool closeArchive(string_view filename); - bool closeArchive(Archive* archive); + bool closeArchive(const Archive* archive); void closeAll(); - int numArchives() const { return (int)open_archives_.size(); } - int archiveIndex(Archive* archive); - vector> getDependentArchives(Archive* archive); + int numArchives() const { return static_cast(open_archives_.size()); } + int archiveIndex(const Archive* archive) const; + vector> getDependentArchives(const Archive* archive); Archive* programResourceArchive() const { return program_resource_archive_.get(); } string getArchiveExtensionsString() const; - bool archiveIsResource(Archive* archive); + bool archiveIsResource(const Archive* archive) const; void setArchiveResource(Archive* archive, bool resource = true); - vector> allArchives(bool resource_only = false); - shared_ptr shareArchive(Archive* archive); + vector> allArchives(bool resource_only = false) const; + shared_ptr shareArchive(const Archive* archive); // General access const vector& recentFiles() const { return recent_files_; } @@ -50,9 +50,10 @@ class ArchiveManager bool openBaseResource(int index); // Resource entry get/search - ArchiveEntry* getResourceEntry(string_view name, Archive* ignore = nullptr); - ArchiveEntry* findResourceEntry(Archive::SearchOptions& options, Archive* ignore = nullptr); - vector findAllResourceEntries(Archive::SearchOptions& options, Archive* ignore = nullptr); + ArchiveEntry* getResourceEntry(string_view name, const Archive* ignore = nullptr) const; + ArchiveEntry* findResourceEntry(Archive::SearchOptions& options, const Archive* ignore = nullptr) const; + vector findAllResourceEntries(Archive::SearchOptions& options, const Archive* ignore = nullptr) + const; // Recent files string recentFile(unsigned index); @@ -65,12 +66,12 @@ class ArchiveManager void addBookmark(const shared_ptr& entry); bool deleteBookmark(ArchiveEntry* entry); bool deleteBookmark(unsigned index); - bool deleteBookmarksInArchive(Archive* archive); - bool deleteBookmarksInDir(ArchiveDir* node); + bool deleteBookmarksInArchive(const Archive* archive); + bool deleteBookmarksInDir(const ArchiveDir* node); void deleteAllBookmarks(); - ArchiveEntry* getBookmark(unsigned index); + ArchiveEntry* getBookmark(unsigned index) const; unsigned numBookmarks() const { return bookmarks_.size(); } - bool isBookmarked(ArchiveEntry* entry); + bool isBookmarked(const ArchiveEntry* entry) const; // Signals struct Signals @@ -111,6 +112,6 @@ class ArchiveManager Signals signals_; bool initArchiveFormats() const; - void getDependentArchivesInternal(Archive* archive, vector>& vec); + void getDependentArchivesInternal(const Archive* archive, vector>& vec); }; } // namespace slade diff --git a/src/Archive/EntryType/DataFormats/AudioFormats.h b/src/Archive/EntryType/DataFormats/AudioFormats.h index db0033680..73f1a8a62 100644 --- a/src/Archive/EntryType/DataFormats/AudioFormats.h +++ b/src/Archive/EntryType/DataFormats/AudioFormats.h @@ -239,7 +239,7 @@ class MODModuleDataFormat : public EntryDataFormat if (mc.size() > 1084) { // Check format; note: byte 951 is used by NoiseTracker to indicate restart byte so it can be any value - if (mc[950] >= 0 && mc[950] <= 129 /*&& (mc[951] & 127) == 127*/) + if (mc[950] <= 129 /*&& (mc[951] & 127) == 127*/) { if ((mc[1080] == 'M' && mc[1081] == '.' && mc[1082] == 'K' && mc[1083] == '.') || (mc[1080] == 'M' && mc[1081] == '!' && mc[1082] == 'K' && mc[1083] == '!') @@ -529,15 +529,18 @@ class DoomPCSpeakerDataFormat : public EntryDataFormat // under the "WAVE form wFormatTag IDs" comment. // There are dozens upon dozens of them, most of // which are not usually seen in practice. -#define WAVE_FMT_UNK 0x0000 -#define WAVE_FMT_PCM 0x0001 -#define WAVE_FMT_ADPCM 0x0002 -#define WAVE_FMT_ALAW 0x0006 -#define WAVE_FMT_MULAW 0x0007 -#define WAVE_FMT_MP3 0x0055 -#define WAVE_FMT_XTNSBL 0xFFFE - -int RiffWavFormat(const MemChunk& mc) +enum +{ + WAVE_FMT_UNK = 0x0000, + WAVE_FMT_PCM = 0x0001, + WAVE_FMT_ADPCM = 0x0002, + WAVE_FMT_ALAW = 0x0006, + WAVE_FMT_MULAW = 0x0007, + WAVE_FMT_MP3 = 0x0055, + WAVE_FMT_XTNSBL = 0xFFFE +}; + +inline int RiffWavFormat(const MemChunk& mc) { // Check size size_t size = mc.size(); @@ -758,12 +761,11 @@ class AudioTPCSoundDataFormat : public EntryDataFormat if (size < (nsamples + 9) && size < 1024 && size > (nsamples + 6) && mc[nsamples + 6] == 0) return MATCH_TRUE; // Hack #1: last PC sound in Wolf3D/Spear carries a Muse end marker - else if ( - size == (nsamples + 11) && (mc[nsamples + 7] == '!') && (mc[nsamples + 8] == 'I') + if (size == (nsamples + 11) && (mc[nsamples + 7] == '!') && (mc[nsamples + 8] == 'I') && (mc[nsamples + 9] == 'D') && (mc[nsamples + 10] == '!')) return MATCH_TRUE; // Hack #2: Rise of the Triad's PCSP53 - else if (size == 150 && nsamples == 142 && mc[147] == 156 && mc[148] == 157 && mc[149] == 97) + if (size == 150 && nsamples == 142 && mc[147] == 156 && mc[148] == 157 && mc[149] == 97) return MATCH_TRUE; } return MATCH_FALSE; @@ -788,12 +790,11 @@ class AudioTAdlibSoundDataFormat : public EntryDataFormat if (size >= (nsamples + 24) && (mc[size - 1] == 0)) return MATCH_TRUE; // Hack #1: last Adlib sound in Wolf3D/Spear carries a Muse end marker - else if ( - size >= nsamples + 28 && mc[size - 1] == '!' && mc[size - 2] == 'D' && mc[size - 3] == 'I' + if (size >= nsamples + 28 && mc[size - 1] == '!' && mc[size - 2] == 'D' && mc[size - 3] == 'I' && mc[size - 4] == '!') return MATCH_TRUE; // Hack #2: Rise of the Triad's ADLB53 - else if (size == 166 && nsamples == 142 && mc[163] == 7 && mc[164] == 7 && mc[165] == 6) + if (size == 166 && nsamples == 142 && mc[163] == 7 && mc[164] == 7 && mc[165] == 6) return MATCH_TRUE; } return MATCH_FALSE; @@ -864,7 +865,7 @@ class SunSoundDataFormat : public EntryDataFormat } }; -CVAR(Bool, debugaiff, false, 0) +// CVAR(Bool, debugaiff, false, 0) class AIFFSoundDataFormat : public EntryDataFormat { public: @@ -883,12 +884,12 @@ class AIFFSoundDataFormat : public EntryDataFormat && mc[10] == 'F' && (mc[11] == 'F' || mc[11] == 'C')) { size_t size = mc.readB32(4) + 8; - if (debugaiff) - log::info(wxString::Format("size %d", size)); + // if (debugaiff) + // log::info(wxString::Format("size %d", size)); if (size > mc.size()) { - if (debugaiff) - log::info(wxString::Format("%d <= %d fails", size, mc.size())); + // if (debugaiff) + // log::info(wxString::Format("%d <= %d fails", size, mc.size())); return MATCH_FALSE; } size_t s = 12; @@ -896,8 +897,8 @@ class AIFFSoundDataFormat : public EntryDataFormat bool ssnd_found = false; while (s < size && !(comm_found && ssnd_found)) { - if (debugaiff) - log::info(wxString::Format("%d/%d", s, size)); + // if (debugaiff) + // log::info(wxString::Format("%d/%d", s, size)); if (mc[s + 0] == 'C' && mc[s + 1] == 'O' && mc[s + 2] == 'M' && mc[s + 3] == 'M') comm_found = true; else if (mc[s + 0] == 'S' && mc[s + 1] == 'S' && mc[s + 2] == 'N' && mc[s + 3] == 'D') @@ -905,14 +906,14 @@ class AIFFSoundDataFormat : public EntryDataFormat s += 8 + mc.readB32(s + 4); if (s % 2) ++s; - if (debugaiff) - log::info(wxString::Format("looking now at offset %d", s)); + // if (debugaiff) + // log::info(wxString::Format("looking now at offset %d", s)); } if (comm_found && ssnd_found) return MATCH_TRUE; - if (debugaiff) - log::info(wxString::Format( - "COMM was %sfound and SSND was %sfound", comm_found ? "" : "not ", ssnd_found ? "" : "not ")); + // if (debugaiff) + // log::info(wxString::Format( + // "COMM was %sfound and SSND was %sfound", comm_found ? "" : "not ", ssnd_found ? "" : "not ")); } } return MATCH_FALSE; diff --git a/src/Archive/EntryType/DataFormats/ImageFormats.h b/src/Archive/EntryType/DataFormats/ImageFormats.h index c348c78ce..53a6bc3f9 100644 --- a/src/Archive/EntryType/DataFormats/ImageFormats.h +++ b/src/Archive/EntryType/DataFormats/ImageFormats.h @@ -134,15 +134,15 @@ class PCXDataFormat : public EntryDataFormat for (size_t i = 74; i < 128; ++i) if (mc[i] != 0) return MATCH_FALSE; - int16_t offsx = (int16_t)mc.readL16(4); - int16_t limx = (int16_t)mc.readL16(8); + int16_t offsx = static_cast(mc.readL16(4)); + int16_t limx = static_cast(mc.readL16(8)); int16_t width = 1 + limx - offsx; // Compute number of bytes needed per scanline, and account for possible padding int16_t bnpsl = (width * mc[3]) / 8; if (bnpsl % 2) bnpsl++; // Bytes per scanline field is always an even number and should correspond to guessed value - int16_t bpsl = (int16_t)mc.readL16(66); + int16_t bpsl = static_cast(mc.readL16(66)); if (bpsl % 2 || bpsl != bnpsl) return MATCH_FALSE; // Passed all tests, so this seems to be a valid PCX @@ -171,7 +171,7 @@ class TGADataFormat : public EntryDataFormat // Let's have halfway "reasonable" limits on the compression ratio // that can be expected from a TGA picture... - if ((unsigned)(5000u * mc.size()) < (unsigned)(height * width)) + if ((unsigned)(5000u * mc.size()) < static_cast(height * width)) return MATCH_FALSE; // Check image type, must be a value between 1 and 3 or 9 and 11 @@ -220,19 +220,19 @@ class TIFFDataFormat : public EntryDataFormat // The value of 42 (0x2A) is present in the next two bytes, // in the given endianness if (42 - != (littleendian ? wxUINT16_SWAP_ON_BE((const uint16_t)(mc[2])) : + != (littleendian ? wxUINT16_SWAP_ON_BE(static_cast(mc[2])) : wxUINT16_SWAP_ON_LE((const uint16_t)(mc[2])))) return MATCH_FALSE; // First offset must be on a word boundary (therefore, %2 == 0) and // somewhere within the file, but not in the header of course. size_t offset = - (littleendian ? wxUINT32_SWAP_ON_BE((const uint32_t)(mc[4])) : + (littleendian ? wxUINT32_SWAP_ON_BE(static_cast(mc[4])) : wxUINT32_SWAP_ON_LE((const uint32_t)(mc[4]))); if (offset < 8 || offset >= size || offset % 2) return MATCH_FALSE; // Check the first IFD for validity uint16_t numentries = - (littleendian ? wxUINT16_SWAP_ON_BE((const uint16_t)(mc[offset])) : + (littleendian ? wxUINT16_SWAP_ON_BE(static_cast(mc[offset])) : wxUINT16_SWAP_ON_LE((const uint16_t)(mc[offset]))); if (offset + 6 + (numentries * 12) > size) return MATCH_FALSE; @@ -337,13 +337,13 @@ class DoomGfxDataFormat : public EntryDataFormat // Check size if (mc.size() > sizeof(gfx::PatchHeader)) { - const gfx::PatchHeader* header = (const gfx::PatchHeader*)data; + auto header = reinterpret_cast(data); // Check header values are 'sane' if (header->height > 0 && header->height < 4096 && header->width > 0 && header->width < 4096 && header->top > -2000 && header->top < 2000 && header->left > -2000 && header->left < 2000) { - uint32_t* col_offsets = (uint32_t*)((const uint8_t*)data + sizeof(gfx::PatchHeader)); + auto col_offsets = (uint32_t*)((const uint8_t*)data + sizeof(gfx::PatchHeader)); // Check there is room for needed column pointers if (mc.size() < sizeof(gfx::PatchHeader) + (header->width * sizeof(uint32_t))) @@ -389,7 +389,7 @@ class DoomGfxAlphaDataFormat : public EntryDataFormat if (mc[mc.size() - 1] != 0xFF) return MATCH_FALSE; - const gfx::OldPatchHeader* header = (const gfx::OldPatchHeader*)mc.data(); + auto header = reinterpret_cast(mc.data()); // Check header values are 'sane' if (header->width > 0 && header->height > 0) @@ -459,13 +459,13 @@ class DoomGfxBetaDataFormat : public EntryDataFormat } } - const gfx::PatchHeader* header = (const gfx::PatchHeader*)data; + auto header = reinterpret_cast(data); // Check header values are 'sane' if (header->height > 0 && header->height < 256 && header->width > 0 && header->width < 384 && header->top > -200 && header->top < 200 && header->left > -200 && header->left < 200) { - uint16_t* col_offsets = (uint16_t*)((const uint8_t*)data + sizeof(gfx::PatchHeader)); + auto col_offsets = (uint16_t*)((const uint8_t*)data + sizeof(gfx::PatchHeader)); // Check there is room for needed column pointers if (mc.size() < sizeof(gfx::PatchHeader) + (header->width * sizeof(uint16_t))) @@ -550,8 +550,8 @@ class DoomArahDataFormat : public EntryDataFormat if (mc.size() < sizeof(gfx::PatchHeader)) return MATCH_FALSE; - const uint8_t* data = mc.data(); - const gfx::PatchHeader* header = (const gfx::PatchHeader*)data; + auto data = mc.data(); + auto header = reinterpret_cast(data); // Check header values are 'sane' if (!(header->height > 0 && header->height < 4096 && header->width > 0 && header->width < 4096 @@ -572,19 +572,19 @@ class DoomJaguarDataFormat : public EntryDataFormat DoomJaguarDataFormat(int colmajor = 0, string_view id = "img_doom_jaguar") : EntryDataFormat(id), colmajor(colmajor){}; - ~DoomJaguarDataFormat() = default; + ~DoomJaguarDataFormat() override = default; int isThisFormat(const MemChunk& mc) override { if (mc.size() < sizeof(gfx::JagPicHeader)) return MATCH_FALSE; - const uint8_t* data = mc.data(); - const gfx::JagPicHeader* header = (const gfx::JagPicHeader*)data; - int width = wxINT16_SWAP_ON_LE(header->width); - int height = wxINT16_SWAP_ON_LE(header->height); - int depth = wxINT16_SWAP_ON_LE(header->depth); - int flags = wxINT16_SWAP_ON_LE(header->flags); + const uint8_t* data = mc.data(); + auto header = reinterpret_cast(data); + int width = wxINT16_SWAP_ON_LE(header->width); + int height = wxINT16_SWAP_ON_LE(header->height); + int depth = wxINT16_SWAP_ON_LE(header->depth); + int flags = wxINT16_SWAP_ON_LE(header->flags); if ((flags & 1) != colmajor) return MATCH_FALSE; @@ -611,7 +611,7 @@ class DoomJaguarColMajorDataFormat : public DoomJaguarDataFormat { public: DoomJaguarColMajorDataFormat() : DoomJaguarDataFormat(1, "img_doom_jaguar_colmajor"){}; - ~DoomJaguarColMajorDataFormat() final = default; + ~DoomJaguarColMajorDataFormat() override = default; }; class DoomJagTexDataFormat : public EntryDataFormat @@ -694,8 +694,8 @@ class DoomPSXDataFormat : public EntryDataFormat if (mc.size() < sizeof(gfx::PSXPicHeader)) return MATCH_FALSE; - const uint8_t* data = mc.data(); - const gfx::PSXPicHeader* header = (const gfx::PSXPicHeader*)data; + const uint8_t* data = mc.data(); + auto header = reinterpret_cast(data); // Check header values are 'sane' if (!(header->height > 0 && header->height < 4096 && header->width > 0 && header->width < 4096 @@ -725,8 +725,8 @@ class IMGZDataFormat : public EntryDataFormat if (size < sizeof(gfx::IMGZHeader)) return MATCH_FALSE; - const uint8_t* data = mc.data(); - const gfx::IMGZHeader* header = (const gfx::IMGZHeader*)data; + const uint8_t* data = mc.data(); + auto header = reinterpret_cast(data); // Check signature if (header->magic[0] != 'I' || header->magic[1] != 'M' || header->magic[2] != 'G' || header->magic[3] != 'Z') @@ -737,8 +737,8 @@ class IMGZDataFormat : public EntryDataFormat return MATCH_FALSE; // The reserved values should all be null - for (uint8_t i = 0; i < 11; ++i) - if (header->reserved[i]) + for (unsigned char i : header->reserved) + if (i) return MATCH_FALSE; // This is probably a genuine IMGZ @@ -932,8 +932,8 @@ class ShadowCasterGfxFormat : public EntryDataFormat if (mc.size() < sizeof(gfx::PatchHeader)) return MATCH_FALSE; - const uint8_t* data = mc.data(); - const gfx::PatchHeader* header = (const gfx::PatchHeader*)data; + const uint8_t* data = mc.data(); + auto header = reinterpret_cast(data); // Check header values are 'sane' if (!(header->height > 0 && header->height < 4096 && header->width > 0 && header->width < 4096 @@ -1194,7 +1194,7 @@ class RottGfxDataFormat : public EntryDataFormat // Check size if (mc.size() > sizeof(gfx::ROTTPatchHeader)) { - const gfx::ROTTPatchHeader* header = (const gfx::ROTTPatchHeader*)data; + auto header = reinterpret_cast(data); // Check header values are 'sane' if (header->height > 0 && header->height < 4096 && header->width > 0 && header->width < 4096 @@ -1244,7 +1244,7 @@ class RottTransGfxDataFormat : public EntryDataFormat // Check size if (mc.size() > sizeof(gfx::ROTTPatchHeader)) { - const gfx::ROTTPatchHeader* header = (const gfx::ROTTPatchHeader*)data; + auto header = reinterpret_cast(data); // Check header values are 'sane' if (header->height > 0 && header->height < 4096 && header->width > 0 && header->width < 4096 @@ -1319,8 +1319,8 @@ class RottRawDataFormat : public EntryDataFormat if (mc.size() < sizeof(gfx::PatchHeader)) return MATCH_FALSE; - const uint8_t* data = mc.data(); - const gfx::PatchHeader* header = (const gfx::PatchHeader*)data; + const uint8_t* data = mc.data(); + auto header = reinterpret_cast(data); // Check header values are 'sane' if (!(header->height > 0 && header->height < 4096 && header->width > 0 && header->width < 4096 @@ -1520,7 +1520,7 @@ class Font0DataFormat : public EntryDataFormat if (mc.size() <= 0x302) return MATCH_FALSE; - const uint16_t* gfx_data = (const uint16_t*)mc.data(); + auto gfx_data = reinterpret_cast(mc.data()); size_t height = wxINT16_SWAP_ON_BE(gfx_data[0]); @@ -1609,7 +1609,7 @@ class FontWolfDataFormat : public EntryDataFormat if (mc.size() <= 0x302) return MATCH_FALSE; - const uint16_t* gfx_data = (const uint16_t*)mc.data(); + auto gfx_data = reinterpret_cast(mc.data()); size_t height = wxINT16_SWAP_ON_BE(gfx_data[0]); diff --git a/src/Archive/EntryType/DataFormats/LumpFormats.h b/src/Archive/EntryType/DataFormats/LumpFormats.h index ee2ec7a11..a89d08369 100644 --- a/src/Archive/EntryType/DataFormats/LumpFormats.h +++ b/src/Archive/EntryType/DataFormats/LumpFormats.h @@ -15,7 +15,7 @@ class TextureXDataFormat : public EntryDataFormat // Not the best test in the world. But a text-based texture lump ought // to fail it every time; as it would be interpreted as too high a number. uint32_t ntex = mc.readL32(0); - if ((int32_t)ntex < 0) + if (static_cast(ntex) < 0) return MATCH_FALSE; if (mc.size() < (ntex * 24)) return MATCH_FALSE; @@ -33,7 +33,7 @@ class PNamesDataFormat : public EntryDataFormat { // It's a pretty simple format alright uint32_t number = mc.readL32(0); - if ((int32_t)number < 0) + if (static_cast(number) < 0) return MATCH_FALSE; if (mc.size() != (4 + number * 8)) return MATCH_FALSE; diff --git a/src/Archive/EntryType/EntryDataFormat.cpp b/src/Archive/EntryType/EntryDataFormat.cpp index 1f747596b..66440ecb5 100644 --- a/src/Archive/EntryType/EntryDataFormat.cpp +++ b/src/Archive/EntryType/EntryDataFormat.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -32,7 +32,6 @@ #include "Main.h" #include "EntryDataFormat.h" #include "Archive/Formats/All.h" -#include "MainEditor/BinaryControlLump.h" #include "Utility/Parser.h" #include "Utility/StringUtils.h" @@ -184,6 +183,9 @@ class AnyDataFormat : public EntryDataFormat int isThisFormat(const MemChunk& mc) override { return MATCH_FALSE; } }; +// Required for below #includes +#include "MainEditor/BinaryControlLump.h" + // Format enumeration moved to separate files #include "DataFormats/ArchiveFormats.h" #include "DataFormats/AudioFormats.h" @@ -192,6 +194,7 @@ class AnyDataFormat : public EntryDataFormat #include "DataFormats/MiscFormats.h" #include "DataFormats/ModelFormats.h" + // ----------------------------------------------------------------------------- // Initialises all built-in data formats (this is currently all formats, as // externally defined formats are not implemented yet) diff --git a/src/Archive/EntryType/EntryType.cpp b/src/Archive/EntryType/EntryType.cpp index 5122454b0..f86a64c6e 100644 --- a/src/Archive/EntryType/EntryType.cpp +++ b/src/Archive/EntryType/EntryType.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -223,14 +223,15 @@ int EntryType::isThisType(ArchiveEntry& entry) const // If both names and extensions are defined, and the type only needs one // of the two, not both, take it into account. - bool extorname = false; - bool matchedname = false; + bool extorname = false; if (match_ext_or_name_ && !match_name_.empty() && !match_extension_.empty()) extorname = true; // Entry name related stuff if (!match_name_.empty() || !match_extension_.empty()) { + bool matchedname = false; + // Get entry name (lowercase), find extension separator const string_view fn = entry.upperName(); const size_t ext_sep = fn.find_last_of('.'); diff --git a/src/Archive/Formats/ADatArchive.cpp b/src/Archive/Formats/ADatArchive.cpp index e997c52c2..f6cecb330 100644 --- a/src/Archive/Formats/ADatArchive.cpp +++ b/src/Archive/Formats/ADatArchive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -346,7 +346,7 @@ bool ADatArchive::isADatArchive(const MemChunk& mc) return false; // Check directory is sane - if (dir_offset < 16 || (unsigned)(dir_offset + dir_size) > mc.size()) + if (dir_offset < 16 || static_cast(dir_offset + dir_size) > mc.size()) return false; // That'll do diff --git a/src/Archive/Formats/BSPArchive.cpp b/src/Archive/Formats/BSPArchive.cpp index 4f7af42b1..fa4f8ed8e 100644 --- a/src/Archive/Formats/BSPArchive.cpp +++ b/src/Archive/Formats/BSPArchive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net diff --git a/src/Archive/Formats/BZip2Archive.cpp b/src/Archive/Formats/BZip2Archive.cpp index cc0b702df..f413e0d7b 100644 --- a/src/Archive/Formats/BZip2Archive.cpp +++ b/src/Archive/Formats/BZip2Archive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net diff --git a/src/Archive/Formats/ChasmBinArchive.cpp b/src/Archive/Formats/ChasmBinArchive.cpp index 5d8a80146..ce292c4fa 100644 --- a/src/Archive/Formats/ChasmBinArchive.cpp +++ b/src/Archive/Formats/ChasmBinArchive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -195,8 +195,7 @@ bool ChasmBinArchive::write(MemChunk& mc) if (num_entries > MAX_ENTRY_COUNT) { - log::error( - "ChasmBinArchive::write: Bin archive can contain no more than {} entries", (unsigned)MAX_ENTRY_COUNT); + log::error("ChasmBinArchive::write: Bin archive can contain no more than {} entries", MAX_ENTRY_COUNT); global::error = "Maximum number of entries exceeded for Chasm: The Rift bin archive"; return false; } diff --git a/src/Archive/Formats/DatArchive.cpp b/src/Archive/Formats/DatArchive.cpp index 678be8498..d5b2ee990 100644 --- a/src/Archive/Formats/DatArchive.cpp +++ b/src/Archive/Formats/DatArchive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -132,7 +132,7 @@ bool DatArchive::open(const MemChunk& mc) { ++len; } - myname.assign((const char*)mcdata + start, len); + myname.assign(reinterpret_cast(mcdata) + start, len); lastname = myname; namecount = 0; } @@ -199,15 +199,15 @@ string DatArchive::detectNamespace(ArchiveEntry* entry) string DatArchive::detectNamespace(unsigned index, ArchiveDir* dir) { // Textures - if (index > (unsigned)walls_[0] && index < (unsigned)walls_[1]) + if (index > static_cast(walls_[0]) && index < static_cast(walls_[1])) return "textures"; // Flats - if (index > (unsigned)flats_[0] && index < (unsigned)flats_[1]) + if (index > static_cast(flats_[0]) && index < static_cast(flats_[1])) return "flats"; // Sprites - if (index > (unsigned)sprites_[0] && index < (unsigned)sprites_[1]) + if (index > static_cast(sprites_[0]) && index < static_cast(sprites_[1])) return "sprites"; return "global"; @@ -346,9 +346,7 @@ bool DatArchive::renameEntry(ArchiveEntry* entry, string_view name, bool force) return false; // Do default rename - bool ok = Archive::renameEntry(entry, name, force); - - if (ok) + if (Archive::renameEntry(entry, name, force)) { // Update namespaces if necessary if (isNamespaceEntry(entry)) @@ -370,9 +368,7 @@ bool DatArchive::swapEntries(ArchiveEntry* entry1, ArchiveEntry* entry2) return false; // Do default swap (force root dir) - bool ok = Archive::swapEntries(entry1, entry2); - - if (ok) + if (Archive::swapEntries(entry1, entry2)) { // Update namespaces if needed if (isNamespaceEntry(entry1) || isNamespaceEntry(entry2)) diff --git a/src/Archive/Formats/DatArchive.h b/src/Archive/Formats/DatArchive.h index ee94378fb..070f4f817 100644 --- a/src/Archive/Formats/DatArchive.h +++ b/src/Archive/Formats/DatArchive.h @@ -44,8 +44,8 @@ class DatArchive : public TreelessArchive static bool isDatArchive(const string& filename); private: - int sprites_[2]; - int flats_[2]; - int walls_[2]; + int sprites_[2] = {}; + int flats_[2] = {}; + int walls_[2] = {}; }; } // namespace slade diff --git a/src/Archive/Formats/DirArchive.cpp b/src/Archive/Formats/DirArchive.cpp index 853ad8b51..433683e97 100644 --- a/src/Archive/Formats/DirArchive.cpp +++ b/src/Archive/Formats/DirArchive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -451,7 +451,7 @@ bool DirArchive::renameEntry(ArchiveEntry* entry, string_view name, bool force) // Returns the mapdesc_t information about the map at [entry], if [entry] is // actually a valid map (ie. a wad archive in the maps folder) // ----------------------------------------------------------------------------- -Archive::MapDesc DirArchive::mapDesc(ArchiveEntry* entry) +MapDesc DirArchive::mapDesc(ArchiveEntry* entry) { MapDesc map; @@ -480,7 +480,7 @@ Archive::MapDesc DirArchive::mapDesc(ArchiveEntry* entry) // Detects all the maps in the archive and returns a vector of information about // them. // ----------------------------------------------------------------------------- -vector DirArchive::detectMaps() +vector DirArchive::detectMaps() { vector ret; @@ -649,9 +649,8 @@ void DirArchive::updateChangedEntries(vector& changes) // Deleted Entries else if (change.action == DirEntryChange::Action::DeletedFile) { - const auto entry = entryAtPath(change.entry_path); // If the parent directory was already removed, this entry no longer exists - if (entry) + if (const auto entry = entryAtPath(change.entry_path)) removeEntry(entry); } diff --git a/src/Archive/Formats/DirArchive.h b/src/Archive/Formats/DirArchive.h index 3319d3508..b902219e7 100644 --- a/src/Archive/Formats/DirArchive.h +++ b/src/Archive/Formats/DirArchive.h @@ -22,7 +22,10 @@ struct DirEntryChange time_t mtime; DirEntryChange(Action action = Action::Updated, string_view file = "", string_view entry = "", time_t mtime = 0) : - entry_path{ entry }, file_path{ file }, action{ action }, mtime{ mtime } + entry_path{ entry }, + file_path{ file }, + action{ action }, + mtime{ mtime } { } }; @@ -91,7 +94,9 @@ class DirArchiveTraverser : public wxDirTraverser { public: DirArchiveTraverser(vector& pathlist, vector& dirlist, bool ignore_hidden) : - paths_{ pathlist }, dirs_{ dirlist }, ignore_hidden_{ ignore_hidden } + paths_{ pathlist }, + dirs_{ dirlist }, + ignore_hidden_{ ignore_hidden } { } ~DirArchiveTraverser() override = default; diff --git a/src/Archive/Formats/DiskArchive.cpp b/src/Archive/Formats/DiskArchive.cpp index 0688dc60b..b1a27747b 100644 --- a/src/Archive/Formats/DiskArchive.cpp +++ b/src/Archive/Formats/DiskArchive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net diff --git a/src/Archive/Formats/GZipArchive.cpp b/src/Archive/Formats/GZipArchive.cpp index c540b0a0f..63e14e0e3 100644 --- a/src/Archive/Formats/GZipArchive.cpp +++ b/src/Archive/Formats/GZipArchive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net diff --git a/src/Archive/Formats/GobArchive.cpp b/src/Archive/Formats/GobArchive.cpp index 7d86c21f4..696f98e17 100644 --- a/src/Archive/Formats/GobArchive.cpp +++ b/src/Archive/Formats/GobArchive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -278,7 +278,7 @@ bool GobArchive::isGobArchive(const string& filename) dir_offset = wxINT32_SWAP_ON_BE(dir_offset); // Check size - if ((unsigned)file.Length() < (dir_offset + 4)) + if (static_cast(file.Length()) < (dir_offset + 4)) return false; // Get number of lumps @@ -289,7 +289,7 @@ bool GobArchive::isGobArchive(const string& filename) // Compute directory size uint32_t dir_size = (num_lumps * 21) + 4; - if ((unsigned)file.Length() < (dir_offset + dir_size)) + if (static_cast(file.Length()) < (dir_offset + dir_size)) return false; // If it's passed to here it's probably a gob file diff --git a/src/Archive/Formats/GrpArchive.cpp b/src/Archive/Formats/GrpArchive.cpp index 20ad06ce8..8999398e7 100644 --- a/src/Archive/Formats/GrpArchive.cpp +++ b/src/Archive/Formats/GrpArchive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -317,7 +317,7 @@ CONSOLE_COMMAND(lookupdat, 0, false) uint8_t numlookup = 0; uint8_t dummy = 0; mc.read(&numlookup, 1); - if (mc.size() < (uint32_t)((numlookup * 256) + (5 * 768) + 1)) + if (mc.size() < static_cast((numlookup * 256) + (5 * 768) + 1)) return; auto nentry = entry->parent()->addNewEntry("COLORMAP.DAT", index + 1, entry->parentDir()); diff --git a/src/Archive/Formats/HogArchive.cpp b/src/Archive/Formats/HogArchive.cpp index 0ad7c1935..ee7d9307a 100644 --- a/src/Archive/Formats/HogArchive.cpp +++ b/src/Archive/Formats/HogArchive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net diff --git a/src/Archive/Formats/LfdArchive.cpp b/src/Archive/Formats/LfdArchive.cpp index 59e7276df..826da9f61 100644 --- a/src/Archive/Formats/LfdArchive.cpp +++ b/src/Archive/Formats/LfdArchive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -336,7 +336,7 @@ bool LfdArchive::isLfdArchive(const string& filename) len1 = wxINT32_SWAP_ON_BE(len1); // Check size - if ((unsigned)file.Length() < (dir_offset + 16 + len1)) + if (static_cast(file.Length()) < (dir_offset + 16 + len1)) return false; // Compare diff --git a/src/Archive/Formats/LibArchive.cpp b/src/Archive/Formats/LibArchive.cpp index e7b34c78c..97c1fee4e 100644 --- a/src/Archive/Formats/LibArchive.cpp +++ b/src/Archive/Formats/LibArchive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net diff --git a/src/Archive/Formats/PakArchive.cpp b/src/Archive/Formats/PakArchive.cpp index cc8ddbef3..72a4c4769 100644 --- a/src/Archive/Formats/PakArchive.cpp +++ b/src/Archive/Formats/PakArchive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -95,7 +95,7 @@ bool PakArchive::open(const MemChunk& mc) size = wxINT32_SWAP_ON_BE(size); // Check offset+size - if ((unsigned)(offset + size) > mc.size()) + if (static_cast(offset + size) > mc.size()) { log::error("PakArchive::open: Pak archive is invalid or corrupt (entry goes past end of file)"); global::error = "Archive is invalid and/or corrupt"; @@ -270,7 +270,7 @@ bool PakArchive::isPakArchive(const MemChunk& mc) return false; // Check directory is sane - if (dir_offset < 12 || (unsigned)(dir_offset + dir_size) > mc.size()) + if (dir_offset < 12 || static_cast(dir_offset + dir_size) > mc.size()) return false; // That'll do diff --git a/src/Archive/Formats/PodArchive.cpp b/src/Archive/Formats/PodArchive.cpp index c6d6fcd21..1f1f7f192 100644 --- a/src/Archive/Formats/PodArchive.cpp +++ b/src/Archive/Formats/PodArchive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net diff --git a/src/Archive/Formats/ResArchive.cpp b/src/Archive/Formats/ResArchive.cpp index c819aceca..501a9f63c 100644 --- a/src/Archive/Formats/ResArchive.cpp +++ b/src/Archive/Formats/ResArchive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -126,8 +126,7 @@ bool ResArchive::readDirectory(const MemChunk& mc, size_t dir_offset, size_t num size_t d_o, n_l; if (isResArchive(nlump->data(), d_o, n_l)) { - auto ndir = createDir(name, parent); - if (ndir) + if (auto ndir = createDir(name, parent)) { ui::setSplashProgressMessage(fmt::format("Reading res archive data: {} directory", name)); // Save offset to restore it once the recursion is done diff --git a/src/Archive/Formats/ResArchive.h b/src/Archive/Formats/ResArchive.h index cbe6417c8..b310e6ecb 100644 --- a/src/Archive/Formats/ResArchive.h +++ b/src/Archive/Formats/ResArchive.h @@ -20,7 +20,7 @@ class ResArchive : public Archive // Static functions static bool isResArchive(const MemChunk& mc); - static bool isResArchive(const MemChunk& mc, size_t& d_o, size_t& n_l); + static bool isResArchive(const MemChunk& mc, size_t& dir_offset, size_t& num_lumps); static bool isResArchive(const string& filename); private: diff --git a/src/Archive/Formats/RffArchive.cpp b/src/Archive/Formats/RffArchive.cpp index f7a994c2e..7151425f0 100644 --- a/src/Archive/Formats/RffArchive.cpp +++ b/src/Archive/Formats/RffArchive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -100,10 +100,10 @@ struct RFFLump // ----------------------------------------------------------------------------- void bloodCrypt(void* data, int key, int len) { - int p = (uint8_t)key, i; + int p = static_cast(key), i; for (i = 0; i < len; ++i) - ((uint8_t*)data)[i] ^= (unsigned char)(p + (i >> 1)); + static_cast(data)[i] ^= static_cast(p + (i >> 1)); } } // namespace diff --git a/src/Archive/Formats/SiNArchive.cpp b/src/Archive/Formats/SiNArchive.cpp index bc47acf56..310b47f00 100644 --- a/src/Archive/Formats/SiNArchive.cpp +++ b/src/Archive/Formats/SiNArchive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -96,7 +96,7 @@ bool SiNArchive::open(const MemChunk& mc) size = wxINT32_SWAP_ON_BE(size); // Check offset+size - if ((unsigned)(offset + size) > mc.size()) + if (static_cast(offset + size) > mc.size()) { log::error("SiNArchive::open: SiN archive is invalid or corrupt (entry goes past end of file)"); global::error = "Archive is invalid and/or corrupt"; @@ -270,7 +270,7 @@ bool SiNArchive::isSiNArchive(const MemChunk& mc) return false; // Check directory is sane - if (dir_offset < 12 || (unsigned)(dir_offset + dir_size) > mc.size()) + if (dir_offset < 12 || static_cast(dir_offset + dir_size) > mc.size()) return false; // That'll do diff --git a/src/Archive/Formats/TarArchive.cpp b/src/Archive/Formats/TarArchive.cpp index 8138c19a2..009d9538f 100644 --- a/src/Archive/Formats/TarArchive.cpp +++ b/src/Archive/Formats/TarArchive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -112,7 +112,7 @@ int tarSum(const char* field, int size) bool tarWriteOctal(size_t sum, char* field, int size) { // Check for overflow, which are possible on 8-byte fields - if (size < 11 && sum >= (unsigned)(1 << (3 * size))) + if (size < 11 && sum >= static_cast(1 << (3 * size))) { char errormessage[9] = "WOLFREVO"; for (int a = 1; a <= (size + 1); ++a) @@ -144,8 +144,8 @@ bool tarChecksum(const TarHeader* header) // to address it either as a tar header, as a block of signed char, // or as a block of unsigned char. int8_t* sigblock = new int8_t[512]; - uint8_t* unsblock = (uint8_t*)sigblock; - TarHeader* block = (TarHeader*)sigblock; + uint8_t* unsblock = reinterpret_cast(sigblock); + TarHeader* block = reinterpret_cast(sigblock); memcpy(sigblock, header, 512); int32_t checksum = 0; // Blank out checksum @@ -189,7 +189,7 @@ bool tarChecksum(const TarHeader* header) size_t tarMakeChecksum(TarHeader* header) { size_t checksum = 0; - uint8_t* h = (uint8_t*)header; + uint8_t* h = reinterpret_cast(header); for (int a = 0; a < 512; ++a) checksum += h[a]; return checksum; @@ -315,7 +315,7 @@ bool TarArchive::open(const MemChunk& mc) // Find size size_t size = tarSum(header.size, 12); - if ((int)header.typeflag == AREGTYPE || (int)header.typeflag == REGTYPE) + if (static_cast(header.typeflag) == AREGTYPE || static_cast(header.typeflag) == REGTYPE) { // Create directory if needed auto dir = createDir(strutil::Path::pathOf(name)); @@ -334,7 +334,7 @@ bool TarArchive::open(const MemChunk& mc) // Add to directory dir->addEntry(entry); } - else if ((int)header.typeflag == DIRTYPE) + else if (static_cast(header.typeflag) == DIRTYPE) { // Directory createDir(name); diff --git a/src/Archive/Formats/Wad2Archive.cpp b/src/Archive/Formats/Wad2Archive.cpp index cd509d979..f6be67d65 100644 --- a/src/Archive/Formats/Wad2Archive.cpp +++ b/src/Archive/Formats/Wad2Archive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -99,7 +99,7 @@ bool Wad2Archive::open(const MemChunk& mc) // If the lump data goes past the end of the file, // the wadfile is invalid - if ((unsigned)(info.offset + info.dsize) > mc.size()) + if (static_cast(info.offset + info.dsize) > mc.size()) { log::error("Wad2Archive::open: Wad2 archive is invalid or corrupt"); global::error = "Archive is invalid and/or corrupt"; @@ -249,7 +249,7 @@ bool Wad2Archive::isWad2Archive(const MemChunk& mc) dir_offset = wxINT32_SWAP_ON_BE(dir_offset); // Check directory offset is decent - if ((unsigned)(dir_offset + (num_lumps * 32)) > mc.size() || dir_offset < 12) + if (static_cast(dir_offset + (num_lumps * 32)) > mc.size() || dir_offset < 12) return false; // If it's passed to here it's probably a wad2 file diff --git a/src/Archive/Formats/WadArchive.cpp b/src/Archive/Formats/WadArchive.cpp index d482bab12..baae886bf 100644 --- a/src/Archive/Formats/WadArchive.cpp +++ b/src/Archive/Formats/WadArchive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -31,7 +31,6 @@ // ----------------------------------------------------------------------------- #include "Main.h" #include "WadArchive.h" -#include "General/Misc.h" #include "General/UI.h" #include "Utility/StringUtils.h" #include "Utility/Tokenizer.h" @@ -421,7 +420,7 @@ bool WadArchive::open(const MemChunk& mc) if (jaguarencrypt) { nlump->setEncryption(ArchiveEntry::Encryption::Jaguar); - nlump->exProp("FullSize") = (int)size; + nlump->exProp("FullSize") = static_cast(size); } // Read entry data if it isn't zero-sized @@ -788,7 +787,7 @@ bool WadArchive::moveEntry(ArchiveEntry* entry, unsigned position, ArchiveDir* d // If [maphead] is not really a map header entry, an invalid MapDesc will be // returned (MapDesc::head == nullptr) // ----------------------------------------------------------------------------- -Archive::MapDesc WadArchive::mapDesc(ArchiveEntry* maphead) +MapDesc WadArchive::mapDesc(ArchiveEntry* maphead) { MapDesc map; @@ -920,8 +919,7 @@ Archive::MapDesc WadArchive::mapDesc(ArchiveEntry* maphead) { Archive::SearchOptions opt; opt.match_name = "playpals"; - auto match = findFirst(opt); - if (match) + if (findFirst(opt)) map.format = MapFormat::Doom32X; else map.format = MapFormat::Doom; @@ -933,7 +931,7 @@ Archive::MapDesc WadArchive::mapDesc(ArchiveEntry* maphead) // ----------------------------------------------------------------------------- // Searches for any maps in the wad and adds them to the map list // ----------------------------------------------------------------------------- -vector WadArchive::detectMaps() +vector WadArchive::detectMaps() { vector maps; @@ -946,8 +944,7 @@ vector WadArchive::detectMaps() Archive::SearchOptions opt; opt.match_name = "playpals"; - auto match = findFirst(opt); - if (match) + if (findFirst(opt)) playpals = true; while (entry) @@ -1042,7 +1039,7 @@ vector WadArchive::detectMaps() md.name = header_entry->name(); // Map title md.end = lastentryismapentry ? // End lump entry : - rootDir()->sharedEntryAt(--index); + rootDir()->sharedEntryAt(--index); // If BEHAVIOR lump exists, it's a hexen format map if (existing_map_lumps[LUMP_BEHAVIOR]) @@ -1170,8 +1167,7 @@ void WadArchive::detectIncludes() if (i == 5) // skip ')' tz.adv(); opt.match_name = name; - auto match = findFirst(opt); - if (match) + if (auto match = findFirst(opt)) match->setType(EntryType::fromId(entrytypes[i])); tz.adv(); } diff --git a/src/Archive/Formats/WadArchive.h b/src/Archive/Formats/WadArchive.h index ebc28b49f..466a931c2 100644 --- a/src/Archive/Formats/WadArchive.h +++ b/src/Archive/Formats/WadArchive.h @@ -57,7 +57,7 @@ class WadArchive : public TreelessArchive static bool isWadArchive(const MemChunk& mc); static bool isWadArchive(const string& filename); - static bool exportEntriesAsWad(string_view filename, vector entries) + static bool exportEntriesAsWad(string_view filename, const vector& entries) { WadArchive wad; diff --git a/src/Archive/Formats/WadJArchive.cpp b/src/Archive/Formats/WadJArchive.cpp index 48ed0b8d7..45aaf8b51 100644 --- a/src/Archive/Formats/WadJArchive.cpp +++ b/src/Archive/Formats/WadJArchive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -180,7 +180,8 @@ bool WadJArchive::open(const MemChunk& mc) mc.exportMemChunk(edata, offset, size); if (nlump->encryption() != ArchiveEntry::Encryption::None) { - if (nlump->exProps().contains("FullSize") && (unsigned)(nlump->exProp("FullSize")) > size) + if (nlump->exProps().contains("FullSize") + && static_cast(nlump->exProp("FullSize")) > size) edata.reSize((nlump->exProp("FullSize")), true); if (!jaguarDecode(edata)) log::warning( @@ -378,7 +379,7 @@ bool WadJArchive::isWadJArchive(const string& filename) // ----------------------------------------------------------------------------- bool WadJArchive::jaguarDecode(MemChunk& mc) { - static const int LENSHIFT = 4; /* this must be log2(LOOKAHEAD_SIZE) */ + static constexpr int LENSHIFT = 4; /* this must be log2(LOOKAHEAD_SIZE) */ bool okay = false; uint8_t getidbyte = 0; diff --git a/src/Archive/Formats/WolfArchive.cpp b/src/Archive/Formats/WolfArchive.cpp index 72710097e..012859b57 100644 --- a/src/Archive/Formats/WolfArchive.cpp +++ b/src/Archive/Formats/WolfArchive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -129,21 +129,21 @@ size_t WolfConstant(int name, size_t numlumps) case 414: game = 4; break; // GFXE_WL6: Just a mess of chunks without anything usable case 556: game = 0; break; // GFXV_WL1 case 558: game = 1; break; // GFXE_WL1 - default: return 0; + default: return 0; } switch (name) // VW1, EW1, ?W1, VW6, EW6, SDM, SOD { - case STARTPICS: return7(game, 3, 3, 3, 3, 0, 3, 3) break; - case STARTPICM: return7(game, 139, 142, 147, 135, 0, 128, 150) break; - case NUMTILE8: return7(game, 72, 72, 72, 72, 0, 72, 72) break; - case STARTPAL: return7(game, 0, 0, 0, 0, 0, 131, 153) break; - case ENDPAL: return7(game, 0, 0, 0, 0, 0, 131, 163) break; - case TITLE1PIC: return7(game, 0, 0, 0, 0, 0, 74, 79) break; - case TITLE2PIC: return7(game, 0, 0, 0, 0, 0, 75, 80) break; + case STARTPICS: return7(game, 3, 3, 3, 3, 0, 3, 3) break; + case STARTPICM: return7(game, 139, 142, 147, 135, 0, 128, 150) break; + case NUMTILE8: return7(game, 72, 72, 72, 72, 0, 72, 72) break; + case STARTPAL: return7(game, 0, 0, 0, 0, 0, 131, 153) break; + case ENDPAL: return7(game, 0, 0, 0, 0, 0, 131, 163) break; + case TITLE1PIC: return7(game, 0, 0, 0, 0, 0, 74, 79) break; + case TITLE2PIC: return7(game, 0, 0, 0, 0, 0, 75, 80) break; case ENDSCREEN1PIC: return7(game, 0, 0, 0, 0, 0, 0, 81) break; case ENDSCREEN9PIC: return7(game, 0, 0, 0, 0, 0, 0, 89) break; - case IDGUYS1PIC: return7(game, 0, 0, 0, 0, 0, 0, 93) break; - case IDGUYS2PIC: return7(game, 0, 0, 0, 0, 0, 0, 94) break; + case IDGUYS1PIC: return7(game, 0, 0, 0, 0, 0, 0, 93) break; + case IDGUYS2PIC: return7(game, 0, 0, 0, 0, 0, 0, 94) break; } return 0; } @@ -204,10 +204,10 @@ void addWolfPicHeader(ArchiveEntry* entry, uint16_t width, uint16_t height) uint32_t newsize = mc.size() + 4; uint8_t* newdata = new uint8_t[newsize]; - newdata[0] = (uint8_t)(width & 0xFF); - newdata[1] = (uint8_t)(width >> 8); - newdata[2] = (uint8_t)(height & 0xFF); - newdata[3] = (uint8_t)(height >> 8); + newdata[0] = static_cast(width & 0xFF); + newdata[1] = static_cast(width >> 8); + newdata[2] = static_cast(height & 0xFF); + newdata[3] = static_cast(height >> 8); for (size_t i = 0; 4 + i < newsize; ++i) { @@ -479,7 +479,7 @@ bool WolfArchive::open(const MemChunk& mc) // If the lump data goes before the end of the directory, // the data file is invalid - if (pages[d].offset != 0 && pages[d].offset < (unsigned)((num_lumps + 1) * 6)) + if (pages[d].offset != 0 && pages[d].offset < static_cast((num_lumps + 1) * 6)) { log::error("WolfArchive::open: Wolf archive is invalid or corrupt"); global::error = "Archive is invalid and/or corrupt "; diff --git a/src/Archive/Formats/ZipArchive.cpp b/src/Archive/Formats/ZipArchive.cpp index da1378aba..b7a13b205 100644 --- a/src/Archive/Formats/ZipArchive.cpp +++ b/src/Archive/Formats/ZipArchive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -462,7 +462,7 @@ shared_ptr ZipArchive::addEntry(shared_ptr entry, st // Returns the mapdesc_t information about the map at [entry], if [entry] is // actually a valid map (ie. a wad archive in the maps folder) // ----------------------------------------------------------------------------- -Archive::MapDesc ZipArchive::mapDesc(ArchiveEntry* maphead) +MapDesc ZipArchive::mapDesc(ArchiveEntry* maphead) { MapDesc map; @@ -491,7 +491,7 @@ Archive::MapDesc ZipArchive::mapDesc(ArchiveEntry* maphead) // Detects all the maps in the archive and returns a vector of information about // them. // ----------------------------------------------------------------------------- -vector ZipArchive::detectMaps() +vector ZipArchive::detectMaps() { vector ret; @@ -602,8 +602,7 @@ ArchiveEntry* ZipArchive::findLast(SearchOptions& options) vector ZipArchive::findAll(SearchOptions& options) { // Init search variables - auto dir = rootDir().get(); - vector ret; + auto dir = rootDir().get(); // Check for search directory (overrides namespace) if (options.dir) @@ -617,7 +616,7 @@ vector ZipArchive::findAll(SearchOptions& options) // If the requested namespace doesn't exist, return nothing if (!dir) - return ret; + return {}; else options.search_subdirs = true; // Namespace search always includes namespace subdirs } diff --git a/src/Archive/MapDesc.h b/src/Archive/MapDesc.h new file mode 100644 index 000000000..2fa1eb13b --- /dev/null +++ b/src/Archive/MapDesc.h @@ -0,0 +1,29 @@ +#pragma once + +#include "General/Defs.h" + +namespace slade +{ +class Archive; +class ArchiveEntry; + +struct MapDesc +{ + string name; + weak_ptr head; + weak_ptr end; // The last entry of the map data + MapFormat format; // See MapTypes enum + bool archive; // True if head is an archive (for maps in zips) + + vector unk; // Unknown map lumps (must be preserved for UDMF compliance) + + MapDesc() + { + archive = false; + format = MapFormat::Unknown; + } + + vector entries(const Archive& parent, bool include_head = false) const; + void updateMapFormatHints() const; +}; +} // namespace slade diff --git a/src/Audio/AudioTags.cpp b/src/Audio/AudioTags.cpp index cfd28aa5d..8343d90e4 100644 --- a/src/Audio/AudioTags.cpp +++ b/src/Audio/AudioTags.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -1283,13 +1283,13 @@ wxString audio::getSunInfo(const MemChunk& mc) wxString format = "Format: "; switch (codec) { - case 1: format += wxString::FromUTF8("\xCE\xBC-Law"); break; + case 1: format += wxString::FromUTF8("\xCE\xBC-Law"); break; case 2: case 3: case 4: - case 5: format += wxString::Format("PCM (signed)"); break; + case 5: format += wxString::Format("PCM (signed)"); break; case 6: - case 7: format += wxString::Format("PCM (float)"); break; + case 7: format += wxString::Format("PCM (float)"); break; case 27: format += wxString::Format("a-Law"); break; default: format += wxString::Format("Unknown (%lu)", codec); break; } @@ -1389,15 +1389,15 @@ wxString audio::getVocInfo(const MemChunk& mc) wxString format = "Format: "; switch (codec) { - case 0: format += wxString::Format("PCM (unsigned)"); break; - case 1: format += wxString::Format("4-to-8 ADPCM"); break; - case 2: format += wxString::Format("3-to-8 ADPCM"); break; - case 3: format += wxString::Format("2-to-8 ADPCM"); break; - case 4: format += wxString::Format("PCM (signed)"); break; - case 6: format += wxString::Format("a-Law"); break; - case 7: format += wxString::FromUTF8("\xCE\xBC-Law"); break; + case 0: format += wxString::Format("PCM (unsigned)"); break; + case 1: format += wxString::Format("4-to-8 ADPCM"); break; + case 2: format += wxString::Format("3-to-8 ADPCM"); break; + case 3: format += wxString::Format("2-to-8 ADPCM"); break; + case 4: format += wxString::Format("PCM (signed)"); break; + case 6: format += wxString::Format("a-Law"); break; + case 7: format += wxString::FromUTF8("\xCE\xBC-Law"); break; case 0x200: format += wxString::Format("4to-16 ADPCM"); break; - default: format += wxString::Format("Unknown (%u)", codec); break; + default: format += wxString::Format("Unknown (%u)", codec); break; } wxString ret = "Mono"; if (fmtchunk.channels == 2) @@ -1470,11 +1470,11 @@ wxString audio::getWavInfo(const MemChunk& mc) } switch (formnum) { - case 1: format += wxString::Format("PCM"); break; - case 2: format += wxString::Format("Microsoft ADPCM"); break; - case 3: format += wxString::Format("IEEE754"); break; - case 6: format += wxString::Format("ITU G.711 a-Law"); break; - case 7: format += wxString::FromUTF8("ITU G.711 \xCE\xBC-Law"); break; + case 1: format += wxString::Format("PCM"); break; + case 2: format += wxString::Format("Microsoft ADPCM"); break; + case 3: format += wxString::Format("IEEE754"); break; + case 6: format += wxString::Format("ITU G.711 a-Law"); break; + case 7: format += wxString::FromUTF8("ITU G.711 \xCE\xBC-Law"); break; case 17: format += wxString::Format("IMA ADPCM"); break; case 20: format += wxString::Format("ITU G.723 ADPCM"); break; case 49: format += wxString::Format("GSM 6.10"); break; @@ -1677,8 +1677,8 @@ size_t audio::checkForTags(const MemChunk& mc) // Check for ID3 header (ID3v2). Version and revision numbers cannot be FF. // Only the four upper flags are valid. if (mc.size() > s + 14 && mc[s + 0] == 'I' && mc[s + 1] == 'D' && mc[s + 2] == '3' && mc[s + 3] != 0xFF - && mc[s + 4] != 0xFF && ((mc[s + 5] & 0x0F) == 0) && mc[s + 6] < 0x80 && mc[s + 7] < 0x80 - && mc[s + 8] < 0x80 && mc[s + 9] < 0x80) + && mc[s + 4] != 0xFF && ((mc[s + 5] & 0x0F) == 0) && mc[s + 6] < 0x80 && mc[s + 7] < 0x80 + && mc[s + 8] < 0x80 && mc[s + 9] < 0x80) { // Compute size. It is stored as a "synchsafe integer", that is to say, // a big-endian value where the highest bit of each byte is not used. diff --git a/src/Audio/MIDIPlayer.cpp b/src/Audio/MIDIPlayer.cpp index cfe3450b1..202652814 100644 --- a/src/Audio/MIDIPlayer.cpp +++ b/src/Audio/MIDIPlayer.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -34,6 +34,8 @@ #include "MIDIPlayer.h" #include "App.h" #include "Utility/StringUtils.h" +#include +#include using namespace slade; using namespace audio; @@ -114,7 +116,7 @@ class FluidSynthMIDIPlayer : public MIDIPlayer // ------------------------------------------------------------------------- // FluidSynthMIDIPlayer class destructor // ------------------------------------------------------------------------- - virtual ~FluidSynthMIDIPlayer() + ~FluidSynthMIDIPlayer() override { FluidSynthMIDIPlayer::stop(); delete_fluid_audio_driver(fs_adriver_); @@ -230,7 +232,7 @@ class FluidSynthMIDIPlayer : public MIDIPlayer bool play() override { stop(); - timer_.restart(); + timer_->restart(); if (!fs_initialised_) return false; @@ -283,7 +285,7 @@ class FluidSynthMIDIPlayer : public MIDIPlayer int position() override { // We cannot query this information from fluidsynth, so we cheat by querying our own timer - return timer_.getElapsedTime().asMilliseconds(); + return timer_->getElapsedTime().asMilliseconds(); } // ------------------------------------------------------------------------- @@ -376,7 +378,7 @@ class TimidityMIDIPlayer : public MIDIPlayer // ------------------------------------------------------------------------- // TimidityMIDIPlayer class destructor // ------------------------------------------------------------------------- - virtual ~TimidityMIDIPlayer() { stop(); } + ~TimidityMIDIPlayer() override { TimidityMIDIPlayer::stop(); } // ------------------------------------------------------------------------- // Returns true if the MIDIPlayer has a soundfont loaded @@ -421,12 +423,13 @@ class TimidityMIDIPlayer : public MIDIPlayer bool play() override { stop(); - timer_.restart(); + timer_->restart(); // Setup environment and command line to run wxExecuteEnv env; env.cwd = string{ strutil::Path::pathOf(snd_timidity_path) }; - auto commandline = fmt::format("\"{}\" \"{}\" {}", string(snd_timidity_path), file_, string(snd_timidity_options)); + auto commandline = fmt::format( + "\"{}\" \"{}\" {}", string(snd_timidity_path), file_, string(snd_timidity_options)); // Execute program pid_ = wxExecute(commandline, wxEXEC_ASYNC | wxEXEC_HIDE_CONSOLE, nullptr, &env); @@ -486,7 +489,7 @@ class TimidityMIDIPlayer : public MIDIPlayer int position() override { // We cannot query this information from timidity, so we cheat by querying our own timer - return timer_.getElapsedTime().asMilliseconds(); + return timer_->getElapsedTime().asMilliseconds(); } // ------------------------------------------------------------------------- @@ -519,6 +522,16 @@ class TimidityMIDIPlayer : public MIDIPlayer // ----------------------------------------------------------------------------- namespace slade::audio { +// ----------------------------------------------------------------------------- +// MIDIPlayer class constructor +// ----------------------------------------------------------------------------- +MIDIPlayer::MIDIPlayer() : timer_{ new sf::Clock() } {} + +// ----------------------------------------------------------------------------- +// MIDIPlayer class destructor +// ----------------------------------------------------------------------------- +MIDIPlayer::~MIDIPlayer() = default; + // ----------------------------------------------------------------------------- // Returns the current MIDIPlayer instance. // Creates one if there is no current instance, depending on what is configured @@ -590,7 +603,7 @@ int midiLength(const MemChunk& data) pos += 8; size_t chunk_end = pos + chunk_size; uint8_t running_status = 0; - if (chunk_name == (size_t)(('M' << 24) | ('T' << 16) | ('h' << 8) | 'd')) // MThd + if (chunk_name == static_cast(('M' << 24) | ('T' << 16) | ('h' << 8) | 'd')) // MThd { format = data.readB16(pos); num_tracks = data.readB16(pos + 2); @@ -603,7 +616,7 @@ int midiLength(const MemChunk& data) if (time_div == 0) // Not a valid MIDI file return 0; } - else if (chunk_name == (size_t)(('M' << 24) | ('T' << 16) | ('r' << 8) | 'k')) // MTrk + else if (chunk_name == static_cast(('M' << 24) | ('T' << 16) | ('r' << 8) | 'k')) // MTrk { size_t tpos = pos; size_t tracklength = 0; @@ -684,7 +697,7 @@ int midiLength(const MemChunk& data) pos = chunk_end; } // MIDI durations are in microseconds - return (int)(microseconds / 1000); + return static_cast(microseconds / 1000); } // ----------------------------------------------------------------------------- @@ -714,7 +727,7 @@ string midiInfo(const MemChunk& data) pos += 8; size_t chunk_end = pos + chunk_size; uint8_t running_status = 0; - if (chunk_name == (size_t)(('M' << 24) | ('T' << 16) | ('h' << 8) | 'd')) // MThd + if (chunk_name == static_cast(('M' << 24) | ('T' << 16) | ('h' << 8) | 'd')) // MThd { format = data.readB16(pos); num_tracks = data.readB16(pos + 2); @@ -725,7 +738,7 @@ string midiInfo(const MemChunk& data) ret += fmt::format( "MIDI format {} with {} tracks and time division {}\n", format, num_tracks, time_div); } - else if (chunk_name == (size_t)(('M' << 24) | ('T' << 16) | ('r' << 8) | 'k')) // MTrk + else if (chunk_name == static_cast(('M' << 24) | ('T' << 16) | ('r' << 8) | 'k')) // MTrk { if (format == 2) ret += fmt::format("\nTrack {}/{}\n", ++track_counter, num_tracks); @@ -764,17 +777,17 @@ string midiInfo(const MemChunk& data) string tmp; if (evtype > 0 && evtype < 8 && evsize) - tmp.append((const char*)(&data[tpos]), evsize); + tmp.append(reinterpret_cast(&data[tpos]), evsize); switch (evtype) { - case 1: ret += fmt::format("Text: {}\n", tmp); break; - case 2: ret += fmt::format("Copyright: {}\n", tmp); break; - case 3: ret += fmt::format("Title: {}\n", tmp); break; - case 4: ret += fmt::format("Instrument: {}\n", tmp); break; - case 5: ret += fmt::format("Lyrics: {}\n", tmp); break; - case 6: ret += fmt::format("Marker: {}\n", tmp); break; - case 7: ret += fmt::format("Cue point: {}\n", tmp); break; + case 1: ret += fmt::format("Text: {}\n", tmp); break; + case 2: ret += fmt::format("Copyright: {}\n", tmp); break; + case 3: ret += fmt::format("Title: {}\n", tmp); break; + case 4: ret += fmt::format("Instrument: {}\n", tmp); break; + case 5: ret += fmt::format("Lyrics: {}\n", tmp); break; + case 6: ret += fmt::format("Marker: {}\n", tmp); break; + case 7: ret += fmt::format("Cue point: {}\n", tmp); break; default: break; } tpos += evsize; diff --git a/src/Audio/MIDIPlayer.h b/src/Audio/MIDIPlayer.h index 53efb7259..5b3a9d5e2 100644 --- a/src/Audio/MIDIPlayer.h +++ b/src/Audio/MIDIPlayer.h @@ -1,11 +1,17 @@ #pragma once +namespace sf +{ +class Clock; +} + namespace slade::audio { class MIDIPlayer { public: - virtual ~MIDIPlayer() = default; + MIDIPlayer(); + virtual ~MIDIPlayer(); virtual bool isSoundfontLoaded() = 0; virtual bool reloadSoundfont() { return true; } @@ -26,9 +32,9 @@ class MIDIPlayer virtual bool setVolume(int volume) = 0; protected: - string file_; - MemChunk data_; - sf::Clock timer_; + string file_; + MemChunk data_; + unique_ptr timer_; }; class NullMIDIPlayer : public MIDIPlayer diff --git a/src/Audio/ModMusic.cpp b/src/Audio/ModMusic.cpp index 6d54516d8..344fe498b 100644 --- a/src/Audio/ModMusic.cpp +++ b/src/Audio/ModMusic.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -100,7 +100,7 @@ bool ModMusic::loadFromMemory(const uint8_t* data, const uint32_t size) close(); // Load module file - dumb_module_ = dumb_read_any(dumbfile_open_memory((const char*)data, size), 0, 0); + dumb_module_ = dumb_read_any(dumbfile_open_memory(reinterpret_cast(data), size), 0, 0); if (dumb_module_ != nullptr) { initialize(2, 44100); @@ -119,7 +119,7 @@ bool ModMusic::loadFromMemory(const uint8_t* data, const uint32_t size) // ----------------------------------------------------------------------------- sf::Time ModMusic::duration() const { - return sf::seconds(static_cast(duh_get_length(dumb_module_) / 65536.f)); + return sf::seconds(static_cast(duh_get_length(dumb_module_)) / 65536.f); } // ----------------------------------------------------------------------------- diff --git a/src/Audio/ModMusic.h b/src/Audio/ModMusic.h index ca6cf145a..b1ad8b4b1 100644 --- a/src/Audio/ModMusic.h +++ b/src/Audio/ModMusic.h @@ -11,7 +11,7 @@ class ModMusic : public sf::SoundStream { public: ModMusic() = default; - ~ModMusic(); + ~ModMusic() override; bool openFromFile(const string& filename); bool loadFromMemory(const uint8_t* data, const uint32_t size); diff --git a/src/Audio/Mp3Music.cpp b/src/Audio/Mp3Music.cpp index 8febf494f..686a25782 100644 --- a/src/Audio/Mp3Music.cpp +++ b/src/Audio/Mp3Music.cpp @@ -1,11 +1,47 @@ +// ----------------------------------------------------------------------------- +// SLADE - It's a Doom Editor +// Copyright(C) 2008 - 2024 Simon Judd +// +// Email: sirjuddington@gmail.com +// Web: http://slade.mancubus.net +// Filename: Mp3Music.cpp +// Description: Mp3Music class, an SFML sound stream class to play mp3 music +// using libmpg123 +// +// This program is free software; you can redistribute it and/or modify it +// under the terms of the GNU General Public License as published by the Free +// Software Foundation; either version 2 of the License, or (at your option) +// any later version. +// +// This program is distributed in the hope that it will be useful, but WITHOUT +// ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or +// FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for +// more details. +// +// You should have received a copy of the GNU General Public License along with +// this program; if not, write to the Free Software Foundation, Inc., +// 51 Franklin Street, Fifth Floor, Boston, MA 02110 - 1301, USA. +// ----------------------------------------------------------------------------- + + +// ----------------------------------------------------------------------------- +// +// Includes +// +// ----------------------------------------------------------------------------- #include "Main.h" #include "Mp3Music.h" -#include using namespace slade; using namespace audio; + +// ----------------------------------------------------------------------------- +// +// Functions +// +// ----------------------------------------------------------------------------- namespace slade::audio { struct Mp3MemoryData @@ -18,26 +54,25 @@ struct Mp3MemoryData ssize_t memoryDataRead(void* raw_mp3_data, void* buffer, size_t nbyte) { auto mp3_data = static_cast(raw_mp3_data); - if (mp3_data->offset >= (ssize_t)mp3_data->size) + if (mp3_data->offset >= static_cast(mp3_data->size)) { memset(buffer, 0, nbyte); - return (ssize_t)0; + return 0; } - else if (mp3_data->offset + (ssize_t)nbyte > (ssize_t)mp3_data->size) + + if (mp3_data->offset + static_cast(nbyte) > static_cast(mp3_data->size)) { size_t read_size = mp3_data->size - mp3_data->offset; - size_t mem_set_size = mp3_data->offset + nbyte - (ssize_t)mp3_data->size; - memcpy(buffer, (unsigned char*)mp3_data->data + mp3_data->offset, read_size); + size_t mem_set_size = mp3_data->offset + nbyte - static_cast(mp3_data->size); + memcpy(buffer, static_cast(mp3_data->data) + mp3_data->offset, read_size); memset(buffer, 0, mem_set_size); mp3_data->offset += read_size; - return (ssize_t)read_size; - } - else - { - memcpy(buffer, (unsigned char*)mp3_data->data + mp3_data->offset, nbyte); - mp3_data->offset += nbyte; - return (ssize_t)nbyte; + return static_cast(read_size); } + + memcpy(buffer, static_cast(mp3_data->data) + mp3_data->offset, nbyte); + mp3_data->offset += nbyte; + return static_cast(nbyte); } off_t memoryDataLSeek(void* raw_mp3_data, off_t offset, int whence) @@ -60,25 +95,37 @@ void memoryDataCleanup(void* raw_mp3_data) } // namespace slade::audio +// ----------------------------------------------------------------------------- +// +// Mp3Music Class Functions +// +// ----------------------------------------------------------------------------- + +// ----------------------------------------------------------------------------- +// Mp3Music class constructor +// ----------------------------------------------------------------------------- Mp3Music::Mp3Music() { int err = MPG123_OK; if ((err = mpg123_init()) != MPG123_OK) { - std::cerr << mpg123_plain_strerror(err) << std::endl; + log::error(mpg123_plain_strerror(err)); return; } handle_ = mpg123_new(nullptr, &err); if (!handle_) { - std::cerr << "Unable to create mpg123 handle: " << mpg123_plain_strerror(err) << std::endl; + log::error("Unable to create mpg123 handle: {}", mpg123_plain_strerror(err)); return; } mpg123_replace_reader_handle(handle_, &memoryDataRead, &memoryDataLSeek, &memoryDataCleanup); } +// ----------------------------------------------------------------------------- +// Mp3Music class destructor +// ----------------------------------------------------------------------------- Mp3Music::~Mp3Music() { SoundStream::stop(); @@ -94,6 +141,9 @@ Mp3Music::~Mp3Music() mpg123_exit(); } +// ----------------------------------------------------------------------------- +// Loads an mp3 file for playback +// ----------------------------------------------------------------------------- bool Mp3Music::openFromFile(const std::string& filename) { stop(); @@ -109,7 +159,7 @@ bool Mp3Music::openFromFile(const std::string& filename) if (mpg123_open(handle_, filename.c_str()) != MPG123_OK) { - std::cerr << mpg123_strerror(handle_) << std::endl; + log::error(mpg123_strerror(handle_)); return false; } @@ -117,7 +167,7 @@ bool Mp3Music::openFromFile(const std::string& filename) int channels = 0, encoding = 0; if (mpg123_getformat(handle_, &rate, &channels, &encoding) != MPG123_OK) { - std::cerr << "Failed to get format information for \"" << filename << "\"" << std::endl; + log::error("Failed to get format information for \"{}\"", filename); return false; } sampling_rate_ = rate; @@ -126,7 +176,7 @@ bool Mp3Music::openFromFile(const std::string& filename) buffer_ = new unsigned char[buffer_size_]; if (!buffer_) { - std::cerr << "Failed to reserve memory for decoding one frame for \"" << filename << "\"" << std::endl; + log::error("Failed to reserve memory for decoding one frame for \"{}\"", filename); return false; } @@ -135,6 +185,9 @@ bool Mp3Music::openFromFile(const std::string& filename) return true; } +// ----------------------------------------------------------------------------- +// Loads mp3 data for playback +// ----------------------------------------------------------------------------- bool Mp3Music::loadFromMemory(void* data, size_t size_in_bytes) { stop(); @@ -179,26 +232,32 @@ bool Mp3Music::loadFromMemory(void* data, size_t size_in_bytes) return false; } - log::info("rate {}, channels {}", rate, channels); + log::debug("rate {}, channels {}", rate, channels); initialize(channels, rate); return true; } +// ----------------------------------------------------------------------------- +// Returns the duration of the currently loaded mp3 +// ----------------------------------------------------------------------------- sf::Time Mp3Music::duration() const { if (!handle_ || sampling_rate_ == 0) return {}; auto len = mpg123_length(handle_); - auto secs = (float)len / (float)sampling_rate_; + auto secs = static_cast(len) / static_cast(sampling_rate_); - log::info("len {} rate {} secs {}", len, sampling_rate_, secs); + log::debug("len {} rate {} secs {}", len, sampling_rate_, secs); return sf::seconds(secs); } +// ----------------------------------------------------------------------------- +// Called when sound data is requested from the stream +// ----------------------------------------------------------------------------- bool Mp3Music::onGetData(Chunk& data) { sf::Lock lock(mutex_); @@ -208,7 +267,7 @@ bool Mp3Music::onGetData(Chunk& data) size_t done; mpg123_read(handle_, buffer_, buffer_size_, &done); - data.samples = (short*)buffer_; + data.samples = reinterpret_cast(buffer_); data.sampleCount = done / sizeof(short); return (data.sampleCount > 0); @@ -217,6 +276,9 @@ bool Mp3Music::onGetData(Chunk& data) return false; } +// ----------------------------------------------------------------------------- +// Called when seeking is requested on the sound stream +// ----------------------------------------------------------------------------- void Mp3Music::onSeek(sf::Time time_offset) { sf::Lock lock(mutex_); diff --git a/src/Audio/Mp3Music.h b/src/Audio/Mp3Music.h index d42ad901c..a51bf6631 100644 --- a/src/Audio/Mp3Music.h +++ b/src/Audio/Mp3Music.h @@ -9,7 +9,7 @@ class Mp3Music : public sf::SoundStream { public: Mp3Music(); - ~Mp3Music(); + ~Mp3Music() override; bool openFromFile(const std::string& filename); bool loadFromMemory(void* data, size_t size_in_bytes); diff --git a/src/Game/ActionSpecial.cpp b/src/Game/ActionSpecial.cpp index 7c33c1088..856980073 100644 --- a/src/Game/ActionSpecial.cpp +++ b/src/Game/ActionSpecial.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -32,6 +32,7 @@ #include "Main.h" #include "ActionSpecial.h" #include "Configuration.h" +#include "Game.h" #include "Utility/Parser.h" #include "Utility/StringUtils.h" diff --git a/src/Game/Args.cpp b/src/Game/Args.cpp index f42f6ce96..b202c2fd7 100644 --- a/src/Game/Args.cpp +++ b/src/Game/Args.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: https://slade.mancubus.net @@ -184,12 +184,12 @@ void Arg::parse(ParseTreeNode* node, SpecialMap* shared_args) // Check for simple definition if (node->isLeaf()) { - auto name = node->stringValue(); + const auto node_name = node->stringValue(); // Names beginning with a dollar sign are references to predeclared args - if (shared_args && strutil::startsWith(name, '$')) + if (shared_args && strutil::startsWith(node_name, '$')) { - auto it = shared_args->find(name.substr(1)); + auto it = shared_args->find(node_name.substr(1)); if (it == shared_args->end()) // Totally bogus reference; silently ignore this arg return; @@ -199,7 +199,7 @@ void Arg::parse(ParseTreeNode* node, SpecialMap* shared_args) else { // Set name - this->name = node->stringValue(); + name = node->stringValue(); // Set description (if specified) if (node->nValues() > 1) diff --git a/src/Game/Args.h b/src/Game/Args.h index b1c5420e6..f0c0b6677 100644 --- a/src/Game/Args.h +++ b/src/Game/Args.h @@ -33,7 +33,7 @@ namespace game vector custom_values; vector custom_flags; - Arg() {} + Arg() = default; Arg(string_view name) : name{ name } {} string valueString(int value) const; diff --git a/src/Game/Configuration.cpp b/src/Game/Configuration.cpp index 55b3f0030..90a25964b 100644 --- a/src/Game/Configuration.cpp +++ b/src/Game/Configuration.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -33,13 +33,18 @@ // ----------------------------------------------------------------------------- #include "Main.h" #include "Configuration.h" +#include "ActionSpecial.h" #include "App.h" #include "Archive/Archive.h" #include "Archive/ArchiveManager.h" #include "Decorate.h" +#include "Game.h" #include "GenLineSpecial.h" #include "General/Console.h" -#include "SLADEMap/SLADEMap.h" +#include "SLADEMap/MapObject/MapLine.h" +#include "SLADEMap/MapObject/MapThing.h" +#include "SpecialPreset.h" +#include "UDMFProperty.h" #include "Utility/Parser.h" #include "Utility/StringUtils.h" #include "ZScript.h" @@ -56,6 +61,25 @@ using namespace game; EXTERN_CVAR(String, game_configuration) EXTERN_CVAR(String, port_configuration) CVAR(Bool, debug_configuration, false, CVar::Flag::Save) +namespace slade::game +{ +Configuration config_current; +} + + +// ----------------------------------------------------------------------------- +// +// Game Namespace Functions +// +// ----------------------------------------------------------------------------- + +// ----------------------------------------------------------------------------- +// Returns the currently loaded game configuration +// ----------------------------------------------------------------------------- +Configuration& game::configuration() +{ + return config_current; +} // ----------------------------------------------------------------------------- @@ -317,9 +341,8 @@ void Configuration::readUDMFProperties(const ParseTreeNode* block, UDMFPropMap& // Reads a game or port definition from a parsed tree [node]. If [port_section] // is true it is a port definition // ----------------------------------------------------------------------------- -#define SET_UDMF_FEATURE(feature, field) \ - else if (strutil::equalCI(node->name(), #field))( \ - udmf_features_[static_cast(feature)]) = node->boolValue() +#define SET_UDMF_FEATURE(feature, field) \ + else if (strutil::equalCI(node->name(), #field))(udmf_features_[static_cast(feature)]) = node->boolValue() #define SET_FEATURE(feature, value) supported_features_[static_cast(feature)] = value void Configuration::readGameSection(const ParseTreeNode* node_game, bool port_section) { @@ -561,12 +584,12 @@ bool Configuration::readConfiguration( Parser parser; switch (format) { - case MapFormat::Doom: parser.define("MAP_DOOM"); break; - case MapFormat::Hexen: parser.define("MAP_HEXEN"); break; - case MapFormat::Doom64: parser.define("MAP_DOOM64"); break; + case MapFormat::Doom: parser.define("MAP_DOOM"); break; + case MapFormat::Hexen: parser.define("MAP_HEXEN"); break; + case MapFormat::Doom64: parser.define("MAP_DOOM64"); break; case MapFormat::Doom32X: parser.define("MAP_DOOM32X"); break; - case MapFormat::UDMF: parser.define("MAP_UDMF"); break; - default: parser.define("MAP_UNKNOWN"); break; + case MapFormat::UDMF: parser.define("MAP_UDMF"); break; + default: parser.define("MAP_UNKNOWN"); break; } parser.parseText(cfg, source); @@ -681,7 +704,7 @@ bool Configuration::readConfiguration( bool exists = false; for (auto& f : flags_line_) { - if ((unsigned)f.flag == flag_val) + if (static_cast(f.flag) == flag_val) { exists = true; f.name = flag_name; @@ -691,7 +714,7 @@ bool Configuration::readConfiguration( // Add flag otherwise if (!exists) - flags_line_.push_back({ (int)flag_val, flag_name, flag_udmf, activation }); + flags_line_.push_back({ static_cast(flag_val), flag_name, flag_udmf, activation }); } } @@ -749,7 +772,7 @@ bool Configuration::readConfiguration( // Add trigger otherwise if (!exists) - triggers_line_.push_back({ (int)flag_val, flag_name, flag_udmf, false }); + triggers_line_.push_back({ static_cast(flag_val), flag_name, flag_udmf, false }); } } @@ -807,7 +830,7 @@ bool Configuration::readConfiguration( // Add flag otherwise if (!exists) - flags_thing_.push_back({ (int)flag_val, flag_name, flag_udmf, false }); + flags_thing_.push_back({ static_cast(flag_val), flag_name, flag_udmf, false }); } } @@ -984,7 +1007,7 @@ bool Configuration::openConfig(const string& game, const string& port, MapFormat log::info("Reading SLADECFG in {}", parent->filename()); // Read embedded config - string config{ (const char*)cfg_entry->rawData(), cfg_entry->size() }; + string config{ reinterpret_cast(cfg_entry->rawData()), cfg_entry->size() }; if (!readConfiguration(config, cfg_entry->name(), format, true, false)) log::error("Error reading embedded game configuration, not loaded"); } @@ -1783,11 +1806,11 @@ UDMFPropMap& Configuration::allUDMFProperties(MapObject::Type type) switch (type) { case MapObject::Type::Vertex: return udmf_vertex_props_; - case MapObject::Type::Line: return udmf_linedef_props_; - case MapObject::Type::Side: return udmf_sidedef_props_; + case MapObject::Type::Line: return udmf_linedef_props_; + case MapObject::Type::Side: return udmf_sidedef_props_; case MapObject::Type::Sector: return udmf_sector_props_; - case MapObject::Type::Thing: return udmf_thing_props_; - default: return map_invalid_type; + case MapObject::Type::Thing: return udmf_thing_props_; + default: return map_invalid_type; } } @@ -2135,11 +2158,11 @@ string Configuration::defaultString(MapObject::Type type, const string& property { switch (type) { - case MapObject::Type::Line: return defaults_line_.getOr(property, {}); - case MapObject::Type::Side: return defaults_side_.getOr(property, {}); + case MapObject::Type::Line: return defaults_line_.getOr(property, {}); + case MapObject::Type::Side: return defaults_side_.getOr(property, {}); case MapObject::Type::Sector: return defaults_sector_.getOr(property, {}); - case MapObject::Type::Thing: return defaults_thing_.getOr(property, {}); - default: return {}; + case MapObject::Type::Thing: return defaults_thing_.getOr(property, {}); + default: return {}; } } @@ -2150,11 +2173,11 @@ int Configuration::defaultInt(MapObject::Type type, const string& property) cons { switch (type) { - case MapObject::Type::Line: return defaults_line_.getOr(property, 0); - case MapObject::Type::Side: return defaults_side_.getOr(property, 0); + case MapObject::Type::Line: return defaults_line_.getOr(property, 0); + case MapObject::Type::Side: return defaults_side_.getOr(property, 0); case MapObject::Type::Sector: return defaults_sector_.getOr(property, 0); - case MapObject::Type::Thing: return defaults_thing_.getOr(property, 0); - default: return 0; + case MapObject::Type::Thing: return defaults_thing_.getOr(property, 0); + default: return 0; } } @@ -2165,11 +2188,11 @@ double Configuration::defaultFloat(MapObject::Type type, const string& property) { switch (type) { - case MapObject::Type::Line: return defaults_line_.getOr(property, 0.); - case MapObject::Type::Side: return defaults_side_.getOr(property, 0.); + case MapObject::Type::Line: return defaults_line_.getOr(property, 0.); + case MapObject::Type::Side: return defaults_side_.getOr(property, 0.); case MapObject::Type::Sector: return defaults_sector_.getOr(property, 0.); - case MapObject::Type::Thing: return defaults_thing_.getOr(property, 0.); - default: return 0.; + case MapObject::Type::Thing: return defaults_thing_.getOr(property, 0.); + default: return 0.; } } @@ -2180,11 +2203,11 @@ bool Configuration::defaultBool(MapObject::Type type, const string& property) co { switch (type) { - case MapObject::Type::Line: return defaults_line_.getOr(property, false); - case MapObject::Type::Side: return defaults_side_.getOr(property, false); + case MapObject::Type::Line: return defaults_line_.getOr(property, false); + case MapObject::Type::Side: return defaults_side_.getOr(property, false); case MapObject::Type::Sector: return defaults_sector_.getOr(property, false); - case MapObject::Type::Thing: return defaults_thing_.getOr(property, false); - default: return false; + case MapObject::Type::Thing: return defaults_thing_.getOr(property, false); + default: return false; } } @@ -2251,7 +2274,7 @@ void Configuration::applyDefaults(MapObject* object, bool udmf) const switch (property::valueType(prop_vals[a])) { case property::ValueType::Bool: object->setBoolProperty(prop_names[a], std::get(prop_vals[a])); break; - case property::ValueType::Int: object->setIntProperty(prop_names[a], std::get(prop_vals[a])); break; + case property::ValueType::Int: object->setIntProperty(prop_names[a], std::get(prop_vals[a])); break; case property::ValueType::UInt: object->setIntProperty(prop_names[a], std::get(prop_vals[a])); break; @@ -2294,7 +2317,7 @@ int Configuration::upLightLevel(int light_level) const if (light_levels_.empty()) return light_level; - for (int a = 0; a < (int)light_levels_.size() - 1; a++) + for (int a = 0; a < static_cast(light_levels_.size()) - 1; a++) { if (light_level >= light_levels_[a] && light_level < light_levels_[a + 1]) return light_levels_[a + 1]; @@ -2313,7 +2336,7 @@ int Configuration::downLightLevel(int light_level) const if (light_levels_.empty()) return light_level; - for (int a = 0; a < (int)light_levels_.size() - 1; a++) + for (int a = 0; a < static_cast(light_levels_.size()) - 1; a++) { if (light_level > light_levels_[a] && light_level <= light_levels_[a + 1]) return light_levels_[a]; diff --git a/src/Game/Configuration.h b/src/Game/Configuration.h index 0d230c8f0..ac9c920f1 100644 --- a/src/Game/Configuration.h +++ b/src/Game/Configuration.h @@ -1,15 +1,13 @@ #pragma once -#include "ActionSpecial.h" -#include "Game.h" +#include "Args.h" #include "General/Defs.h" #include "MapInfo.h" #include "SLADEMap/MapObject/MapObject.h" -#include "SpecialPreset.h" #include "ThingType.h" -#include "UDMFProperty.h" -#include "Utility/Property.h" +#include +// Forward declarations namespace slade { class ParseTreeNode; @@ -21,250 +19,261 @@ namespace zscript { class Definitions; } - namespace game { - // Feature Support - enum class Feature + struct SpecialPreset; + class ThingType; + class ActionSpecial; + class UDMFProperty; +} // namespace game +} // namespace slade + +namespace slade::game +{ +// Feature Support +enum class Feature +{ + Boom, + AnyMapName, + MixTexFlats, + TxTextures, + LongNames, + MBF21, +}; +enum class UDMFFeature +{ + Slopes, // Slope support + FlatLighting, // Flat lighting independent from sector lighting + FlatPanning, // Flat panning + FlatRotation, // Flat rotation + FlatScaling, // Flat scaling + LineTransparency, // Line transparency + SectorColor, // Sector colour + SectorFog, // Sector fog + SideLighting, // Sidedef lighting independent from sector lighting + SideMidtexWrapping, // Per-sidedef midtex wrapping + SideScaling, // Line scaling + TextureScaling, // Per-texture line scaling + TextureOffsets, // Per-texture offsets compared to per-sidedef + ThingScaling, // Per-thing scaling + ThingRotation, // Per-thing pitch and yaw rotation +}; + +typedef std::map UDMFPropMap; + +class Configuration +{ +public: + struct Flag { - Boom, - AnyMapName, - MixTexFlats, - TxTextures, - LongNames, - MBF21, + int flag; + string name; + string udmf; + bool activation; }; - enum class UDMFFeature + + struct MapConf { - Slopes, // Slope support - FlatLighting, // Flat lighting independent from sector lighting - FlatPanning, // Flat panning - FlatRotation, // Flat rotation - FlatScaling, // Flat scaling - LineTransparency, // Line transparency - SectorColor, // Sector colour - SectorFog, // Sector fog - SideLighting, // Sidedef lighting independent from sector lighting - SideMidtexWrapping, // Per-sidedef midtex wrapping - SideScaling, // Line scaling - TextureScaling, // Per-texture line scaling - TextureOffsets, // Per-texture offsets compared to per-sidedef - ThingScaling, // Per-thing scaling - ThingRotation, // Per-thing pitch and yaw rotation + string mapname; + string sky1; + string sky2; }; - typedef std::map UDMFPropMap; + Configuration(); + ~Configuration() = default; - class Configuration - { - public: - struct Flag - { - int flag; - string name; - string udmf; - bool activation; - }; - - struct MapConf - { - string mapname; - string sky1; - string sky2; - }; - - Configuration(); - ~Configuration() = default; - - void setDefaults(); - const string& currentGame() const { return current_game_; } - const string& currentPort() const { return current_port_; } - bool supportsSectorFlags() const { return boom_sector_flag_start_ > 0; } - string udmfNamespace() const; - const string& skyFlat() const { return sky_flat_; } - const string& scriptLanguage() const { return script_language_; } - int lightLevelInterval() const; - int playerEyeHeight() const { return player_eye_height_; } - - unsigned nMapNames() const { return maps_.size(); } - const string& mapName(unsigned index); - MapConf mapInfo(string_view mapname); - - // General Accessors - const std::map& allActionSpecials() const { return action_specials_; } - const std::map& allThingTypes() const { return thing_types_; } - const std::map& allSectorTypes() const { return sector_types_; } - - // Feature Support - bool featureSupported(Feature feature) const { return supported_features_[static_cast(feature)]; } - bool featureSupported(UDMFFeature feature) const { return udmf_features_[static_cast(feature)]; } - - // Configuration reading - void readActionSpecials( - ParseTreeNode* node, - Arg::SpecialMap& shared_args, - const ActionSpecial* group_defaults = nullptr); - void readThingTypes(ParseTreeNode* node, const ThingType& group_defaults = ThingType::unknown()); - void readUDMFProperties(const ParseTreeNode* block, UDMFPropMap& plist) const; - void readGameSection(const ParseTreeNode* node_game, bool port_section = false); - bool readConfiguration( - string_view cfg, - string_view source = "", - MapFormat format = MapFormat::Unknown, - bool ignore_game = false, - bool clear = true); - bool openConfig(const string& game, const string& port = "", MapFormat format = MapFormat::Unknown); - - // Action specials - const ActionSpecial& actionSpecial(unsigned id); - string actionSpecialName(int special); - - // Thing types - const ThingType& thingType(unsigned type); - const ThingType& thingTypeGroupDefaults(const string& group); - - // Thing flags - int nThingFlags() const { return flags_thing_.size(); } - string thingFlag(unsigned flag_index); - bool thingFlagSet(unsigned flag_index, const MapThing* thing) const; - bool thingFlagSet(string_view udmf_name, MapThing* thing, MapFormat map_format) const; - bool thingBasicFlagSet(string_view flag, MapThing* thing, MapFormat map_format) const; - string thingFlagsString(int flags) const; - void setThingFlag(unsigned flag_index, MapThing* thing, bool set = true) const; - void setThingFlag(string_view udmf_name, MapThing* thing, MapFormat map_format, bool set = true) const; - void setThingBasicFlag(string_view flag, MapThing* thing, MapFormat map_format, bool set = true) const; - - // DECORATE - bool parseDecorateDefs(Archive* archive); - void clearDecorateDefs() const; - - // ZScript - void importZScriptDefs(zscript::Definitions& defs); - - // MapInfo - bool parseMapInfo(const Archive& archive); - void clearMapInfo() { map_info_.clear(); } - void linkDoomEdNums(); - - // Line flags - unsigned nLineFlags() const { return flags_line_.size(); } - const Flag& lineFlag(unsigned flag_index); - bool lineFlagSet(unsigned flag_index, const MapLine* line) const; - bool lineFlagSet(string_view udmf_name, MapLine* line, MapFormat map_format) const; - bool lineBasicFlagSet(string_view flag, MapLine* line, MapFormat map_format) const; - string lineFlagsString(const MapLine* line) const; - void setLineFlag(unsigned flag_index, MapLine* line, bool set = true) const; - void setLineFlag(string_view udmf_name, MapLine* line, MapFormat map_format, bool set = true) const; - void setLineBasicFlag(string_view flag, MapLine* line, MapFormat map_format, bool set = true) const; - - // Line action (SPAC) triggers - string spacTriggerString(MapLine* line, MapFormat map_format); - int spacTriggerIndexHexen(const MapLine* line) const; - vector allSpacTriggers() const; - void setLineSpacTrigger(unsigned trigger_index, MapLine* line) const; - const string& spacTriggerUDMFName(unsigned trigger_index); - - // UDMF properties - UDMFProperty* getUDMFProperty(const string& name, MapObject::Type type); - UDMFPropMap& allUDMFProperties(MapObject::Type type); - void cleanObjectUDMFProps(MapObject* object); - - // Sector types - string sectorTypeName(int type); - int sectorTypeByName(string_view name) const; - int baseSectorType(int type) const; - int sectorBoomDamage(int type) const; - bool sectorBoomSecret(int type) const; - bool sectorBoomFriction(int type) const; - bool sectorBoomPushPull(int type) const; - bool sectorMBF21AltDamageMode(int type) const; - bool sectorMBF21KillGroundedMonsters(int type) const; - int boomSectorType( - int base, - int damage, - bool secret, - bool friction, - bool pushpull, - bool alt_damage, - bool kill_grounded) const; - - // Defaults - string defaultString(MapObject::Type type, const string& property) const; - int defaultInt(MapObject::Type type, const string& property) const; - double defaultFloat(MapObject::Type type, const string& property) const; - bool defaultBool(MapObject::Type type, const string& property) const; - void applyDefaults(MapObject* object, bool udmf = false) const; - - // Special Presets - const vector& specialPresets() const { return special_presets_; } - - // Misc - void setLightLevelInterval(int interval); - int upLightLevel(int light_level) const; - int downLightLevel(int light_level) const; - - // Testing - void dumpActionSpecials() const; - void dumpThingTypes() const; - void dumpValidMapNames() const; - void dumpUDMFProperties(); - - private: - string current_game_; // Current game name - string current_port_; // Current port name (empty if none) - std::map map_formats_; // Supported map formats - string udmf_namespace_; // Namespace to use for UDMF - int boom_sector_flag_start_; // Beginning of Boom sector flags - string sky_flat_; // Sky flat for 3d mode - string script_language_; // Scripting language (should be extended to allow multiple) - vector light_levels_; // Light levels for up/down light in editor - int player_eye_height_; // Player eye height for 3d mode camera - - // Action specials - std::map action_specials_; - - // Thing types - std::map thing_types_; - std::map tt_group_defaults_; - vector parsed_types_; - // std::map parsed_types_; // ThingTypes parsed from definitions - // (DECORATE, ZScript etc.) - - // Flags - vector flags_thing_; - vector flags_line_; - vector triggers_line_; - - // Sector types - std::map sector_types_; - - // Map info - vector maps_; - MapInfo map_info_; - - // UDMF properties - UDMFPropMap udmf_vertex_props_; - UDMFPropMap udmf_linedef_props_; - UDMFPropMap udmf_sidedef_props_; - UDMFPropMap udmf_sector_props_; - UDMFPropMap udmf_thing_props_; - - // Defaults - PropertyList defaults_line_; - PropertyList defaults_line_udmf_; - PropertyList defaults_side_; - PropertyList defaults_side_udmf_; - PropertyList defaults_sector_; - PropertyList defaults_sector_udmf_; - PropertyList defaults_thing_; - PropertyList defaults_thing_udmf_; - - // Feature Support - std::array supported_features_; - std::array udmf_features_; - - // Special Presets - vector special_presets_; - }; -} // namespace game -} // namespace slade + void setDefaults(); + const string& currentGame() const { return current_game_; } + const string& currentPort() const { return current_port_; } + bool supportsSectorFlags() const { return boom_sector_flag_start_ > 0; } + string udmfNamespace() const; + const string& skyFlat() const { return sky_flat_; } + const string& scriptLanguage() const { return script_language_; } + int lightLevelInterval() const; + int playerEyeHeight() const { return player_eye_height_; } + + unsigned nMapNames() const { return maps_.size(); } + const string& mapName(unsigned index); + MapConf mapInfo(string_view mapname); + + // General Accessors + const std::map& allActionSpecials() const { return action_specials_; } + const std::map& allThingTypes() const { return thing_types_; } + const std::map& allSectorTypes() const { return sector_types_; } + + // Feature Support + bool featureSupported(Feature feature) const { return supported_features_[static_cast(feature)]; } + bool featureSupported(UDMFFeature feature) const { return udmf_features_[static_cast(feature)]; } + + // Configuration reading + void readActionSpecials( + ParseTreeNode* node, + Arg::SpecialMap& shared_args, + const ActionSpecial* group_defaults = nullptr); + void readThingTypes(ParseTreeNode* node, const ThingType& group_defaults = ThingType::unknown()); + void readUDMFProperties(const ParseTreeNode* block, UDMFPropMap& plist) const; + void readGameSection(const ParseTreeNode* node_game, bool port_section = false); + bool readConfiguration( + string_view cfg, + string_view source = "", + MapFormat format = MapFormat::Unknown, + bool ignore_game = false, + bool clear = true); + bool openConfig(const string& game, const string& port = "", MapFormat format = MapFormat::Unknown); + + // Action specials + const ActionSpecial& actionSpecial(unsigned id); + string actionSpecialName(int special); + + // Thing types + const ThingType& thingType(unsigned type); + const ThingType& thingTypeGroupDefaults(const string& group); + + // Thing flags + int nThingFlags() const { return flags_thing_.size(); } + string thingFlag(unsigned flag_index); + bool thingFlagSet(unsigned flag_index, const MapThing* thing) const; + bool thingFlagSet(string_view udmf_name, MapThing* thing, MapFormat map_format) const; + bool thingBasicFlagSet(string_view flag, MapThing* thing, MapFormat map_format) const; + string thingFlagsString(int flags) const; + void setThingFlag(unsigned flag_index, MapThing* thing, bool set = true) const; + void setThingFlag(string_view udmf_name, MapThing* thing, MapFormat map_format, bool set = true) const; + void setThingBasicFlag(string_view flag, MapThing* thing, MapFormat map_format, bool set = true) const; + + // DECORATE + bool parseDecorateDefs(Archive* archive); + void clearDecorateDefs() const; + + // ZScript + void importZScriptDefs(zscript::Definitions& defs); + + // MapInfo + bool parseMapInfo(const Archive& archive); + void clearMapInfo() { map_info_.clear(); } + void linkDoomEdNums(); + + // Line flags + unsigned nLineFlags() const { return flags_line_.size(); } + const Flag& lineFlag(unsigned flag_index); + bool lineFlagSet(unsigned flag_index, const MapLine* line) const; + bool lineFlagSet(string_view udmf_name, MapLine* line, MapFormat map_format) const; + bool lineBasicFlagSet(string_view flag, MapLine* line, MapFormat map_format) const; + string lineFlagsString(const MapLine* line) const; + void setLineFlag(unsigned flag_index, MapLine* line, bool set = true) const; + void setLineFlag(string_view udmf_name, MapLine* line, MapFormat map_format, bool set = true) const; + void setLineBasicFlag(string_view flag, MapLine* line, MapFormat map_format, bool set = true) const; + + // Line action (SPAC) triggers + string spacTriggerString(MapLine* line, MapFormat map_format); + int spacTriggerIndexHexen(const MapLine* line) const; + vector allSpacTriggers() const; + void setLineSpacTrigger(unsigned trigger_index, MapLine* line) const; + const string& spacTriggerUDMFName(unsigned trigger_index); + + // UDMF properties + UDMFProperty* getUDMFProperty(const string& name, MapObject::Type type); + UDMFPropMap& allUDMFProperties(MapObject::Type type); + void cleanObjectUDMFProps(MapObject* object); + + // Sector types + string sectorTypeName(int type); + int sectorTypeByName(string_view name) const; + int baseSectorType(int type) const; + int sectorBoomDamage(int type) const; + bool sectorBoomSecret(int type) const; + bool sectorBoomFriction(int type) const; + bool sectorBoomPushPull(int type) const; + bool sectorMBF21AltDamageMode(int type) const; + bool sectorMBF21KillGroundedMonsters(int type) const; + int boomSectorType( + int base, + int damage, + bool secret, + bool friction, + bool pushpull, + bool alt_damage, + bool kill_grounded) const; + + // Defaults + string defaultString(MapObject::Type type, const string& property) const; + int defaultInt(MapObject::Type type, const string& property) const; + double defaultFloat(MapObject::Type type, const string& property) const; + bool defaultBool(MapObject::Type type, const string& property) const; + void applyDefaults(MapObject* object, bool udmf = false) const; + + // Special Presets + const vector& specialPresets() const { return special_presets_; } + + // Misc + void setLightLevelInterval(int interval); + int upLightLevel(int light_level) const; + int downLightLevel(int light_level) const; + + // Testing + void dumpActionSpecials() const; + void dumpThingTypes() const; + void dumpValidMapNames() const; + void dumpUDMFProperties(); + +private: + string current_game_; // Current game name + string current_port_; // Current port name (empty if none) + std::map map_formats_; // Supported map formats + string udmf_namespace_; // Namespace to use for UDMF + int boom_sector_flag_start_; // Beginning of Boom sector flags + string sky_flat_; // Sky flat for 3d mode + string script_language_; // Scripting language (should be extended to allow multiple) + vector light_levels_; // Light levels for up/down light in editor + int player_eye_height_; // Player eye height for 3d mode camera + + // Action specials + std::map action_specials_; + + // Thing types + std::map thing_types_; + std::map tt_group_defaults_; + vector parsed_types_; + // std::map parsed_types_; // ThingTypes parsed from definitions + // (DECORATE, ZScript etc.) + + // Flags + vector flags_thing_; + vector flags_line_; + vector triggers_line_; + + // Sector types + std::map sector_types_; + + // Map info + vector maps_; + MapInfo map_info_; + + // UDMF properties + UDMFPropMap udmf_vertex_props_; + UDMFPropMap udmf_linedef_props_; + UDMFPropMap udmf_sidedef_props_; + UDMFPropMap udmf_sector_props_; + UDMFPropMap udmf_thing_props_; + + // Defaults + PropertyList defaults_line_; + PropertyList defaults_line_udmf_; + PropertyList defaults_side_; + PropertyList defaults_side_udmf_; + PropertyList defaults_sector_; + PropertyList defaults_sector_udmf_; + PropertyList defaults_thing_; + PropertyList defaults_thing_udmf_; + + // Feature Support + std::array supported_features_; + std::array udmf_features_; + + // Special Presets + vector special_presets_; +}; + +// Full Game Configuration +Configuration& configuration(); + +} // namespace slade::game diff --git a/src/Game/Decorate.cpp b/src/Game/Decorate.cpp index 693af771b..af0da7a99 100644 --- a/src/Game/Decorate.cpp +++ b/src/Game/Decorate.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net diff --git a/src/Game/Game.cpp b/src/Game/Game.cpp index 8baa16ba3..f079a4f60 100644 --- a/src/Game/Game.cpp +++ b/src/Game/Game.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -32,10 +32,12 @@ // ----------------------------------------------------------------------------- #include "Main.h" #include "Game.h" +#include "ActionSpecial.h" #include "App.h" #include "Archive/ArchiveManager.h" #include "Archive/Formats/ZipArchive.h" #include "Configuration.h" +#include "SpecialPreset.h" #include "TextEditor/TextLanguage.h" #include "Utility/Parser.h" #include "Utility/StringUtils.h" @@ -53,7 +55,6 @@ using namespace game; // ----------------------------------------------------------------------------- namespace slade::game { -Configuration config_current; std::map game_defs; GameDef game_def_unknown; std::map port_defs; @@ -223,20 +224,14 @@ bool PortDef::parse(const MemChunk& mc) // ----------------------------------------------------------------------------- -// ----------------------------------------------------------------------------- -// Returns the currently loaded game configuration -// ----------------------------------------------------------------------------- -Configuration& game::configuration() -{ - return config_current; -} - // ----------------------------------------------------------------------------- // Clears and re-parses custom definitions in all open archives // (DECORATE, *MAPINFO, ZScript etc.) // ----------------------------------------------------------------------------- void game::updateCustomDefinitions() { + auto& config_current = configuration(); + // Clear out all existing custom definitions config_current.clearDecorateDefs(); config_current.clearMapInfo(); @@ -407,7 +402,7 @@ void game::init() // Load last configuration if any if (!game_configuration.value.empty()) - config_current.openConfig(game_configuration, port_configuration); + configuration().openConfig(game_configuration, port_configuration); // Load custom special presets if (!loadCustomSpecialPresets()) @@ -440,7 +435,7 @@ void game::init() lang->loadZScript(zscript_base); // MapInfo - config_current.parseMapInfo(zdoom_pk3); + configuration().parseMapInfo(zdoom_pk3); } }); zscript_parse_thread->detach(); diff --git a/src/Game/Game.h b/src/Game/Game.h index 693b041ca..18c93c721 100644 --- a/src/Game/Game.h +++ b/src/Game/Game.h @@ -7,8 +7,6 @@ class ParseTreeNode; namespace game { - class Configuration; - // Structs struct GameDef { @@ -92,9 +90,6 @@ namespace game bool mapFormatSupported(MapFormat format, const string& game, const string& port = ""); - // Full Game Configuration - Configuration& configuration(); - // Tagging TagType parseTagged(const ParseTreeNode* tagged); diff --git a/src/Game/GenLineSpecial.cpp b/src/Game/GenLineSpecial.cpp index 0055abd49..7c35e4de8 100644 --- a/src/Game/GenLineSpecial.cpp +++ b/src/Game/GenLineSpecial.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -37,145 +37,187 @@ using namespace slade; // ----------------------------------------------------------------------------- // -// Defines +// Values // // ----------------------------------------------------------------------------- -#define GenFloorBase 0x6000 -#define GenCeilingBase 0x4000 -#define GenDoorBase 0x3c00 -#define GenLockedBase 0x3800 -#define GenLiftBase 0x3400 -#define GenStairsBase 0x3000 -#define GenCrusherBase 0x2F80 - -#define TriggerType 0x0007 -#define TriggerTypeShift 0 - -#define FloorCrush 0x1000 -#define FloorChange 0x0c00 -#define FloorTarget 0x0380 -#define FloorDirection 0x0040 -#define FloorModel 0x0020 -#define FloorSpeed 0x0018 - -#define FloorCrushShift 12 -#define FloorChangeShift 10 -#define FloorTargetShift 7 -#define FloorDirectionShift 6 -#define FloorModelShift 5 -#define FloorSpeedShift 3 - -#define CeilingCrush 0x1000 -#define CeilingChange 0x0c00 -#define CeilingTarget 0x0380 -#define CeilingDirection 0x0040 -#define CeilingModel 0x0020 -#define CeilingSpeed 0x0018 - -#define CeilingCrushShift 12 -#define CeilingChangeShift 10 -#define CeilingTargetShift 7 -#define CeilingDirectionShift 6 -#define CeilingModelShift 5 -#define CeilingSpeedShift 3 - -#define LiftTarget 0x0300 -#define LiftDelay 0x00c0 -#define LiftMonster 0x0020 -#define LiftSpeed 0x0018 - -#define LiftTargetShift 8 -#define LiftDelayShift 6 -#define LiftMonsterShift 5 -#define LiftSpeedShift 3 - -#define StairIgnore 0x0200 -#define StairDirection 0x0100 -#define StairStep 0x00c0 -#define StairMonster 0x0020 -#define StairSpeed 0x0018 - -#define StairIgnoreShift 9 -#define StairDirectionShift 8 -#define StairStepShift 6 -#define StairMonsterShift 5 -#define StairSpeedShift 3 - -#define CrusherSilent 0x0040 -#define CrusherMonster 0x0020 -#define CrusherSpeed 0x0018 - -#define CrusherSilentShift 6 -#define CrusherMonsterShift 5 -#define CrusherSpeedShift 3 - -#define DoorDelay 0x0300 -#define DoorMonster 0x0080 -#define DoorKind 0x0060 -#define DoorSpeed 0x0018 - -#define DoorDelayShift 8 -#define DoorMonsterShift 7 -#define DoorKindShift 5 -#define DoorSpeedShift 3 - -#define LockedNKeys 0x0200 -#define LockedKey 0x01c0 -#define LockedKind 0x0020 -#define LockedSpeed 0x0018 - -#define LockedNKeysShift 9 -#define LockedKeyShift 6 -#define LockedKindShift 5 -#define LockedSpeedShift 3 +namespace +{ +enum +{ + GenFloorBase = 0x6000, + GenCeilingBase = 0x4000, + GenDoorBase = 0x3c00, + GenLockedBase = 0x3800, + GenLiftBase = 0x3400, + GenStairsBase = 0x3000, + GenCrusherBase = 0x2F80 +}; +enum +{ + TriggerType = 0x0007, + TriggerTypeShift = 0 +}; -// ----------------------------------------------------------------------------- -// -// genlinespecial Namespace -// -// ----------------------------------------------------------------------------- -namespace slade::genlinespecial +enum +{ + FloorCrush = 0x1000, + FloorChange = 0x0c00, + FloorTarget = 0x0380, + FloorDirection = 0x0040, + FloorModel = 0x0020, + FloorSpeed = 0x0018 +}; + +enum +{ + FloorCrushShift = 12, + FloorChangeShift = 10, + FloorTargetShift = 7, + FloorDirectionShift = 6, + FloorModelShift = 5, + FloorSpeedShift = 3 +}; + +enum +{ + CeilingCrush = 0x1000, + CeilingChange = 0x0c00, + CeilingTarget = 0x0380, + CeilingDirection = 0x0040, + CeilingModel = 0x0020, + CeilingSpeed = 0x0018 +}; + +enum +{ + CeilingCrushShift = 12, + CeilingChangeShift = 10, + CeilingTargetShift = 7, + CeilingDirectionShift = 6, + CeilingModelShift = 5, + CeilingSpeedShift = 3 +}; + +enum +{ + LiftTarget = 0x0300, + LiftDelay = 0x00c0, + LiftMonster = 0x0020, + LiftSpeed = 0x0018 +}; + +enum +{ + LiftTargetShift = 8, + LiftDelayShift = 6, + LiftMonsterShift = 5, + LiftSpeedShift = 3 +}; + +enum +{ + StairIgnore = 0x0200, + StairDirection = 0x0100, + StairStep = 0x00c0, + StairMonster = 0x0020, + StairSpeed = 0x0018 +}; + +enum +{ + StairIgnoreShift = 9, + StairDirectionShift = 8, + StairStepShift = 6, + StairMonsterShift = 5, + StairSpeedShift = 3 +}; + +enum +{ + CrusherSilent = 0x0040, + CrusherMonster = 0x0020, + CrusherSpeed = 0x0018 +}; + +enum +{ + CrusherSilentShift = 6, + CrusherMonsterShift = 5, + CrusherSpeedShift = 3 +}; + +enum +{ + DoorDelay = 0x0300, + DoorMonster = 0x0080, + DoorKind = 0x0060, + DoorSpeed = 0x0018 +}; + +enum +{ + DoorDelayShift = 8, + DoorMonsterShift = 7, + DoorKindShift = 5, + DoorSpeedShift = 3 +}; + +enum +{ + LockedNKeys = 0x0200, + LockedKey = 0x01c0, + LockedKind = 0x0020, + LockedSpeed = 0x0018 +}; + +enum { -static const char* Triggers[] = { + LockedNKeysShift = 9, + LockedKeyShift = 6, + LockedKindShift = 5, + LockedSpeedShift = 3 +}; + +const char* triggers[] = { "W1", "WR", "S1", "SR", "G1", "GR", "D1", "DR", }; -static const char* FloorTargets[] = { +const char* floor_targets[] = { "to Highest N Floor", "to Lowest N Floor", "to Next N Floor", "to Lowest N Ceiling", "to Ceiling", "by Lower Tex", "24 Units", "32 Units", }; -static const char* Directions[] = { +const char* directions[] = { "Down", "Up", }; -static const char* Speeds[] = { +const char* speeds[] = { "Slow", "Normal", "Fast", "Turbo", }; -static const char* Changers[] = { +const char* changers[] = { "", "Zero Type/Copy Tex", "Copy Tex", "Copy Type/Copy Tex", }; -static const char* Models[] = { +const char* models[] = { "Trigger", "Numeric", }; -static const char* Crushers[] = { +const char* crushers[] = { "", "Cr", }; -static const char* CeilingTargets[] = { +const char* ceiling_targets[] = { "to Highest N Ceiling", "to Lowest N Ceiling", "to Next N Ceiling", @@ -186,57 +228,66 @@ static const char* CeilingTargets[] = { "32 Units", }; -static const char* Doors1[] = { +const char* doors1[] = { "OpnD", "Opn", "ClsD", "Cls", }; -static const char* Doors2[] = { +const char* doors2[] = { "Cls", "", "Opn", "", }; -static const char* Delays[] = { +const char* delays[] = { "1", "4", "9", "30", }; -static const char* LockedDelays[] = { +const char* locked_delays[] = { "4", }; -static const char* Locks[] = { +const char* locks[] = { "Any Key", "Red Card", "Blue Card", "Yellow Card", "Red Skull", "Blue Skull", "Yellow Skull", "All 6 Keys", "Any Key", "Red Key", "Blue Key", "Yellow Key", "Red Key", "Blue Key", "Yellow Key", "All 3 Keys", }; -static const char* LiftTargets[] = { +const char* lift_targets[] = { "to Lowest N Floor", "to Next N Floor", "to Lowest N Ceiling", "Perpetual", }; -static const char* LiftDelays[] = { +const char* lift_delays[] = { "1", "3", "5", "10", }; -static const char* Steps[] = { +const char* steps[] = { "4", "8", "16", "24", }; +} // namespace + +// ----------------------------------------------------------------------------- +// +// genlinespecial Namespace +// +// ----------------------------------------------------------------------------- +namespace slade::genlinespecial +{ // ------------------------------------------------------------------------ // Returns a string representation of the generalised line value [type] // ------------------------------------------------------------------------ @@ -255,18 +306,18 @@ string parseLineType(int type) int model = (type & FloorModel) >> FloorModelShift; // Trigger - type_string += Triggers[trigger]; + type_string += triggers[trigger]; if (change == 0 && model == 1) type_string += "M"; type_string += " Floor "; // Direction, target, speed - type_string += fmt::format("{} {} {}", Directions[direction], FloorTargets[target], Speeds[speed]); + type_string += fmt::format("{} {} {}", directions[direction], floor_targets[target], speeds[speed]); // Change if (type & FloorChange) - type_string += fmt::format(" {} ({})", Changers[change], Models[model]); + type_string += fmt::format(" {} ({})", changers[change], models[model]); // Crush if (type & FloorCrush) @@ -284,18 +335,18 @@ string parseLineType(int type) int model = (type & CeilingModel) >> CeilingModelShift; // Trigger - type_string += Triggers[trigger]; + type_string += triggers[trigger]; if (change == 0 && model == 1) type_string += "M"; type_string += " Ceiling "; // Direction, target, speed - type_string += fmt::format("{} {} {}", Directions[direction], CeilingTargets[target], Speeds[speed]); + type_string += fmt::format("{} {} {}", directions[direction], ceiling_targets[target], speeds[speed]); // Change if (type & CeilingChange) - type_string += fmt::format(" {} ({})", Changers[change], Models[model]); + type_string += fmt::format(" {} ({})", changers[change], models[model]); // Crush if (type & CeilingCrush) @@ -311,7 +362,7 @@ string parseLineType(int type) int speed = (type & DoorSpeed) >> DoorSpeedShift; // Trigger - type_string += Triggers[trigger]; + type_string += triggers[trigger]; if (type & DoorMonster) type_string += "M"; @@ -320,15 +371,15 @@ string parseLineType(int type) // Door kind switch (kind) { - case 0: type_string += fmt::format("Open Wait {} Close", Delays[delay]); break; - case 1: type_string += "Open Stay"; break; - case 2: type_string += fmt::format("Close Wait {} Open", Delays[delay]); break; - case 3: type_string += "Close Stay"; break; + case 0: type_string += fmt::format("Open Wait {} Close", delays[delay]); break; + case 1: type_string += "Open Stay"; break; + case 2: type_string += fmt::format("Close Wait {} Open", delays[delay]); break; + case 3: type_string += "Close Stay"; break; default: break; } // Door speed - type_string += fmt::format(" {}", Speeds[speed]); + type_string += fmt::format(" {}", speeds[speed]); } // Locked Door type @@ -341,25 +392,25 @@ string parseLineType(int type) int speed = (type & DoorSpeed) >> DoorSpeedShift; // Trigger - type_string += Triggers[trigger]; + type_string += triggers[trigger]; type_string += " Door "; // Lock - type_string += fmt::format("{} ", Locks[num * 8 + key]); + type_string += fmt::format("{} ", locks[num * 8 + key]); // Door kind switch (kind) { - case 0: type_string += "Open Wait 4 Close"; break; - case 1: type_string += "Open Stay"; break; - case 2: type_string += "Close Wait 4 Open"; break; - case 3: type_string += "Close Stay"; break; + case 0: type_string += "Open Wait 4 Close"; break; + case 1: type_string += "Open Stay"; break; + case 2: type_string += "Close Wait 4 Open"; break; + case 3: type_string += "Close Stay"; break; default: break; } // Door speed - type_string += fmt::format(" {}", Speeds[speed]); + type_string += fmt::format(" {}", speeds[speed]); } // Lift type @@ -371,20 +422,20 @@ string parseLineType(int type) int speed = (type & LiftSpeed) >> LiftSpeedShift; // Trigger - type_string += Triggers[trigger]; + type_string += triggers[trigger]; if (type & LiftMonster) type_string += "M"; type_string += " Lift "; // Target - type_string += LiftTargets[target]; + type_string += lift_targets[target]; // Delay - type_string += fmt::format(" Delay {} ", LiftDelays[delay]); + type_string += fmt::format(" Delay {} ", lift_delays[delay]); // Speed - type_string += Speeds[speed]; + type_string += speeds[speed]; } // Stairs type @@ -396,12 +447,12 @@ string parseLineType(int type) int speed = (type & StairSpeed) >> StairSpeedShift; // Trigger - type_string += Triggers[trigger]; + type_string += triggers[trigger]; if (type & StairMonster) type_string += "M"; // Direction, step height, speed - type_string += fmt::format(" Stairs {} {} {}", Directions[direction], Steps[step], Speeds[speed]); + type_string += fmt::format(" Stairs {} {} {}", directions[direction], steps[step], speeds[speed]); // Ignore if (type & StairIgnore) @@ -415,12 +466,12 @@ string parseLineType(int type) int speed = (type & CrusherSpeed) >> CrusherSpeedShift; // Trigger - type_string += Triggers[trigger]; + type_string += triggers[trigger]; if (type & CrusherMonster) type_string += "M"; // Speed - type_string += fmt::format(" Crusher {}", Speeds[speed]); + type_string += fmt::format(" Crusher {}", speeds[speed]); // Silent if (type & CrusherSilent) diff --git a/src/Game/MapInfo.cpp b/src/Game/MapInfo.cpp index 98c126e53..6944e7c9d 100644 --- a/src/Game/MapInfo.cpp +++ b/src/Game/MapInfo.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -32,8 +32,8 @@ #include "Main.h" #include "MapInfo.h" #include "Archive/Archive.h" -#include "UI/WxUtils.h" #include "Utility/StringUtils.h" +#include "Utility/Tokenizer.h" using namespace slade; using namespace game; @@ -76,7 +76,7 @@ MapInfo::Map& MapInfo::getMap(string_view name) // ----------------------------------------------------------------------------- // Adds [map] info, or updates the existing map info if it exists // ----------------------------------------------------------------------------- -bool MapInfo::addOrUpdateMap(Map& map) +bool MapInfo::addOrUpdateMap(const Map& map) { for (auto& m : maps_) if (m.entry_name == map.entry_name) @@ -92,7 +92,7 @@ bool MapInfo::addOrUpdateMap(Map& map) // ----------------------------------------------------------------------------- // Returns the DoomEdNum for the ZScript/DECORATE class [actor_class] // ----------------------------------------------------------------------------- -int MapInfo::doomEdNumForClass(string_view actor_class) +int MapInfo::doomEdNumForClass(string_view actor_class) const { // Find DoomEdNum def with matching class for (auto& i : editor_nums_) @@ -125,11 +125,10 @@ bool MapInfo::readMapInfo(const Archive& archive) switch (detectMapInfoType(entry.get())) { case Format::Hexen: - case Format::ZDoomOld: log::info("MAPINFO (Hexen/Old ZDoom) parsing not yet implemented"); break; - case Format::ZDoomNew: return parseZMapInfo(entry.get()); - case Format::Eternity: log::info("EMAPINFO parsing not yet implemented"); break; + case Format::ZDoomOld: log::info("MAPINFO (Hexen/Old ZDoom) parsing not yet implemented"); break; + case Format::ZDoomNew: return parseZMapInfo(entry.get()); + case Format::Eternity: log::info("EMAPINFO parsing not yet implemented"); break; case Format::Universal: log::info("UMAPINFO parsing not yet implemented"); break; - default: break; } } } @@ -144,7 +143,7 @@ bool MapInfo::checkEqualsToken(Tokenizer& tz, string_view parsing) const { if (tz.next() != "=") { - log::error("Error Parsing {}: Expected \"=\", got \"{}\" at line {}", parsing, tz.current().text, tz.lineNo()); + log::error(R"(Error Parsing {}: Expected "=", got "{}" at line {})", parsing, tz.current().text, tz.lineNo()); return false; } @@ -184,7 +183,7 @@ bool MapInfo::strToCol(const string& str, ColRGBA& col) const // ----------------------------------------------------------------------------- // Parses ZMAPINFO-format definitions in [entry] // ----------------------------------------------------------------------------- -bool MapInfo::parseZMapInfo(ArchiveEntry* entry) +bool MapInfo::parseZMapInfo(const ArchiveEntry* entry) { Tokenizer tz; tz.setReadLowerCase(true); @@ -530,7 +529,7 @@ bool MapInfo::parseDoomEdNums(Tokenizer& tz) // ----------------------------------------------------------------------------- // Attempts to detect the port-specific MAPINFO format of [entry] // ----------------------------------------------------------------------------- -MapInfo::Format MapInfo::detectMapInfoType(ArchiveEntry* entry) const +MapInfo::Format MapInfo::detectMapInfoType(const ArchiveEntry* entry) const { Tokenizer tz; tz.openMem(entry->data(), entry->name()); @@ -570,7 +569,7 @@ MapInfo::Format MapInfo::detectMapInfoType(ArchiveEntry* entry) const // ----------------------------------------------------------------------------- // Dumps all parsed DoomEdNums to the log // ----------------------------------------------------------------------------- -void MapInfo::dumpDoomEdNums() +void MapInfo::dumpDoomEdNums() const { for (auto& num : editor_nums_) { diff --git a/src/Game/MapInfo.h b/src/Game/MapInfo.h index 171751cae..b3555270c 100644 --- a/src/Game/MapInfo.h +++ b/src/Game/MapInfo.h @@ -1,10 +1,10 @@ #pragma once #include "Utility/Colour.h" -#include "Utility/Tokenizer.h" namespace slade { +class Tokenizer; class Archive; class ArchiveEntry; @@ -65,12 +65,12 @@ namespace game // Maps access const vector& maps() const { return maps_; } Map& getMap(string_view name); - bool addOrUpdateMap(Map& map); + bool addOrUpdateMap(const Map& map); // DoomEdNum access const DoomEdNumMap& doomEdNums() const { return editor_nums_; } DoomEdNum& doomEdNum(int number) { return editor_nums_[number]; } - int doomEdNumForClass(string_view actor_class); + int doomEdNumForClass(string_view actor_class) const; // MAPINFO loading bool readMapInfo(const Archive& archive); @@ -80,15 +80,15 @@ namespace game bool strToCol(const string& str, ColRGBA& col) const; // ZDoom MAPINFO parsing - bool parseZMapInfo(ArchiveEntry* entry); + bool parseZMapInfo(const ArchiveEntry* entry); bool parseZMap(Tokenizer& tz, string_view type); bool parseDoomEdNums(Tokenizer& tz); // General - Format detectMapInfoType(ArchiveEntry* entry) const; + Format detectMapInfoType(const ArchiveEntry* entry) const; // Debug info - void dumpDoomEdNums(); + void dumpDoomEdNums() const; private: vector maps_; diff --git a/src/Game/SpecialPreset.cpp b/src/Game/SpecialPreset.cpp index 6bfbc79fe..ac5009e3a 100644 --- a/src/Game/SpecialPreset.cpp +++ b/src/Game/SpecialPreset.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -33,6 +33,7 @@ #include "SpecialPreset.h" #include "App.h" #include "Utility/Parser.h" +#include "Utility/Property.h" #include "Utility/StringUtils.h" using namespace slade; @@ -59,7 +60,7 @@ vector custom_presets; // ----------------------------------------------------------------------------- // Reads a special preset definition from a parsed tree [node] // ----------------------------------------------------------------------------- -void SpecialPreset::parse(ParseTreeNode* node) +void SpecialPreset::parse(const ParseTreeNode* node) { name = node->name(); @@ -98,7 +99,7 @@ void SpecialPreset::parse(ParseTreeNode* node) // Writes the special preset to a new 'preset' ParseTreeNode under [parent] and // returns it // ----------------------------------------------------------------------------- -ParseTreeNode* SpecialPreset::write(ParseTreeNode* parent) +ParseTreeNode* SpecialPreset::write(ParseTreeNode* parent) const { auto node = new ParseTreeNode(parent, nullptr, nullptr, "preset"); node->setName(name); @@ -172,7 +173,7 @@ bool game::loadCustomSpecialPresets() auto child = node->childPTN(a); if (strutil::equalCI(child->type(), "preset")) { - custom_presets.push_back({}); + custom_presets.emplace_back(); custom_presets.back().parse(child); // Add 'Custom' to preset group diff --git a/src/Game/SpecialPreset.h b/src/Game/SpecialPreset.h index 2a5b81c60..567237b6e 100644 --- a/src/Game/SpecialPreset.h +++ b/src/Game/SpecialPreset.h @@ -14,8 +14,8 @@ namespace game int args[5] = { 0, 0, 0, 0, 0 }; vector flags; - void parse(ParseTreeNode* node); - ParseTreeNode* write(ParseTreeNode* parent); + void parse(const ParseTreeNode* node); + ParseTreeNode* write(ParseTreeNode* parent) const; }; const vector& customSpecialPresets(); diff --git a/src/Game/ThingType.cpp b/src/Game/ThingType.cpp index 53d9a7cba..e63bda715 100644 --- a/src/Game/ThingType.cpp +++ b/src/Game/ThingType.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -31,6 +31,7 @@ // ----------------------------------------------------------------------------- #include "Main.h" #include "ThingType.h" +#include "Game.h" #include "Game/Configuration.h" #include "Utility/Parser.h" #include "Utility/StringUtils.h" @@ -58,7 +59,10 @@ ThingType ThingType::unknown_; // ThingType class constructor // ----------------------------------------------------------------------------- ThingType::ThingType(string_view name, string_view group, string_view class_name) : - name_{ name }, group_{ group }, tagged_{ TagType::None }, class_name_{ class_name } + name_{ name }, + group_{ group }, + tagged_{ TagType::None }, + class_name_{ class_name } { } @@ -147,7 +151,7 @@ void ThingType::reset() // ----------------------------------------------------------------------------- // Reads an thing type definition from a parsed tree [node] // ----------------------------------------------------------------------------- -void ThingType::parse(ParseTreeNode* node) +void ThingType::parse(const ParseTreeNode* node) { // Go through all child nodes/values for (unsigned a = 0; a < node->nChildren(); a++) @@ -239,7 +243,7 @@ void ThingType::parse(ParseTreeNode* node) do { translation_ += child->stringValue(v++); - } while ((v < child->nValues()) && ((translation_ += "\", \""), true)); + } while ((v < child->nValues()) && (translation_ += "\", \"", true)); translation_ += "\""; } @@ -420,7 +424,7 @@ void ThingType::loadProps(PropertyList& props, bool decorate, bool zscript) { 0xDA, 0xA5, 0x20, 0xFF }, // Goldenrod ARGB value of #FFDAA520 }; - if (*color < (int)db2_colours.size()) + if (*color < static_cast(db2_colours.size())) colour_ = db2_colours[*color]; } @@ -447,7 +451,7 @@ void ThingType::loadProps(PropertyList& props, bool decorate, bool zscript) translation_ = *val; if (auto val = props.getIf("solid")) solid_ = *val; - if (auto val = props.getIf("obsolete")) + if (props.getIf("obsolete")) flags_ |= Obsolete; // ZScript-only props diff --git a/src/Game/ThingType.h b/src/Game/ThingType.h index 07b30799b..b77ce7643 100644 --- a/src/Game/ThingType.h +++ b/src/Game/ThingType.h @@ -66,7 +66,7 @@ namespace game void define(int number, string_view name, string_view group); void reset(); - void parse(ParseTreeNode* node); + void parse(const ParseTreeNode* node); string stringDesc() const; void loadProps(PropertyList& props, bool decorate = true, bool zscript = false); diff --git a/src/Game/UDMFProperty.cpp b/src/Game/UDMFProperty.cpp index f339b9962..fff8b2edd 100644 --- a/src/Game/UDMFProperty.cpp +++ b/src/Game/UDMFProperty.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -48,7 +48,7 @@ using namespace game; // ----------------------------------------------------------------------------- // Reads a UDMF property definition from a parsed tree [node] // ----------------------------------------------------------------------------- -void UDMFProperty::parse(ParseTreeNode* node, string_view group) +void UDMFProperty::parse(const ParseTreeNode* node, string_view group) { // Set group and property name group_ = group; @@ -107,18 +107,18 @@ void UDMFProperty::parse(ParseTreeNode* node, string_view group) { switch (type_) { - case Type::Boolean: default_value_ = prop->boolValue(); break; - case Type::Int: default_value_ = prop->intValue(); break; - case Type::Float: default_value_ = prop->floatValue(); break; - case Type::String: default_value_ = prop->stringValue(); break; + case Type::Boolean: default_value_ = prop->boolValue(); break; + case Type::Int: default_value_ = prop->intValue(); break; + case Type::Float: default_value_ = prop->floatValue(); break; + case Type::String: default_value_ = prop->stringValue(); break; case Type::ActionSpecial: default_value_ = prop->intValue(); break; case Type::SectorSpecial: default_value_ = prop->intValue(); break; - case Type::ThingType: default_value_ = prop->intValue(); break; - case Type::Angle: default_value_ = prop->intValue(); break; - case Type::TextureWall: default_value_ = prop->stringValue(); break; - case Type::TextureFlat: default_value_ = prop->stringValue(); break; - case Type::ID: default_value_ = prop->intValue(); break; - default: default_value_ = prop->stringValue(); break; + case Type::ThingType: default_value_ = prop->intValue(); break; + case Type::Angle: default_value_ = prop->intValue(); break; + case Type::TextureWall: default_value_ = prop->stringValue(); break; + case Type::TextureFlat: default_value_ = prop->stringValue(); break; + case Type::ID: default_value_ = prop->intValue(); break; + default: default_value_ = prop->stringValue(); break; } // Not sure why I have to do this here, but for whatever reason prop->getIntValue() doesn't work @@ -179,20 +179,20 @@ string UDMFProperty::getStringRep() switch (type_) { - case Type::Boolean: ret += ", type = bool"; break; - case Type::Int: ret += ", type = int"; break; - case Type::Float: ret += ", type = float"; break; - case Type::String: ret += ", type = string"; break; - case Type::Colour: ret += ", type = colour"; break; + case Type::Boolean: ret += ", type = bool"; break; + case Type::Int: ret += ", type = int"; break; + case Type::Float: ret += ", type = float"; break; + case Type::String: ret += ", type = string"; break; + case Type::Colour: ret += ", type = colour"; break; case Type::ActionSpecial: ret += ", type = actionspecial"; break; case Type::SectorSpecial: ret += ", type = sectorspecial"; break; - case Type::ThingType: ret += ", type = thingtype"; break; - case Type::Angle: ret += ", type = angle"; break; - case Type::TextureWall: ret += ", type = wall texture"; break; - case Type::TextureFlat: ret += ", type = flat texture"; break; - case Type::ID: ret += ", type = id"; break; - default: ret += ", ******unknown type********"; break; - }; + case Type::ThingType: ret += ", type = thingtype"; break; + case Type::Angle: ret += ", type = angle"; break; + case Type::TextureWall: ret += ", type = wall texture"; break; + case Type::TextureFlat: ret += ", type = flat texture"; break; + case Type::ID: ret += ", type = id"; break; + default: ret += ", ******unknown type********"; break; + } if (has_default_) { diff --git a/src/Game/UDMFProperty.h b/src/Game/UDMFProperty.h index 3d64d210e..3488f61d7 100644 --- a/src/Game/UDMFProperty.h +++ b/src/Game/UDMFProperty.h @@ -48,7 +48,7 @@ namespace game return has_default_ && property::value(default_value_) == value; } - void parse(ParseTreeNode* node, string_view group); + void parse(const ParseTreeNode* node, string_view group); string getStringRep(); diff --git a/src/Game/ZScript.cpp b/src/Game/ZScript.cpp index 9e2d6cbe9..2d7f454dc 100644 --- a/src/Game/ZScript.cpp +++ b/src/Game/ZScript.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -33,7 +33,7 @@ #include "ZScript.h" #include "App.h" #include "Archive/Archive.h" -#include "Archive/ArchiveManager.h" +#include "ThingType.h" #include "Utility/StringUtils.h" #include "Utility/Tokenizer.h" @@ -241,7 +241,7 @@ void parseBlocks(ArchiveEntry* entry, vector& parsed, vector last_qualifier + 2 && statement.tokens[index] == '(') + else if (static_cast(index) > last_qualifier + 2 && statement.tokens[index] == '(') { name_ = statement.tokens[index - 1]; return_type_ = statement.tokens[index - 2]; @@ -1176,7 +1176,7 @@ bool ParsedStatement::parse(Tokenizer& tz) return false; } - block.push_back({}); + block.emplace_back(); block.back().entry = entry; if (!block.back().parse(tz) || block.back().tokens.empty()) block.pop_back(); diff --git a/src/Game/ZScript.h b/src/Game/ZScript.h index d3ddfa8fc..7b438c9c8 100644 --- a/src/Game/ZScript.h +++ b/src/Game/ZScript.h @@ -1,6 +1,5 @@ #pragma once -#include "ThingType.h" #include "Utility/Property.h" namespace slade @@ -8,6 +7,10 @@ namespace slade class Archive; class ArchiveEntry; class Tokenizer; +namespace game +{ + class ThingType; +} namespace zscript { @@ -73,7 +76,9 @@ namespace zscript { public: Function(string_view name = {}, string_view def_class = {}) : - Identifier(name), return_type_{ "void" }, base_class_{ def_class } + Identifier(name), + return_type_{ "void" }, + base_class_{ def_class } { } @@ -84,7 +89,7 @@ namespace zscript string name; string type; string default_value; - Parameter() : name{ "" }, type{ "" }, default_value{ "" } {} + Parameter() : name{ "" }, type{ "" } {} unsigned parse(const vector& tokens, unsigned start_index); }; diff --git a/src/General/CVar.cpp b/src/General/CVar.cpp index 5e171446a..3f00dcb34 100644 --- a/src/General/CVar.cpp +++ b/src/General/CVar.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -61,7 +61,7 @@ namespace // ----------------------------------------------------------------------------- void addCVarList(CVar* cvar) { - cvars = (CVar**)realloc(cvars, (n_cvars + 1) * sizeof(CVar*)); + cvars = static_cast(realloc(cvars, (n_cvars + 1) * sizeof(CVar*))); cvars[n_cvars] = cvar; n_cvars++; } @@ -87,7 +87,8 @@ CIntCVar::CIntCVar(string_view name, int defval, uint16_t flags) : CVar{ Type::I // CBoolCVar class constructor // ----------------------------------------------------------------------------- CBoolCVar::CBoolCVar(string_view name, bool defval, uint16_t flags) : - CVar{ Type::Boolean, flags, name }, value{ defval } + CVar{ Type::Boolean, flags, name }, + value{ defval } { addCVarList(this); } @@ -96,7 +97,8 @@ CBoolCVar::CBoolCVar(string_view name, bool defval, uint16_t flags) : // CFloatCVar class constructor // ----------------------------------------------------------------------------- CFloatCVar::CFloatCVar(string_view name, double defval, uint16_t flags) : - CVar{ Type::Float, flags, name }, value{ defval } + CVar{ Type::Float, flags, name }, + value{ defval } { addCVarList(this); } @@ -105,7 +107,8 @@ CFloatCVar::CFloatCVar(string_view name, double defval, uint16_t flags) : // CStringCVar class constructor // ----------------------------------------------------------------------------- CStringCVar::CStringCVar(string_view name, string_view defval, uint16_t flags) : - CVar{ Type::String, flags, name }, value{ defval } + CVar{ Type::String, flags, name }, + value{ defval } { addCVarList(this); } @@ -166,7 +169,7 @@ string CVar::writeAll() } fmt::memory_buffer mem_buf; - auto buf = fmt::appender(mem_buf); + auto buf = fmt::appender(mem_buf); format_to(buf, "cvars\n{{\n"); for (auto* cvar : all_cvars) diff --git a/src/General/ColourConfiguration.cpp b/src/General/ColourConfiguration.cpp index 4bfbaf224..fb878356b 100644 --- a/src/General/ColourConfiguration.cpp +++ b/src/General/ColourConfiguration.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net diff --git a/src/General/Console.cpp b/src/General/Console.cpp index 8582e8876..dcd30e268 100644 --- a/src/General/Console.cpp +++ b/src/General/Console.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -33,7 +33,6 @@ #include "Console.h" #include "App.h" #include "General/CVar.h" -#include "MainEditor/MainEditor.h" #include "Utility/StringUtils.h" #include "Utility/Tokenizer.h" @@ -50,7 +49,7 @@ using namespace slade; // ----------------------------------------------------------------------------- // Adds a ConsoleCommand to the Console // ----------------------------------------------------------------------------- -void Console::addCommand(ConsoleCommand& c) +void Console::addCommand(const ConsoleCommand& c) { // Add the command to the list commands_.push_back(c); @@ -132,7 +131,7 @@ void Console::execute(string_view command) else if (cvar->type == CVar::Type::Float) value = fmt::format("{:1.4f}", cvar->getValue().Float); else - value = ((CStringCVar*)cvar)->value; + value = dynamic_cast(cvar)->value; log::console(fmt::format(R"("{}" = "{}")", cmd_name, value)); @@ -170,7 +169,7 @@ string Console::lastCommand() string Console::prevCommand(int index) { // Check index - if (index < 0 || (unsigned)index >= cmd_log_.size()) + if (index < 0 || static_cast(index) >= cmd_log_.size()) return ""; return cmd_log_[index]; @@ -200,9 +199,9 @@ ConsoleCommand& Console::command(size_t index) // ----------------------------------------------------------------------------- ConsoleCommand::ConsoleCommand( string_view name, - void (*command_func)(const vector&), - int min_args = 0, - bool show_in_list) + void (*command_func)(const vector&), + int min_args = 0, + bool show_in_list) { // Init variables name_ = name; diff --git a/src/General/Console.h b/src/General/Console.h index 2ca7c3848..ea3f7ce16 100644 --- a/src/General/Console.h +++ b/src/General/Console.h @@ -7,9 +7,9 @@ class ConsoleCommand public: ConsoleCommand( string_view name, - void (*command_func)(const vector&), - int min_args, - bool show_in_list = true); + void (*command_func)(const vector&), + int min_args, + bool show_in_list = true); ~ConsoleCommand() = default; string name() const { return name_; } @@ -17,12 +17,12 @@ class ConsoleCommand void execute(const vector& args) const; size_t minArgs() const { return min_args_; } - bool operator<(ConsoleCommand c) const { return name_ < c.name(); } - bool operator>(ConsoleCommand c) const { return name_ > c.name(); } + bool operator<(const ConsoleCommand& c) const { return name_ < c.name(); } + bool operator>(const ConsoleCommand& c) const { return name_ > c.name(); } private: string name_; - void (*command_func_)(const vector&); + void (*command_func_)(const vector&); size_t min_args_; bool show_in_list_; }; @@ -33,10 +33,10 @@ class Console Console() = default; ~Console() = default; - int numCommands() const { return (int)commands_.size(); } + int numCommands() const { return static_cast(commands_.size()); } ConsoleCommand& command(size_t index); - void addCommand(ConsoleCommand& c); + void addCommand(const ConsoleCommand& c); void execute(string_view command); string lastCommand(); string prevCommand(int index); diff --git a/src/General/Executables.cpp b/src/General/Executables.cpp index a9b46a35b..5dbaad617 100644 --- a/src/General/Executables.cpp +++ b/src/General/Executables.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -195,7 +195,7 @@ void executables::init() // ----------------------------------------------------------------------------- // Parses an executables configuration from [p] // ----------------------------------------------------------------------------- -void executables::parse(Parser* p, bool custom) +void executables::parse(const Parser* p, bool custom) { auto n = p->parseTreeRoot()->childPTN("executables"); if (!n) @@ -219,7 +219,7 @@ void executables::parse(Parser* p, bool custom) // ----------------------------------------------------------------------------- // Parses a game executable config from [node] // ----------------------------------------------------------------------------- -void executables::parseGameExe(ParseTreeNode* node, bool custom) +void executables::parseGameExe(const ParseTreeNode* node, bool custom) { // Get GameExe being parsed auto exe = gameExe(strutil::lower(node->name())); @@ -434,7 +434,7 @@ executables::ExternalExe executables::externalExe(string_view name, string_view if (exe.name == name) return exe; - return ExternalExe(); + return {}; } // ----------------------------------------------------------------------------- @@ -454,7 +454,7 @@ vector executables::externalExes(string_view category) // ----------------------------------------------------------------------------- // Parses an external executable config from [node] // ----------------------------------------------------------------------------- -void executables::parseExternalExe(ParseTreeNode* node) +void executables::parseExternalExe(const ParseTreeNode* node) { ExternalExe exe; exe.name = node->name(); diff --git a/src/General/Executables.h b/src/General/Executables.h index e61a21b29..fbc1af40d 100644 --- a/src/General/Executables.h +++ b/src/General/Executables.h @@ -32,14 +32,14 @@ namespace executables string writePaths(); string writeExecutables(); void init(); - void parse(Parser* p, bool custom); + void parse(const Parser* p, bool custom); // Game executables GameExe* gameExe(string_view id); GameExe* gameExe(unsigned index); unsigned nGameExes(); void setGameExePath(string_view id, string_view path); - void parseGameExe(ParseTreeNode* node, bool custom); + void parseGameExe(const ParseTreeNode* node, bool custom); void addGameExe(string_view name); bool removeGameExe(unsigned index); void addGameExeRunConfig( @@ -59,7 +59,7 @@ namespace executables int nExternalExes(string_view category = ""); ExternalExe externalExe(string_view name, string_view category = ""); vector externalExes(string_view category = ""); - void parseExternalExe(ParseTreeNode* node); + void parseExternalExe(const ParseTreeNode* node); void addExternalExe(string_view name, string_view path, string_view category); void setExternalExeName(string_view name_old, string_view name_new, string_view category); void setExternalExePath(string_view name, string_view path, string_view category); diff --git a/src/General/KeyBind.cpp b/src/General/KeyBind.cpp index f1f46bc2d..db8cbf90d 100644 --- a/src/General/KeyBind.cpp +++ b/src/General/KeyBind.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -66,7 +66,7 @@ string Keypress::asString() const if (key.empty()) return ""; - string ret = ""; + string ret; if (ctrl) ret += "Ctrl+"; if (alt) @@ -101,7 +101,7 @@ void KeyBind::addKey(string_view key, bool alt, bool ctrl, bool shift) // ----------------------------------------------------------------------------- // Returns a string representation of all the keys bound to this keybind // ----------------------------------------------------------------------------- -string KeyBind::keysAsString() +string KeyBind::keysAsString() const { string ret; @@ -154,7 +154,7 @@ KeyBind& KeyBind::bind(string_view name) // ----------------------------------------------------------------------------- // Returns a list of all keybind names bound to [key] // ----------------------------------------------------------------------------- -vector KeyBind::bindsForKey(Keypress key) +vector KeyBind::bindsForKey(const Keypress& key) { vector matches; @@ -250,103 +250,103 @@ string KeyBind::keyName(int key) // Return string representation of key id switch (key) { - case WXK_BACK: return "backspace"; - case WXK_TAB: return "tab"; - case WXK_RETURN: return "return"; - case WXK_ESCAPE: return "escape"; - case WXK_SPACE: return "space"; - case WXK_DELETE: return "delete"; - case WXK_CLEAR: return "clear"; - case WXK_SHIFT: return "shift"; - case WXK_ALT: return "alt"; - case WXK_PAUSE: return "pause"; - case WXK_END: return "end"; - case WXK_HOME: return "home"; - case WXK_LEFT: return "left"; - case WXK_UP: return "up"; - case WXK_RIGHT: return "right"; - case WXK_DOWN: return "down"; - case WXK_INSERT: return "insert"; - case WXK_NUMPAD0: return "num_0"; - case WXK_NUMPAD1: return "num_1"; - case WXK_NUMPAD2: return "num_2"; - case WXK_NUMPAD3: return "num_3"; - case WXK_NUMPAD4: return "num_4"; - case WXK_NUMPAD5: return "num_5"; - case WXK_NUMPAD6: return "num_6"; - case WXK_NUMPAD7: return "num_7"; - case WXK_NUMPAD8: return "num_8"; - case WXK_NUMPAD9: return "num_9"; - case WXK_ADD: return "plus"; - case WXK_SUBTRACT: return "minus"; - case WXK_F1: return "f1"; - case WXK_F2: return "f2"; - case WXK_F3: return "f3"; - case WXK_F4: return "f4"; - case WXK_F5: return "f5"; - case WXK_F6: return "f6"; - case WXK_F7: return "f7"; - case WXK_F8: return "f8"; - case WXK_F9: return "f9"; - case WXK_F10: return "f10"; - case WXK_F11: return "f11"; - case WXK_F12: return "f12"; - case WXK_F13: return "f13"; - case WXK_F14: return "f14"; - case WXK_F15: return "f15"; - case WXK_F16: return "f16"; - case WXK_F17: return "f17"; - case WXK_F18: return "f18"; - case WXK_F19: return "f19"; - case WXK_F20: return "f20"; - case WXK_F21: return "f21"; - case WXK_F22: return "f22"; - case WXK_F23: return "f23"; - case WXK_F24: return "f24"; - case WXK_NUMLOCK: return "numlock"; - case WXK_PAGEUP: return "pageup"; - case WXK_PAGEDOWN: return "pagedown"; - case WXK_NUMPAD_SPACE: return "num_space"; - case WXK_NUMPAD_TAB: return "num_tab"; - case WXK_NUMPAD_ENTER: return "num_enter"; - case WXK_NUMPAD_F1: return "num_f1"; - case WXK_NUMPAD_F2: return "num_f2"; - case WXK_NUMPAD_F3: return "num_f3"; - case WXK_NUMPAD_F4: return "num_f4"; - case WXK_NUMPAD_HOME: return "num_home"; - case WXK_NUMPAD_LEFT: return "num_left"; - case WXK_NUMPAD_UP: return "num_up"; - case WXK_NUMPAD_RIGHT: return "num_right"; - case WXK_NUMPAD_DOWN: return "num_down"; - case WXK_NUMPAD_PAGEUP: return "num_pageup"; - case WXK_NUMPAD_PAGEDOWN: return "num_pagedown"; - case WXK_NUMPAD_END: return "num_end"; - case WXK_NUMPAD_BEGIN: return "num_begin"; - case WXK_NUMPAD_INSERT: return "num_insert"; - case WXK_NUMPAD_DELETE: return "num_delete"; - case WXK_NUMPAD_EQUAL: return "num_equal"; - case WXK_NUMPAD_MULTIPLY: return "num_multiply"; - case WXK_NUMPAD_ADD: return "num_plus"; + case WXK_BACK: return "backspace"; + case WXK_TAB: return "tab"; + case WXK_RETURN: return "return"; + case WXK_ESCAPE: return "escape"; + case WXK_SPACE: return "space"; + case WXK_DELETE: return "delete"; + case WXK_CLEAR: return "clear"; + case WXK_SHIFT: return "shift"; + case WXK_ALT: return "alt"; + case WXK_PAUSE: return "pause"; + case WXK_END: return "end"; + case WXK_HOME: return "home"; + case WXK_LEFT: return "left"; + case WXK_UP: return "up"; + case WXK_RIGHT: return "right"; + case WXK_DOWN: return "down"; + case WXK_INSERT: return "insert"; + case WXK_NUMPAD0: return "num_0"; + case WXK_NUMPAD1: return "num_1"; + case WXK_NUMPAD2: return "num_2"; + case WXK_NUMPAD3: return "num_3"; + case WXK_NUMPAD4: return "num_4"; + case WXK_NUMPAD5: return "num_5"; + case WXK_NUMPAD6: return "num_6"; + case WXK_NUMPAD7: return "num_7"; + case WXK_NUMPAD8: return "num_8"; + case WXK_NUMPAD9: return "num_9"; + case WXK_ADD: return "plus"; + case WXK_SUBTRACT: return "minus"; + case WXK_F1: return "f1"; + case WXK_F2: return "f2"; + case WXK_F3: return "f3"; + case WXK_F4: return "f4"; + case WXK_F5: return "f5"; + case WXK_F6: return "f6"; + case WXK_F7: return "f7"; + case WXK_F8: return "f8"; + case WXK_F9: return "f9"; + case WXK_F10: return "f10"; + case WXK_F11: return "f11"; + case WXK_F12: return "f12"; + case WXK_F13: return "f13"; + case WXK_F14: return "f14"; + case WXK_F15: return "f15"; + case WXK_F16: return "f16"; + case WXK_F17: return "f17"; + case WXK_F18: return "f18"; + case WXK_F19: return "f19"; + case WXK_F20: return "f20"; + case WXK_F21: return "f21"; + case WXK_F22: return "f22"; + case WXK_F23: return "f23"; + case WXK_F24: return "f24"; + case WXK_NUMLOCK: return "numlock"; + case WXK_PAGEUP: return "pageup"; + case WXK_PAGEDOWN: return "pagedown"; + case WXK_NUMPAD_SPACE: return "num_space"; + case WXK_NUMPAD_TAB: return "num_tab"; + case WXK_NUMPAD_ENTER: return "num_enter"; + case WXK_NUMPAD_F1: return "num_f1"; + case WXK_NUMPAD_F2: return "num_f2"; + case WXK_NUMPAD_F3: return "num_f3"; + case WXK_NUMPAD_F4: return "num_f4"; + case WXK_NUMPAD_HOME: return "num_home"; + case WXK_NUMPAD_LEFT: return "num_left"; + case WXK_NUMPAD_UP: return "num_up"; + case WXK_NUMPAD_RIGHT: return "num_right"; + case WXK_NUMPAD_DOWN: return "num_down"; + case WXK_NUMPAD_PAGEUP: return "num_pageup"; + case WXK_NUMPAD_PAGEDOWN: return "num_pagedown"; + case WXK_NUMPAD_END: return "num_end"; + case WXK_NUMPAD_BEGIN: return "num_begin"; + case WXK_NUMPAD_INSERT: return "num_insert"; + case WXK_NUMPAD_DELETE: return "num_delete"; + case WXK_NUMPAD_EQUAL: return "num_equal"; + case WXK_NUMPAD_MULTIPLY: return "num_multiply"; + case WXK_NUMPAD_ADD: return "num_plus"; case WXK_NUMPAD_SEPARATOR: return "num_separator"; - case WXK_NUMPAD_SUBTRACT: return "num_minus"; - case WXK_NUMPAD_DECIMAL: return "num_decimal"; - case WXK_NUMPAD_DIVIDE: return "num_divide"; - case WXK_WINDOWS_LEFT: return "win_left"; - case WXK_WINDOWS_RIGHT: return "win_right"; - case WXK_WINDOWS_MENU: return "win_menu"; - case WXK_PRINT: return "printscrn"; + case WXK_NUMPAD_SUBTRACT: return "num_minus"; + case WXK_NUMPAD_DECIMAL: return "num_decimal"; + case WXK_NUMPAD_DIVIDE: return "num_divide"; + case WXK_WINDOWS_LEFT: return "win_left"; + case WXK_WINDOWS_RIGHT: return "win_right"; + case WXK_WINDOWS_MENU: return "win_menu"; + case WXK_PRINT: return "printscrn"; #ifdef __APPLE__ case WXK_COMMAND: return "command"; #else case WXK_CONTROL: return "control"; #endif case '\\': return "backslash"; - default: break; - }; + default: break; + } // Check for ascii character if (key > 32 && key < 128) - return { (char)key }; + return { static_cast(key) }; // Unknown character, just return "key##" return fmt::format("key{}", key); @@ -359,19 +359,19 @@ string KeyBind::mbName(int button) { switch (button) { - case wxMOUSE_BTN_LEFT: return "mouse1"; - case wxMOUSE_BTN_RIGHT: return "mouse2"; + case wxMOUSE_BTN_LEFT: return "mouse1"; + case wxMOUSE_BTN_RIGHT: return "mouse2"; case wxMOUSE_BTN_MIDDLE: return "mouse3"; - case wxMOUSE_BTN_AUX1: return "mouse4"; - case wxMOUSE_BTN_AUX2: return "mouse5"; - default: return fmt::format("mouse{}", button); - }; + case wxMOUSE_BTN_AUX1: return "mouse4"; + case wxMOUSE_BTN_AUX2: return "mouse5"; + default: return fmt::format("mouse{}", button); + } } // ----------------------------------------------------------------------------- // 'Presses' all keybinds bound to [key] // ----------------------------------------------------------------------------- -bool KeyBind::keyPressed(Keypress key) +bool KeyBind::keyPressed(const Keypress& key) { // Ignore raw modifier keys if (key.key == "control" || key.key == "shift" || key.key == "alt" || key.key == "command") @@ -465,11 +465,10 @@ void KeyBind::pressBind(string_view name) // ----------------------------------------------------------------------------- Keypress KeyBind::asKeyPress(int keycode, int modifiers) { - return Keypress( - keyName(keycode), - ((modifiers & wxMOD_ALT) != 0), - ((modifiers & wxMOD_CMD) != 0), - ((modifiers & wxMOD_SHIFT) != 0)); + return { keyName(keycode), + ((modifiers & wxMOD_ALT) != 0), + ((modifiers & wxMOD_CMD) != 0), + ((modifiers & wxMOD_SHIFT) != 0) }; } // ----------------------------------------------------------------------------- @@ -761,7 +760,7 @@ void KeyBind::initBinds() string KeyBind::writeBinds() { // Init string - string ret = ""; + string ret; // Go through all keybinds for (auto& kb : keybinds) diff --git a/src/General/KeyBind.h b/src/General/KeyBind.h index c1fca4a74..18ad38b8d 100644 --- a/src/General/KeyBind.h +++ b/src/General/KeyBind.h @@ -1,8 +1,11 @@ #pragma once -#define KPM_CTRL 0x01 -#define KPM_ALT 0x02 -#define KPM_SHIFT 0x04 +enum +{ + KPM_CTRL = 0x01, + KPM_ALT = 0x02, + KPM_SHIFT = 0x04 +}; namespace slade { @@ -39,7 +42,7 @@ class KeyBind ~KeyBind() = default; // Operators - bool operator>(const KeyBind r) const + bool operator>(const KeyBind& r) const { if (priority_ == r.priority_) return name_ < r.name_; @@ -47,7 +50,7 @@ class KeyBind return priority_ < r.priority_; } - bool operator<(const KeyBind r) const + bool operator<(const KeyBind& r) const { if (priority_ == r.priority_) return name_ > r.name_; @@ -60,13 +63,13 @@ class KeyBind string name() const { return name_; } string group() const { return group_; } string description() const { return description_; } - string keysAsString(); + string keysAsString() const; int nKeys() const { return keys_.size(); } Keypress key(unsigned index) { if (index >= keys_.size()) - return Keypress(); + return {}; else return keys_[index]; } @@ -75,7 +78,7 @@ class KeyBind // Static functions static KeyBind& bind(string_view name); - static vector bindsForKey(Keypress key); + static vector bindsForKey(const Keypress& key); static bool isPressed(string_view name); static bool addBind( string_view name, @@ -86,7 +89,7 @@ class KeyBind int priority = -1); static string keyName(int key); static string mbName(int button); - static bool keyPressed(Keypress key); + static bool keyPressed(const Keypress& key); static bool keyReleased(string_view key); static Keypress asKeyPress(int keycode, int modifiers); static void allKeyBinds(vector& list); diff --git a/src/General/Log.cpp b/src/General/Log.cpp index 8d39f6447..8bbc27576 100644 --- a/src/General/Log.cpp +++ b/src/General/Log.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -31,10 +31,16 @@ // ----------------------------------------------------------------------------- #include "Main.h" #include "App.h" +#include +#include #include #include #include +#ifndef _WIN32 +#undef _WINDOWS_ // Undefine _WINDOWS_ that has been defined by FreeImage +#endif + using namespace slade; @@ -54,25 +60,22 @@ CVAR(Int, log_verbosity, 1, CVar::Flag::Save) // ----------------------------------------------------------------------------- // Formatter for fmt so that log::MessageType can be written to a string // ----------------------------------------------------------------------------- -namespace fmt -{ -template<> struct formatter +template<> struct fmt::formatter { template constexpr auto parse(ParseContext& ctx) { return ctx.begin(); } template auto format(const log::MessageType& type, FormatContext& ctx) { switch (type) { - case log::MessageType::Info: return format_to(ctx.out(), " [Info]"); - case log::MessageType::Warning: return format_to(ctx.out(), " [Warn]"); - case log::MessageType::Error: return format_to(ctx.out(), "[Error]"); - case log::MessageType::Debug: return format_to(ctx.out(), "[Debug]"); - case log::MessageType::Script: return format_to(ctx.out(), "[Script]"); - default: return format_to(ctx.out(), " [Log]"); + case log::MessageType::Info: return format_to(ctx.out(), " [Info]"); + case log::MessageType::Warning: return format_to(ctx.out(), " [Warn]"); + case log::MessageType::Error: return format_to(ctx.out(), " [Error]"); + case log::MessageType::Debug: return format_to(ctx.out(), " [Debug]"); + case log::MessageType::Script: return format_to(ctx.out(), "[Script]"); + default: return format_to(ctx.out(), " [Log]"); } } -}; -} // namespace fmt +}; // namespace fmt // ----------------------------------------------------------------------------- @@ -136,7 +139,7 @@ void log::init() info(fmt::format("Version {}", app::version().toString())); if (!global::sc_rev.empty()) info(fmt::format("Git Revision {}", global::sc_rev)); - if (app::platform() == app::Platform::Windows) + if (app::platform() == app::Platform::Windows) info(fmt::format("{} Windows Build", app::isWin64Build() ? "64bit" : "32bit")); info(fmt::format("Written by Simon Judd, 2008-{:%Y}", *tm)); #ifdef SFML_VERSION_MAJOR @@ -192,7 +195,8 @@ void log::message(MessageType type, string_view text) log.emplace_back(text, type, *std::localtime(&t)); // Write to log file - if (log_file.is_open() && type != MessageType::Console) { + if (log_file.is_open() && type != MessageType::Console) + { sf::err() << log.back().formattedMessageLine() << "\n"; sf::err().flush(); } diff --git a/src/General/Log.h b/src/General/Log.h index 6d1e5cf2a..581d0ce6b 100644 --- a/src/General/Log.h +++ b/src/General/Log.h @@ -21,8 +21,10 @@ namespace log MessageType type; std::tm timestamp; - Message(string_view message, MessageType type, std::tm timestamp) : - message{ message.data(), message.size() }, type{ type }, timestamp{ timestamp } + Message(string_view message, MessageType type, const std::tm& timestamp) : + message{ message.data(), message.size() }, + type{ type }, + timestamp{ timestamp } { } @@ -43,14 +45,32 @@ namespace log // Message shortcuts by type // ----------------------------------------------------------------------------- - inline void info(int level, const wxString& text) { message(MessageType::Info, level, text.ToStdString()); } - inline void info(const wxString& text) { message(MessageType::Info, text.ToStdString()); } + inline void info(int level, const wxString& text) + { + message(MessageType::Info, level, text.ToStdString()); + } + inline void info(const wxString& text) + { + message(MessageType::Info, text.ToStdString()); + } - inline void warning(int level, const wxString& text) { message(MessageType::Warning, level, text.ToStdString()); } - inline void warning(const wxString& text) { message(MessageType::Warning, text.ToStdString()); } + inline void warning(int level, const wxString& text) + { + message(MessageType::Warning, level, text.ToStdString()); + } + inline void warning(const wxString& text) + { + message(MessageType::Warning, text.ToStdString()); + } - inline void error(int level, const wxString& text) { message(MessageType::Error, level, text.ToStdString()); } - inline void error(const wxString& text) { message(MessageType::Error, text.ToStdString()); } + inline void error(int level, const wxString& text) + { + message(MessageType::Error, level, text.ToStdString()); + } + inline void error(const wxString& text) + { + message(MessageType::Error, text.ToStdString()); + } // These can't be inline, need access to Global::debug void debug(int level, const wxString& text); @@ -58,7 +78,10 @@ namespace log void debug(int level, string_view text, fmt::format_args args); void debug(string_view text, fmt::format_args args); - inline void console(const wxString& text) { message(MessageType::Console, text.ToStdString()); } + inline void console(const wxString& text) + { + message(MessageType::Console, text.ToStdString()); + } // Message shortcuts by type with args for fmt::format @@ -109,13 +132,12 @@ namespace log // disabled, but it's also the only macro cmake defines differently between // debug and release builds, so we co-opt it just for this. #ifndef NDEBUG -#include class Debuggable { wxString repr; public: - Debuggable(wxString v) { repr = v; } + Debuggable(const wxString& v) { repr = v; } Debuggable(const char* v) { repr = v; } Debuggable(bool v) { repr = v ? "true" : "false"; } Debuggable(int v) { repr = wxString::Format("%d", v); } @@ -124,9 +146,12 @@ class Debuggable Debuggable(unsigned long v) { repr = wxString::Format("%lu", v); } Debuggable(double v) { repr = wxString::Format("%g", v); } - Debuggable(Vec2d v) { repr = wxString::Format("(%0.6f, %0.6f)", v.x, v.y); } - Debuggable(Vec3f v) { repr = wxString::Format("(%0.6f, %0.6f, %0.6f)", v.x, v.y, v.z); } - Debuggable(Rectf v) { repr = wxString::Format("(%0.6f, %0.6f to %0.6f, %0.6f)", v.x1(), v.y1(), v.x2(), v.y2()); } + Debuggable(const Vec2d& v) { repr = wxString::Format("(%0.6f, %0.6f)", v.x, v.y); } + Debuggable(const Vec3f& v) { repr = wxString::Format("(%0.6f, %0.6f, %0.6f)", v.x, v.y, v.z); } + Debuggable(const Rectf& v) + { + repr = wxString::Format("(%0.6f, %0.6f to %0.6f, %0.6f)", v.x1(), v.y1(), v.x2(), v.y2()); + } template Debuggable(T* v) { repr = Debuggable(*v).repr; } diff --git a/src/General/Misc.cpp b/src/General/Misc.cpp index 272f0c5e3..053c22f28 100644 --- a/src/General/Misc.cpp +++ b/src/General/Misc.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -153,7 +153,7 @@ bool misc::loadImageFromEntry(SImage* image, ArchiveEntry* entry, int index) // Detects the few known cases where a picture does not use PLAYPAL as its // default palette. // ----------------------------------------------------------------------------- -int misc::detectPaletteHack(ArchiveEntry* entry) +int misc::detectPaletteHack(const ArchiveEntry* entry) { if (entry == nullptr || entry->type() == nullptr) return palhack::NONE; @@ -299,12 +299,12 @@ string misc::sizeAsString(uint32_t size) } else if (size < 1024 * 1024) { - double kb = (double)size / 1024; + double kb = static_cast(size) / 1024; return fmt::format("{:1.2f}kb", kb); } else { - double mb = (double)size / (1024 * 1024); + double mb = static_cast(size) / (1024 * 1024); return fmt::format("{:1.2f}mb", mb); } } @@ -376,7 +376,7 @@ string misc::fileNameToLumpName(string_view file) // ----------------------------------------------------------------------------- // Creates a mass rename filter string from [names] // ----------------------------------------------------------------------------- -string misc::massRenameFilter(vector& names) +string misc::massRenameFilter(const vector& names) { // Check any names were given if (names.empty()) @@ -457,14 +457,14 @@ uint32_t crc_table[256]; int crc_table_computed = 0; /* Make the table for a fast CRC. */ -void make_crc_table(void) +void make_crc_table() { uint32_t c; int n, k; for (n = 0; n < 256; n++) { - c = (uint32_t)n; + c = static_cast(n); for (k = 0; k < 8; k++) { @@ -509,7 +509,7 @@ uint32_t misc::crc(const uint8_t* buf, uint32_t len) // the dimensions. // In case the texture is not found, the dimensions returned are null // ----------------------------------------------------------------------------- -Vec2i misc::findJaguarTextureDimensions(ArchiveEntry* entry, string_view name) +Vec2i misc::findJaguarTextureDimensions(const ArchiveEntry* entry, string_view name) { Vec2i dimensions; dimensions.x = 0; diff --git a/src/General/Misc.h b/src/General/Misc.h index cafb7ba1c..c9402ac2c 100644 --- a/src/General/Misc.h +++ b/src/General/Misc.h @@ -15,29 +15,29 @@ namespace misc // Palette detection namespace palhack { - static const int NONE = 0; - static const int ALPHA = 1; - static const int HERETIC = 2; - static const int SHADOW = 3; - static const int ROTT_N = 4; - static const int ROTT_D = 5; - static const int ROTT_F = 6; - static const int ROTT_A = 7; - static const int SOD_ID = 8; - static const int SOD_TITLE = 9; - static const int SOD_END = 10; - }; // namespace palhack - int detectPaletteHack(ArchiveEntry* entry); + static constexpr int NONE = 0; + static constexpr int ALPHA = 1; + static constexpr int HERETIC = 2; + static constexpr int SHADOW = 3; + static constexpr int ROTT_N = 4; + static constexpr int ROTT_D = 5; + static constexpr int ROTT_F = 6; + static constexpr int ROTT_A = 7; + static constexpr int SOD_ID = 8; + static constexpr int SOD_TITLE = 9; + static constexpr int SOD_END = 10; + } // namespace palhack + int detectPaletteHack(const ArchiveEntry* entry); bool loadPaletteFromArchive(Palette* pal, Archive* archive, int lump = palhack::NONE); string sizeAsString(uint32_t size); string lumpNameToFileName(string_view lump); string fileNameToLumpName(string_view file); uint32_t crc(const uint8_t* buf, uint32_t len); - Vec2i findJaguarTextureDimensions(ArchiveEntry* entry, string_view name); + Vec2i findJaguarTextureDimensions(const ArchiveEntry* entry, string_view name); // Mass Rename - string massRenameFilter(vector& names); + string massRenameFilter(const vector& names); void doMassRename(vector& names, string_view name_filter); // Dialog/Window sizes diff --git a/src/General/ResourceManager.cpp b/src/General/ResourceManager.cpp index 49cb4a3e8..1e7cf9c16 100644 --- a/src/General/ResourceManager.cpp +++ b/src/General/ResourceManager.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -37,6 +37,7 @@ #include "Archive/ArchiveManager.h" #include "General/Console.h" #include "Graphics/CTexture/CTexture.h" +#include "Graphics/CTexture/PatchTable.h" #include "Graphics/CTexture/TextureXList.h" #include "Utility/StringUtils.h" @@ -207,7 +208,7 @@ ArchiveEntry* EntryResource::getEntry(const Archive* priority, string_view nspac // ----------------------------------------------------------------------------- // Adds a texture to this resource // ----------------------------------------------------------------------------- -void TextureResource::add(CTexture* tex, Archive* parent) +void TextureResource::add(CTexture* tex, const Archive* parent) { // Check args auto parent_shared = app::archiveManager().shareArchive(parent); @@ -803,7 +804,6 @@ CONSOLE_COMMAND(list_res_patches, 0, false) app::resources().listAllPatches(); } -#include "App.h" CONSOLE_COMMAND(test_res_speed, 0, false) { vector list; @@ -830,5 +830,5 @@ CONSOLE_COMMAND(test_res_speed, 0, false) } float avg = static_cast(times[0] + times[1] + times[2] + times[3] + times[4]) / 5.0f; - log::console(fmt::format("Test took {}ms avg", (int)avg)); + log::console(fmt::format("Test took {}ms avg", static_cast(avg))); } diff --git a/src/General/ResourceManager.h b/src/General/ResourceManager.h index a973d6941..f7232f963 100644 --- a/src/General/ResourceManager.h +++ b/src/General/ResourceManager.h @@ -1,10 +1,11 @@ #pragma once -#include "Archive/Archive.h" #include "Graphics/CTexture/CTexture.h" namespace slade { +class Archive; +class ArchiveEntry; class ResourceManager; // This base class is probably not really needed @@ -61,7 +62,7 @@ class TextureResource : public Resource TextureResource() : Resource("texture") {} ~TextureResource() override = default; - void add(CTexture* tex, Archive* parent); + void add(CTexture* tex, const Archive* parent); void remove(const Archive* parent); int length() const override { return textures_.size(); } diff --git a/src/General/SAction.cpp b/src/General/SAction.cpp index 3dc0b4e3f..8a5f08383 100644 --- a/src/General/SAction.cpp +++ b/src/General/SAction.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -108,10 +108,10 @@ string SAction::shortcutText() const } // ----------------------------------------------------------------------------- -// Sets the toggled state of the action to [toggle], and updates the value of +// Sets the toggled state of the action to [checked], and updates the value of // the linked cvar (if any) to match // ----------------------------------------------------------------------------- -void SAction::setChecked(bool toggle) +void SAction::setChecked(bool checked) { if (type_ == Type::Normal) { @@ -120,7 +120,7 @@ void SAction::setChecked(bool toggle) } // If toggling a radio action, un-toggle others in the group - if (toggle && type_ == Type::Radio && group_ >= 0) + if (checked && type_ == Type::Radio && group_ >= 0) { // Go through and toggle off all other actions in the same group for (auto& action : actions_) @@ -132,7 +132,7 @@ void SAction::setChecked(bool toggle) checked_ = true; } else - checked_ = toggle; // Otherwise just set toggled state + checked_ = checked; // Otherwise just set toggled state // Update linked CVar if (linked_cvar_) diff --git a/src/General/UI.cpp b/src/General/UI.cpp index 954ceed20..2f9c25d99 100644 --- a/src/General/UI.cpp +++ b/src/General/UI.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -197,14 +197,14 @@ void ui::setCursor(wxWindow* window, MouseCursor cursor) { switch (cursor) { - case MouseCursor::Hand: window->SetCursor(wxCursor(wxCURSOR_HAND)); break; - case MouseCursor::Move: window->SetCursor(wxCursor(wxCURSOR_SIZING)); break; - case MouseCursor::Cross: window->SetCursor(wxCursor(wxCURSOR_CROSS)); break; - case MouseCursor::SizeNS: window->SetCursor(wxCursor(wxCURSOR_SIZENS)); break; - case MouseCursor::SizeWE: window->SetCursor(wxCursor(wxCURSOR_SIZEWE)); break; + case MouseCursor::Hand: window->SetCursor(wxCursor(wxCURSOR_HAND)); break; + case MouseCursor::Move: window->SetCursor(wxCursor(wxCURSOR_SIZING)); break; + case MouseCursor::Cross: window->SetCursor(wxCursor(wxCURSOR_CROSS)); break; + case MouseCursor::SizeNS: window->SetCursor(wxCursor(wxCURSOR_SIZENS)); break; + case MouseCursor::SizeWE: window->SetCursor(wxCursor(wxCURSOR_SIZEWE)); break; case MouseCursor::SizeNESW: window->SetCursor(wxCursor(wxCURSOR_SIZENESW)); break; case MouseCursor::SizeNWSE: window->SetCursor(wxCursor(wxCURSOR_SIZENWSE)); break; - default: window->SetCursor(wxNullCursor); + default: window->SetCursor(wxNullCursor); } } @@ -225,13 +225,14 @@ int ui::px(Size size) { switch (size) { - case Size::PadLarge: return px_pad; - case Size::Pad: return px_pad_small; - case Size::PadMinimum: return px_pad_min; - case Size::Splitter: return px_splitter; + case Size::PadLarge: return px_pad; + case Size::Pad: return px_pad_small; + case Size::PadMinimum: return px_pad_min; + case Size::Splitter: return px_splitter; case Size::SpinCtrlWidth: return px_spin_width; - default: return 0; } + + return 0; } // ----------------------------------------------------------------------------- diff --git a/src/General/UndoRedo.cpp b/src/General/UndoRedo.cpp index 3ed3ae1e3..829d209b4 100644 --- a/src/General/UndoRedo.cpp +++ b/src/General/UndoRedo.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -75,11 +75,11 @@ string UndoLevel::timeStamp(bool date, bool time) const // ----------------------------------------------------------------------------- // Performs all undo steps for this level // ----------------------------------------------------------------------------- -bool UndoLevel::doUndo() +bool UndoLevel::doUndo() const { log::info(3, "Performing undo \"{}\" ({} steps)", name_, undo_steps_.size()); bool ok = true; - for (int a = (int)undo_steps_.size() - 1; a >= 0; a--) + for (int a = static_cast(undo_steps_.size()) - 1; a >= 0; a--) { if (!undo_steps_[a]->doUndo()) ok = false; @@ -91,7 +91,7 @@ bool UndoLevel::doUndo() // ----------------------------------------------------------------------------- // Performs all redo steps for this level // ----------------------------------------------------------------------------- -bool UndoLevel::doRedo() +bool UndoLevel::doRedo() const { log::info(3, "Performing redo \"{}\" ({} steps)", name_, undo_steps_.size()); bool ok = true; @@ -123,7 +123,7 @@ bool UndoLevel::writeFile(string_view filename) const // ----------------------------------------------------------------------------- // Adds all undo steps from all undo levels in [levels] // ----------------------------------------------------------------------------- -void UndoLevel::createMerged(vector>& levels) +void UndoLevel::createMerged(const vector>& levels) { for (auto& level : levels) { @@ -183,7 +183,7 @@ void UndoManager::endRecord(bool success) } // Remove any undo levels after the current - while ((int)undo_levels_.size() - 1 > current_level_index_) + while (static_cast(undo_levels_.size()) - 1 > current_level_index_) { // log::info(1, "Removing undo level \"%s\"", undo_levels.back()->getName()); undo_levels_.pop_back(); @@ -266,7 +266,7 @@ string UndoManager::redo() return ""; // Can't if no more levels to redo - if (current_level_index_ == (int)undo_levels_.size() - 1 || undo_levels_.empty()) + if (current_level_index_ == static_cast(undo_levels_.size()) - 1 || undo_levels_.empty()) return ""; // Perform redo level @@ -286,7 +286,7 @@ string UndoManager::redo() // ----------------------------------------------------------------------------- // Adds all undo level names to [list] // ----------------------------------------------------------------------------- -void UndoManager::putAllLevels(vector& list) +void UndoManager::putAllLevels(vector& list) const { for (auto& undo_level : undo_levels_) list.push_back(undo_level->name()); diff --git a/src/General/UndoRedo.h b/src/General/UndoRedo.h index 9bdfda277..06c43b5d3 100644 --- a/src/General/UndoRedo.h +++ b/src/General/UndoRedo.h @@ -22,14 +22,14 @@ class UndoLevel ~UndoLevel() = default; string name() const { return name_; } - bool doUndo(); - bool doRedo(); + bool doUndo() const; + bool doRedo() const; void addStep(unique_ptr step) { undo_steps_.push_back(std::move(step)); } string timeStamp(bool date, bool time) const; bool writeFile(string_view filename) const; bool readFile(string_view filename) const; - void createMerged(vector>& levels); + void createMerged(const vector>& levels); private: string name_; @@ -45,7 +45,7 @@ class UndoManager ~UndoManager() = default; SLADEMap* map() const { return map_; } - void putAllLevels(vector& list); + void putAllLevels(vector& list) const; int currentIndex() const { return current_level_index_; } unsigned nUndoLevels() const { return undo_levels_.size(); } UndoLevel* undoLevel(unsigned index) const { return undo_levels_[index].get(); } diff --git a/src/General/Web.cpp b/src/General/Web.cpp index f5129a3c2..817cddeb0 100644 --- a/src/General/Web.cpp +++ b/src/General/Web.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net diff --git a/src/Graphics/CTexture/CTexture.cpp b/src/Graphics/CTexture/CTexture.cpp index 7e5129f4e..9cc28b509 100644 --- a/src/Graphics/CTexture/CTexture.cpp +++ b/src/Graphics/CTexture/CTexture.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -33,6 +33,7 @@ #include "Main.h" #include "CTexture.h" #include "App.h" +#include "Archive/ArchiveEntry.h" #include "General/Misc.h" #include "General/ResourceManager.h" #include "Graphics/SImage/SImage.h" @@ -88,7 +89,8 @@ ArchiveEntry* CTPatch::patchEntry(Archive* parent) // CTPatchEx class constructor w/basic initial values // ----------------------------------------------------------------------------- CTPatchEx::CTPatchEx(string_view name, int16_t offset_x, int16_t offset_y, Type type) : - CTPatch{ name, offset_x, offset_y }, type_{ type } + CTPatch{ name, offset_x, offset_y }, + type_{ type } { } diff --git a/src/Graphics/CTexture/CTexture.h b/src/Graphics/CTexture/CTexture.h index eee73472f..d36da8e0c 100644 --- a/src/Graphics/CTexture/CTexture.h +++ b/src/Graphics/CTexture/CTexture.h @@ -1,10 +1,11 @@ #pragma once -#include "Archive/ArchiveEntry.h" #include "Graphics/Translation.h" namespace slade { +class Archive; +class ArchiveEntry; class SImage; class Tokenizer; diff --git a/src/Graphics/CTexture/PatchTable.cpp b/src/Graphics/CTexture/PatchTable.cpp index 39f56bc4d..59cc872ba 100644 --- a/src/Graphics/CTexture/PatchTable.cpp +++ b/src/Graphics/CTexture/PatchTable.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -33,6 +33,7 @@ #include "Main.h" #include "PatchTable.h" #include "App.h" +#include "Archive/ArchiveEntry.h" #include "CTexture.h" #include "General/ResourceManager.h" #include "Utility/StringUtils.h" @@ -93,7 +94,7 @@ const string& PatchTable::patchName(size_t index) const // Returns the entry associated with the patch at [index], or null if [index] is // invalid // ----------------------------------------------------------------------------- -ArchiveEntry* PatchTable::patchEntry(size_t index) +ArchiveEntry* PatchTable::patchEntry(size_t index) const { // Check index if (index >= patches_.size()) @@ -111,7 +112,7 @@ ArchiveEntry* PatchTable::patchEntry(size_t index) // Returns the entry associated with the patch matching [name], or null if no // match found // ----------------------------------------------------------------------------- -ArchiveEntry* PatchTable::patchEntry(string_view name) +ArchiveEntry* PatchTable::patchEntry(string_view name) const { // Search for patch by name for (size_t a = 0; a < patches_.size(); a++) @@ -144,7 +145,7 @@ int32_t PatchTable::patchIndex(string_view name) const // Returns the index of the patch associated with [entry], or null if no match // found // ----------------------------------------------------------------------------- -int32_t PatchTable::patchIndex(ArchiveEntry* entry) const +int32_t PatchTable::patchIndex(const ArchiveEntry* entry) const { // Search for patch by entry for (size_t a = 0; a < patches_.size(); a++) @@ -224,7 +225,7 @@ bool PatchTable::addPatch(string_view name, bool allow_dup) // ----------------------------------------------------------------------------- // Loads a PNAMES entry, returns true on success, false otherwise // ----------------------------------------------------------------------------- -bool PatchTable::loadPNAMES(ArchiveEntry* pnames, Archive* parent) +bool PatchTable::loadPNAMES(const ArchiveEntry* pnames, Archive* parent) { // Check entry was given if (!pnames) @@ -280,7 +281,7 @@ bool PatchTable::loadPNAMES(ArchiveEntry* pnames, Archive* parent) // Writes the patch table to the entry [pnames]. // Returns false if no entry was given, true otherwise // ----------------------------------------------------------------------------- -bool PatchTable::writePNAMES(ArchiveEntry* pnames) +bool PatchTable::writePNAMES(ArchiveEntry* pnames) const { // Check entry was given if (!pnames) @@ -329,7 +330,7 @@ void PatchTable::clearPatchUsage() // ----------------------------------------------------------------------------- // Updates patch usage data for [tex] // ----------------------------------------------------------------------------- -void PatchTable::updatePatchUsage(CTexture* tex) +void PatchTable::updatePatchUsage(const CTexture* tex) { // Remove texture from all patch usage tables for (auto& patch : patches_) diff --git a/src/Graphics/CTexture/PatchTable.h b/src/Graphics/CTexture/PatchTable.h index 79c3a3986..f002e6902 100644 --- a/src/Graphics/CTexture/PatchTable.h +++ b/src/Graphics/CTexture/PatchTable.h @@ -1,9 +1,9 @@ #pragma once -#include "Archive/ArchiveEntry.h" - namespace slade { +class ArchiveEntry; +class Archive; class CTexture; class PatchTable @@ -40,19 +40,19 @@ class PatchTable Patch& patch(size_t index); Patch& patch(string_view name); const string& patchName(size_t index) const; - ArchiveEntry* patchEntry(size_t index); - ArchiveEntry* patchEntry(string_view name); + ArchiveEntry* patchEntry(size_t index) const; + ArchiveEntry* patchEntry(string_view name) const; int32_t patchIndex(string_view name) const; - int32_t patchIndex(ArchiveEntry* entry) const; + int32_t patchIndex(const ArchiveEntry* entry) const; bool removePatch(unsigned index); bool replacePatch(unsigned index, string_view newname); bool addPatch(string_view name, bool allow_dup = false); - bool loadPNAMES(ArchiveEntry* pnames, Archive* parent = nullptr); - bool writePNAMES(ArchiveEntry* pnames); + bool loadPNAMES(const ArchiveEntry* pnames, Archive* parent = nullptr); + bool writePNAMES(ArchiveEntry* pnames) const; void clearPatchUsage(); - void updatePatchUsage(CTexture* tex); + void updatePatchUsage(const CTexture* tex); // Signals struct Signals diff --git a/src/Graphics/CTexture/TextureXList.cpp b/src/Graphics/CTexture/TextureXList.cpp index a7637826c..de7314ab7 100644 --- a/src/Graphics/CTexture/TextureXList.cpp +++ b/src/Graphics/CTexture/TextureXList.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -31,11 +31,12 @@ // // ----------------------------------------------------------------------------- #include "Main.h" -#include "TextureXList.h" + #include "Archive/Archive.h" -#include "Archive/ArchiveManager.h" #include "Graphics/SImage/SImage.h" #include "MainEditor/MainEditor.h" +#include "PatchTable.h" +#include "TextureXList.h" #include "Utility/StringUtils.h" #include "Utility/Tokenizer.h" @@ -173,7 +174,7 @@ void TextureXList::addTexture(unique_ptr tex, int position) { // Add it to the list at position if valid tex->in_list_ = this; - if (position >= 0 && (unsigned)position < textures_.size()) + if (position >= 0 && static_cast(position) < textures_.size()) { tex->index_ = position; textures_.insert(textures_.begin() + position, std::move(tex)); @@ -258,7 +259,7 @@ void TextureXList::removePatch(string_view patch) const // Reads in a doom-format TEXTUREx entry. // Returns true on success, false otherwise // ----------------------------------------------------------------------------- -bool TextureXList::readTEXTUREXData(ArchiveEntry* texturex, const PatchTable& patch_table, bool add) +bool TextureXList::readTEXTUREXData(const ArchiveEntry* texturex, const PatchTable& patch_table, bool add) { // Check entries were actually given if (!texturex) @@ -517,11 +518,10 @@ bool TextureXList::writeTEXTUREXData(ArchiveEntry* texturex, const PatchTable& p } log::info("{} patch references in {} textures", numpatchrefs, numtextures); - size_t datasize = 0; - size_t headersize = 4 + (4 * numtextures); + size_t datasize; switch (txformat_) { - case Format::Normal: datasize = 4 + (26 * numtextures) + (10 * numpatchrefs); break; + case Format::Normal: datasize = 4 + (26 * numtextures) + (10 * numpatchrefs); break; case Format::Nameless: datasize = 4 + (18 * numtextures) + (10 * numpatchrefs); break; case Format::Strife11: datasize = 4 + (22 * numtextures) + (6 * numpatchrefs); @@ -532,7 +532,7 @@ bool TextureXList::writeTEXTUREXData(ArchiveEntry* texturex, const PatchTable& p MemChunk txdata(datasize); vector offsets(numtextures); - int32_t foo = wxINT32_SWAP_ON_BE((signed)numtextures); + int32_t foo = wxINT32_SWAP_ON_BE(static_cast(numtextures)); // Write header txdata.seek(0, SEEK_SET); @@ -548,7 +548,7 @@ bool TextureXList::writeTEXTUREXData(ArchiveEntry* texturex, const PatchTable& p auto tex = textures_[i].get(); // Set offset - offsets[i] = (signed)txdata.currentPos(); + offsets[i] = static_cast(txdata.currentPos()); // Write texture entry switch (txformat_) @@ -677,7 +677,7 @@ bool TextureXList::writeTEXTUREXData(ArchiveEntry* texturex, const PatchTable& p // Reads in a ZDoom-format TEXTURES entry. // Returns true on success, false otherwise // ----------------------------------------------------------------------------- -bool TextureXList::readTEXTURESData(ArchiveEntry* textures) +bool TextureXList::readTEXTURESData(const ArchiveEntry* textures) { // Check for empty entry if (!textures) @@ -786,11 +786,11 @@ string TextureXList::textureXFormatString() const { switch (txformat_) { - case Format::Normal: return "Doom TEXTUREx"; + case Format::Normal: return "Doom TEXTUREx"; case Format::Strife11: return "Strife TEXTUREx"; case Format::Nameless: return "Nameless (Doom Alpha)"; case Format::Textures: return "ZDoom TEXTURES"; - default: return "Unknown"; + default: return "Unknown"; } } @@ -889,7 +889,7 @@ bool TextureXList::removeDupesFoundIn(TextureXList& texture_list) for (unsigned a = 0; a < textures_.size(); a++) { - CTexture* this_texture = textures_[a].get(); + CTexture* this_texture = textures_[a].get(); int other_texture_index = texture_list.textureIndex(this_texture->name()); if (other_texture_index < 0) @@ -1136,7 +1136,7 @@ bool TextureXList::cleanTEXTURESsinglePatch(Archive* current_archive) { CTexture* texture = a.get(); - for (int p = 0; p < texture->nPatches(); p++) + for (int p = 0; p < static_cast(texture->nPatches()); p++) { ArchiveEntry* patch_entry = texture->patches()[p]->patchEntry(nullptr); @@ -1178,16 +1178,16 @@ bool TextureXList::cleanTEXTURESsinglePatch(Archive* current_archive) for (auto iter : single_patch_textures) { ArchiveEntry* patch_entry = iter.first; - CTexture* texture = textures_[iter.second].get(); + CTexture* texture = textures_[iter.second].get(); indices_to_remove.push_back(iter.second); // Currently only supporting converting patch to texture in archives that support directories so just move // things from patches to textures string::size_type patch_extension_pos = patch_entry->name().find_last_of('.'); - string patch_extension = patch_extension_pos != string::npos ? - patch_entry->name().substr(patch_extension_pos, patch_entry->name().size()) : - ""; + string patch_extension = patch_extension_pos != string::npos ? + patch_entry->name().substr(patch_extension_pos, patch_entry->name().size()) : + ""; string texture_file_name = texture->name(); texture_file_name.append(patch_extension); diff --git a/src/Graphics/CTexture/TextureXList.h b/src/Graphics/CTexture/TextureXList.h index ee983cc15..4b68b9c03 100644 --- a/src/Graphics/CTexture/TextureXList.h +++ b/src/Graphics/CTexture/TextureXList.h @@ -1,11 +1,10 @@ #pragma once -#include "Archive/ArchiveEntry.h" #include "CTexture.h" -#include "PatchTable.h" namespace slade { +class PatchTable; class TextureXList { public: @@ -55,10 +54,10 @@ class TextureXList void clear(bool clear_patches = false); void removePatch(string_view patch) const; - bool readTEXTUREXData(ArchiveEntry* texturex, const PatchTable& patch_table, bool add = false); + bool readTEXTUREXData(const ArchiveEntry* texturex, const PatchTable& patch_table, bool add = false); bool writeTEXTUREXData(ArchiveEntry* texturex, const PatchTable& patch_table) const; - bool readTEXTURESData(ArchiveEntry* textures); + bool readTEXTURESData(const ArchiveEntry* textures); bool writeTEXTURESData(ArchiveEntry* textures) const; bool convertToTEXTURES(); @@ -69,6 +68,7 @@ class TextureXList private: vector> textures_; Format txformat_ = Format::Normal; - CTexture tex_invalid_{ static_cast("INVALID_TEXTURE") }; // Deliberately set the invalid name to >8 characters + CTexture tex_invalid_{ static_cast( + "INVALID_TEXTURE") }; // Deliberately set the invalid name to >8 characters }; } // namespace slade diff --git a/src/Graphics/Font/SFont.cpp b/src/Graphics/Font/SFont.cpp index e3c734b6e..6af4fc0cc 100644 --- a/src/Graphics/Font/SFont.cpp +++ b/src/Graphics/Font/SFont.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -174,7 +174,7 @@ void SFont::drawCharacter(char c, ColRGBA colour) const gl::setColour(colour); // Get character to draw - auto& ch = characters_[(uint8_t)c]; + auto& ch = characters_[static_cast(c)]; if (ch.width_ == 0 && ch.height_ == 0) return; @@ -182,9 +182,11 @@ void SFont::drawCharacter(char c, ColRGBA colour) const Rectf tex_rect; auto& tex_info = gl::Texture::info(texture_); tex_rect.tl.set( - (double)ch.tex_bounds_.x1() / (double)tex_info.size.x, (double)ch.tex_bounds_.y1() / (double)tex_info.size.y); + static_cast(ch.tex_bounds_.x1()) / static_cast(tex_info.size.x), + static_cast(ch.tex_bounds_.y1()) / static_cast(tex_info.size.y)); tex_rect.br.set( - (double)ch.tex_bounds_.x2() / (double)tex_info.size.x, (double)ch.tex_bounds_.y2() / (double)tex_info.size.y); + static_cast(ch.tex_bounds_.x2()) / static_cast(tex_info.size.x), + static_cast(ch.tex_bounds_.y2()) / static_cast(tex_info.size.y)); glBegin(GL_QUADS); glTexCoord2d(tex_rect.x1(), tex_rect.y1()); glVertex2d(0, 0); @@ -249,11 +251,11 @@ void SFont::drawString(string_view str, ColRGBA colour, SFont::Align align) cons Rectf tex_rect; auto& tex_info = gl::Texture::info(texture_); tex_rect.tl.set( - (double)ch.tex_bounds_.x1() / (double)tex_info.size.x, - (double)ch.tex_bounds_.y1() / (double)tex_info.size.y); + static_cast(ch.tex_bounds_.x1()) / static_cast(tex_info.size.x), + static_cast(ch.tex_bounds_.y1()) / static_cast(tex_info.size.y)); tex_rect.br.set( - (double)ch.tex_bounds_.x2() / (double)tex_info.size.x, - (double)ch.tex_bounds_.y2() / (double)tex_info.size.y); + static_cast(ch.tex_bounds_.x2()) / static_cast(tex_info.size.x), + static_cast(ch.tex_bounds_.y2()) / static_cast(tex_info.size.y)); glBegin(GL_QUADS); glTexCoord2d(tex_rect.x1(), tex_rect.y1()); glVertex2d(xoff, 0); diff --git a/src/Graphics/Graphics.cpp b/src/Graphics/Graphics.cpp index 10ca44933..4948615e6 100644 --- a/src/Graphics/Graphics.cpp +++ b/src/Graphics/Graphics.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -32,7 +32,6 @@ // ----------------------------------------------------------------------------- #include "Main.h" #include "Graphics.h" -#include "Archive/ArchiveEntry.h" #include "General/Misc.h" #include "Graphics/GameFormats.h" #include "SImage/SIFormat.h" @@ -98,8 +97,8 @@ bool setOffsetsDoomGfx(SeekableData& data, int xoff, int yoff) return false; // Apply new offsets - header.left = wxINT16_SWAP_ON_BE((int16_t)xoff); - header.top = wxINT16_SWAP_ON_BE((int16_t)yoff); + header.left = wxINT16_SWAP_ON_BE(static_cast(xoff)); + header.top = wxINT16_SWAP_ON_BE(static_cast(yoff)); // Write new header to entry data.seekFromStart(0); @@ -122,8 +121,8 @@ bool setOffsetsDoomAlphaGfx(SeekableData& data, int xoff, int yoff) return false; // Apply new offsets - header.left = (int8_t)xoff; - header.top = (int8_t)yoff; + header.left = static_cast(xoff); + header.top = static_cast(yoff); // Write new header to entry data.seekFromStart(0); @@ -150,9 +149,9 @@ Vec2i gfx::pngGetSize(const MemChunk& png_data) return { 0, 0 }; // Read width and height from IHDR chunk - const Ihdr* ihdr = (Ihdr*)(png_data.data() + 12); - uint32_t w = wxINT32_SWAP_ON_LE(ihdr->width); - uint32_t h = wxINT32_SWAP_ON_LE(ihdr->height); + auto ihdr = reinterpret_cast(png_data.data() + 12); + uint32_t w = wxINT32_SWAP_ON_LE(ihdr->width); + uint32_t h = wxINT32_SWAP_ON_LE(ihdr->height); return { static_cast(w), static_cast(h) }; } @@ -200,7 +199,7 @@ bool gfx::pngSetgrAb(MemChunk& png_data, int xoff, int yoff) if (data[a] == 'g' && data[a + 1] == 'r' && data[a + 2] == 'A' && data[a + 3] == 'b') { grab_start = a - 4; - auto grab = (const GrabChunk*)(data + a); + auto grab = reinterpret_cast(data + a); ox = wxINT32_SWAP_ON_LE(grab->xoff); oy = wxINT32_SWAP_ON_LE(grab->yoff); break; @@ -303,7 +302,6 @@ bool gfx::pngSettRNS(MemChunk& png_data, bool value) if (png_data[a] == 't' && png_data[a + 1] == 'R' && png_data[a + 2] == 'N' && png_data[a + 3] == 'S') { trns_start = a - 4; - auto trns = (TransChunk*)(png_data.data() + a); trns_size = 12 + memory::readB32(png_data.data(), a - 4); } @@ -502,15 +500,16 @@ Vec2i gfx::calculateOffsets(int width, int height, OffsetType type) { switch (type) { - case OffsetType::Monster: return { static_cast(width * 0.5), height - 4 }; - case OffsetType::MonsterGL: return { static_cast(width * 0.5), height }; - case OffsetType::Projectile: return { static_cast(width * 0.5), static_cast(height * 0.5) }; - case OffsetType::WeaponFull: return { -160 + static_cast(width * 0.5), -200 + height }; - case OffsetType::WeaponDoom: return { -160 + static_cast(width * 0.5), -200 + 32 + height }; + case OffsetType::Monster: return { static_cast(width * 0.5), height - 4 }; + case OffsetType::MonsterGL: return { static_cast(width * 0.5), height }; + case OffsetType::Projectile: return { static_cast(width * 0.5), static_cast(height * 0.5) }; + case OffsetType::WeaponFull: return { -160 + static_cast(width * 0.5), -200 + height }; + case OffsetType::WeaponDoom: return { -160 + static_cast(width * 0.5), -200 + 32 + height }; case OffsetType::WeaponHeretic: return { -160 + static_cast(width * 0.5), -200 + 42 + height }; - case OffsetType::WeaponHexen: return { -160 + static_cast(width * 0.5), -200 + 38 + height }; - default: return { 0, 0 }; - }; + case OffsetType::WeaponHexen: return { -160 + static_cast(width * 0.5), -200 + 38 + height }; + } + + return { 0, 0 }; } // ----------------------------------------------------------------------------- diff --git a/src/Graphics/Icons.cpp b/src/Graphics/Icons.cpp index a9d401cfa..a7c97ca51 100644 --- a/src/Graphics/Icons.cpp +++ b/src/Graphics/Icons.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: https://slade.mancubus.net @@ -278,7 +278,7 @@ void parseGeneralBlock(const ParseTreeNode& node, const Archive& res_archive) // ----------------------------------------------------------------------------- // Loads an SVG [svg_data] of [size] into a wxBitmap, with optional [padding] // ----------------------------------------------------------------------------- -wxBitmap loadSVGIcon(const string& svg_data, int size, Point2i padding) +wxBitmap loadSVGIcon(const string& svg_data, int size, const Point2i& padding) { const auto img = wxutil::createImageFromSVG(svg_data, size, size); @@ -448,7 +448,7 @@ bool icons::loadIcons() // NOTE: this does not use any kind of caching and will generate/load the icon // from svg/png data each time // ----------------------------------------------------------------------------- -wxBitmapBundle icons::getIcon(Type type, string_view name, int size, Point2i padding) +wxBitmapBundle icons::getIcon(Type type, string_view name, int size, const Point2i& padding) { // Get icon definition const auto* icon_def = iconDef(type, name); @@ -529,8 +529,8 @@ wxBitmapBundle icons::getInterfaceIcon(string_view name, int size, InterfaceThem switch (theme) { case System: dark = ui_icons_dark; break; - case Light: dark = false; break; - case Dark: dark = true; break; + case Light: dark = false; break; + case Dark: dark = true; break; } // Get icon definition @@ -568,8 +568,8 @@ wxBitmap icons::getInterfaceIcon(string_view name, int size, InterfaceTheme them switch (theme) { case System: dark = ui_icons_dark; break; - case Light: dark = false; break; - case Dark: dark = true; break; + case Light: dark = false; break; + case Dark: dark = true; break; } // Get icon definition diff --git a/src/Graphics/Icons.h b/src/Graphics/Icons.h index 5793cd3ad..a8bc07929 100644 --- a/src/Graphics/Icons.h +++ b/src/Graphics/Icons.h @@ -24,7 +24,7 @@ namespace icons bool loadIcons(); #if wxCHECK_VERSION(3, 1, 6) - wxBitmapBundle getIcon(Type type, string_view name, int size = -1, Point2i padding = { 0, 0 }); + wxBitmapBundle getIcon(Type type, string_view name, int size = -1, const Point2i& padding = { 0, 0 }); wxBitmapBundle getInterfaceIcon(string_view name, int size = -1, InterfaceTheme theme = System); #else wxBitmap getIcon(Type type, string_view name, int size = -1, Point2i padding = { 0, 0 }); diff --git a/src/Graphics/Palette/Palette.cpp b/src/Graphics/Palette/Palette.cpp index e275b0a7d..c21ede08c 100644 --- a/src/Graphics/Palette/Palette.cpp +++ b/src/Graphics/Palette/Palette.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: https://slade.mancubus.net @@ -45,7 +45,7 @@ using namespace slade; // Variables // // ----------------------------------------------------------------------------- -CVAR(Int, col_match, (int)Palette::ColourMatch::Old, CVar::Flag::Save) +CVAR(Int, col_match, static_cast(Palette::ColourMatch::Old), CVar::Flag::Save) CVAR(Float, col_match_r, 1.0, CVar::Flag::Save) CVAR(Float, col_match_g, 1.0, CVar::Flag::Save) CVAR(Float, col_match_b, 1.0, CVar::Flag::Save) @@ -72,7 +72,7 @@ Palette::Palette(unsigned size) : colours_{ size }, colours_hsl_{ size }, colour // Init palette (to greyscale) for (unsigned a = 0; a < size; a++) { - double mult = (double)a / (double)size; + double mult = static_cast(a) / static_cast(size); colours_[a].set(mult * 255, mult * 255, mult * 255, 255, -1, a); colours_lab_[a].l = mult; colours_hsl_[a].l = mult; @@ -354,7 +354,7 @@ bool Palette::saveMem(MemChunk& mc, Format format, string_view name) string csv; for (unsigned a = 0; a < 256; a++) csv += fmt::format("{}, {}, {}\n", colours_[a].r, colours_[a].g, colours_[a].b); - mc.importMem((const uint8_t*)((const char*)csv.data()), csv.size()); + mc.importMem(reinterpret_cast(csv.data()), csv.size()); } // JASC palette @@ -363,7 +363,7 @@ bool Palette::saveMem(MemChunk& mc, Format format, string_view name) string jasc = "JASC-PAL\n0100\n256\n"; for (unsigned a = 0; a < 256; a++) jasc += fmt::format("{} {} {}\n", colours_[a].r, colours_[a].g, colours_[a].b); - mc.importMem((const uint8_t*)((const char*)jasc.data()), jasc.size()); + mc.importMem(reinterpret_cast(jasc.data()), jasc.size()); } // GIMP palette @@ -372,7 +372,7 @@ bool Palette::saveMem(MemChunk& mc, Format format, string_view name) string gimp = fmt::format("GIMP Palette\nName: {}\n#\n", name); for (unsigned a = 0; a < 256; a++) gimp += fmt::format("{}\t{}\t{}\tIndex {}\n", colours_[a].r, colours_[a].g, colours_[a].b, a); - mc.importMem((const uint8_t*)((const char*)gimp.data()), gimp.size()); + mc.importMem(reinterpret_cast(gimp.data()), gimp.size()); } // Image @@ -515,13 +515,13 @@ void Palette::setGradient(uint8_t startIndex, uint8_t endIndex, const ColRGBA& s } else { - perc = (float)a / (float)range; + perc = static_cast(a) / static_cast(range); } gradCol.set( - (int)(((r_range * perc) + startCol.fr()) * 255.0f), - (int)(((g_range * perc) + startCol.fg()) * 255.0f), - (int)(((b_range * perc) + startCol.fb()) * 255.0f), + static_cast(((r_range * perc) + startCol.fr()) * 255.0f), + static_cast(((g_range * perc) + startCol.fg()) * 255.0f), + static_cast(((b_range * perc) + startCol.fb()) * 255.0f), 255, -1, a + startIndex); @@ -705,9 +705,9 @@ void Palette::colourise(const ColRGBA& colour, int start, int end) double grey = (ncol.r * col_greyscale_r + ncol.g * col_greyscale_g + ncol.b * col_greyscale_b) / 255.0f; if (grey > 1.0) grey = 1.0; - ncol.r = (uint8_t)(colour.r * grey); - ncol.g = (uint8_t)(colour.g * grey); - ncol.b = (uint8_t)(colour.b * grey); + ncol.r = static_cast(colour.r * grey); + ncol.g = static_cast(colour.g * grey); + ncol.b = static_cast(colour.b * grey); setColour(i, ncol); } } diff --git a/src/Graphics/Palette/Palette.h b/src/Graphics/Palette/Palette.h index 12df28916..cfbacc73d 100644 --- a/src/Graphics/Palette/Palette.h +++ b/src/Graphics/Palette/Palette.h @@ -1,4 +1,5 @@ #pragma once + #include "Utility/Colour.h" namespace slade diff --git a/src/Graphics/Palette/PaletteManager.cpp b/src/Graphics/Palette/PaletteManager.cpp index a6f94e832..ef2d21a5b 100644 --- a/src/Graphics/Palette/PaletteManager.cpp +++ b/src/Graphics/Palette/PaletteManager.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: https://slade.mancubus.net @@ -142,7 +142,7 @@ string PaletteManager::palName(int index) // Returns the name of the given palette, or an empty string if the palette // isn't managed by the PaletteManager // ----------------------------------------------------------------------------- -string PaletteManager::palName(Palette* pal) +string PaletteManager::palName(const Palette* pal) { for (uint32_t a = 0; a < palettes_.size(); a++) { diff --git a/src/Graphics/Palette/PaletteManager.h b/src/Graphics/Palette/PaletteManager.h index 73ddaa8e8..8e7046f05 100644 --- a/src/Graphics/Palette/PaletteManager.h +++ b/src/Graphics/Palette/PaletteManager.h @@ -12,13 +12,13 @@ class PaletteManager bool init(); bool addPalette(unique_ptr pal, string_view name); - int numPalettes() const { return (int)palettes_.size(); } + int numPalettes() const { return static_cast(palettes_.size()); } Palette* defaultPalette() { return &pal_default_; } Palette* globalPalette(); Palette* palette(int index); Palette* palette(string_view name); string palName(int index); - string palName(Palette* pal); + string palName(const Palette* pal); bool loadResourcePalettes(); bool loadCustomPalettes(); diff --git a/src/Graphics/SImage/Formats/SIFDoom.h b/src/Graphics/SImage/Formats/SIFDoom.h index 916adf68a..1b1ac502b 100644 --- a/src/Graphics/SImage/Formats/SIFDoom.h +++ b/src/Graphics/SImage/Formats/SIFDoom.h @@ -96,13 +96,13 @@ class SIFDoomGfx : public SIFormat { width = gfx_data[0]; height = gfx_data[1]; - offset_x = (int8_t)gfx_data[2]; - offset_y = (int8_t)gfx_data[3]; + offset_x = static_cast(gfx_data[2]); + offset_y = static_cast(gfx_data[3]); hdr_size = 4; } else { - auto header = (gfx::PatchHeader*)gfx_data; + auto header = reinterpret_cast(gfx_data); width = wxINT16_SWAP_ON_BE(header->width); height = wxINT16_SWAP_ON_BE(header->height); offset_x = wxINT16_SWAP_ON_BE(header->left); @@ -117,13 +117,13 @@ class SIFDoomGfx : public SIFormat vector col_offsets(width); if (version > 0) { - auto c_ofs = (uint16_t*)((uint8_t*)gfx_data + hdr_size); + auto c_ofs = reinterpret_cast(gfx_data + hdr_size); for (int a = 0; a < width; a++) col_offsets[a] = wxUINT16_SWAP_ON_BE(c_ofs[a]); } else { - auto c_ofs = (uint32_t*)((uint8_t*)gfx_data + hdr_size); + auto c_ofs = reinterpret_cast(gfx_data + hdr_size); for (int a = 0; a < width; a++) col_offsets[a] = wxUINT32_SWAP_ON_BE(c_ofs[a]); } @@ -241,7 +241,6 @@ class SIFDoomGfx : public SIFormat auto mask = imageMask(image); // Go through columns - uint32_t offset = 0; for (int c = 0; c < image.width(); c++) { Column col; @@ -250,8 +249,8 @@ class SIFDoomGfx : public SIFormat bool ispost = false; bool first_254 = true; // First 254 pixels should use absolute offsets - offset = c; - uint8_t row_off = 0; + uint32_t offset = c; + uint8_t row_off = 0; for (int r = 0; r < image.height(); r++) { // For vanilla-compatible dimensions, use a split at 128 to prevent tiling. @@ -278,7 +277,6 @@ class SIFDoomGfx : public SIFormat { col.posts.push_back(post); post.pixels.clear(); - ispost = false; } // Begin relative offsets @@ -333,9 +331,6 @@ class SIFDoomGfx : public SIFormat // Add the column data columns.push_back(col); - - // Go to next column - offset++; } // Write doom gfx data to output @@ -434,7 +429,10 @@ class SIFDoomBetaGfx : public SIFDoomGfx SIFDoomBetaGfx() : SIFDoomGfx("doom_beta", "Doom Gfx (Beta)", 160) {} ~SIFDoomBetaGfx() override = default; - bool isThisFormat(const MemChunk& mc) override { return EntryDataFormat::format("img_doom_beta")->isThisFormat(mc); } + bool isThisFormat(const MemChunk& mc) override + { + return EntryDataFormat::format("img_doom_beta")->isThisFormat(mc); + } SImage::Info info(const MemChunk& mc, int index) override { @@ -458,7 +456,10 @@ class SIFDoomAlphaGfx : public SIFDoomGfx SIFDoomAlphaGfx() : SIFDoomGfx("doom_alpha", "Doom Gfx (Alpha)", 100) {} ~SIFDoomAlphaGfx() override = default; - bool isThisFormat(const MemChunk& mc) override { return EntryDataFormat::format("img_doom_alpha")->isThisFormat(mc); } + bool isThisFormat(const MemChunk& mc) override + { + return EntryDataFormat::format("img_doom_alpha")->isThisFormat(mc); + } SImage::Info info(const MemChunk& mc, int index) override { @@ -490,7 +491,10 @@ class SIFDoomArah : public SIFormat SIFDoomArah() : SIFormat("doom_arah", "Doom Arah", "lmp", 100) {} ~SIFDoomArah() override = default; - bool isThisFormat(const MemChunk& mc) override { return EntryDataFormat::format("img_doom_arah")->isThisFormat(mc); } + bool isThisFormat(const MemChunk& mc) override + { + return EntryDataFormat::format("img_doom_arah")->isThisFormat(mc); + } SImage::Info info(const MemChunk& mc, int index) override { @@ -534,7 +538,7 @@ class SIFDoomArah : public SIFormat memset(img_mask, 255, width * height); // Mark as transparent all pixels that are index 255 - for (size_t i = 0; i < (unsigned)(width * height); ++i) + for (size_t i = 0; i < static_cast(width * height); ++i) if (img_data[i] == 255) img_mask[i] = 0; @@ -552,7 +556,10 @@ class SIFDoomSnea : public SIFormat SIFDoomSnea() : SIFormat("doom_snea", "Doom Snea", "lmp") {} ~SIFDoomSnea() override = default; - bool isThisFormat(const MemChunk& mc) override { return EntryDataFormat::format("img_doom_snea")->isThisFormat(mc); } + bool isThisFormat(const MemChunk& mc) override + { + return EntryDataFormat::format("img_doom_snea")->isThisFormat(mc); + } SImage::Info info(const MemChunk& mc, int index) override { @@ -653,12 +660,12 @@ class SIFDoomPSXHelper // indexes other than '0' which are black are assumed to be black with the 'semi transparency' flag set. We have to // make this assumption because SLADE does not have the concept of the PSX semi-transparency flag in it's color // model... - static short getPsxOpaqueBlackColorIndex(Palette& palette) + static short getPsxOpaqueBlackColorIndex(const Palette& palette) { // Search for for black with the 'semi-transparency' bit set first (any black with color index other than '0') const std::vector& colors = palette.colours(); - for (short i = 1; i < colors.size(); ++i) + for (short i = 1; i < static_cast(colors.size()); ++i) { if (colors[i].equals(ColRGBA::BLACK)) return i; @@ -823,7 +830,7 @@ class SIFDoomJagHelper } } - static short getOpaqueZeroColorIndex(Palette& palette) + static short getOpaqueZeroColorIndex(const Palette& palette) { ColRGBA color = palette.colour(0); auto icolor = ColRGBA(255 - color.r, 255 - color.g, 255 - color.b, 255); @@ -840,12 +847,16 @@ class SIFDoomJaguar : public SIFormat { public: SIFDoomJaguar(int colmajor = 0, string_view id = "doom_jaguar", string_view name = "Doom Jaguar") : - SIFormat(id, name, "lmp", 85), colmajor(colmajor) + SIFormat(id, name, "lmp", 85), + colmajor(colmajor) { } - ~SIFDoomJaguar() = default; + ~SIFDoomJaguar() override = default; - bool isThisFormat(const MemChunk& mc) override { return EntryDataFormat::format("img_doom_jaguar")->isThisFormat(mc); } + bool isThisFormat(const MemChunk& mc) override + { + return EntryDataFormat::format("img_doom_jaguar")->isThisFormat(mc); + } SImage::Info info(const MemChunk& mc, int index) override { @@ -979,12 +990,11 @@ class SIFDoomJaguar : public SIFormat out.clear(); out.seek(0, SEEK_SET); - gfx::JagPicHeader header; - memset(&header, 0, sizeof(header)); - header.width = wxINT16_SWAP_ON_LE((short)image.width()); - header.height = wxINT16_SWAP_ON_LE((short)image.height()); - header.depth = wxINT16_SWAP_ON_LE(3); - header.flags = wxINT16_SWAP_ON_LE(colmajor & 1); + gfx::JagPicHeader header = {}; + header.width = wxINT16_SWAP_ON_LE((short)image.width()); + header.height = wxINT16_SWAP_ON_LE((short)image.height()); + header.depth = wxINT16_SWAP_ON_LE(3); + header.flags = wxINT16_SWAP_ON_LE(colmajor & 1); out.write(&header, sizeof(header)); @@ -1008,7 +1018,7 @@ class SIFDoomJaguarColMajor : public SIFDoomJaguar { public: SIFDoomJaguarColMajor() : SIFDoomJaguar(1, "doom_jaguar_colmajor", "Doom Jaguar CM") {} - ~SIFDoomJaguarColMajor() final = default; + ~SIFDoomJaguarColMajor() override = default; bool isThisFormat(const MemChunk& mc) override { diff --git a/src/Graphics/SImage/Formats/SIFImages.h b/src/Graphics/SImage/Formats/SIFImages.h index 774702489..0bd0cdfd7 100644 --- a/src/Graphics/SImage/Formats/SIFImages.h +++ b/src/Graphics/SImage/Formats/SIFImages.h @@ -5,7 +5,7 @@ class PNGChunk PNGChunk(string_view name = "----") { memcpy(name_, name.data(), 4); } ~PNGChunk() = default; - string name() const { return string(name_, 4); } + string name() const { return { name_, 4 }; } uint32_t size() const { return size_; } uint32_t crc() const { return crc_; } MemChunk& data() { return data_; } @@ -233,7 +233,7 @@ class SIFPng : public SIFormat bool readImage(SImage& image, const MemChunk& data, int index) override { // Create FreeImage bitmap from entry data - auto mem = FreeImage_OpenMemory((BYTE*)data.data(), data.size()); + auto mem = FreeImage_OpenMemory(const_cast(data.data()), data.size()); auto fif = FreeImage_GetFileTypeFromMemory(mem, 0); auto bm = FreeImage_LoadFromMemory(fif, mem, 0); FreeImage_CloseMemory(mem); @@ -522,7 +522,7 @@ class SIFPng : public SIFormat PNGChunk grAb("grAb"); GrabChunk gc = { wxINT32_SWAP_ON_LE((int32_t)image.offset().x), wxINT32_SWAP_ON_LE((int32_t)image.offset().y) }; - grAb.setData((const uint8_t*)&gc, 8); + grAb.setData(reinterpret_cast(&gc), 8); grAb.write(data); } diff --git a/src/Graphics/SImage/Formats/SIFOther.h b/src/Graphics/SImage/Formats/SIFOther.h index a0fd491b3..c2eaf41d1 100644 --- a/src/Graphics/SImage/Formats/SIFOther.h +++ b/src/Graphics/SImage/Formats/SIFOther.h @@ -234,7 +234,7 @@ class SIFSCGfx : public SIFormat memset(img_mask, 255, width * height); // Mark as transparent all pixels that are index 0 - for (size_t i = 0; i < (unsigned)(width * height); ++i) + for (size_t i = 0; i < static_cast(width * height); ++i) if (img_data[i] == 0) img_mask[i] = 0; @@ -286,7 +286,7 @@ class SIFSCWall : public SIFormat // Determine width and height int height = data[0] * 4; int width = 64; - if ((int)data.size() != width * height + HEADEROFFSET) + if (static_cast(data.size()) != width * height + HEADEROFFSET) return false; // Create image @@ -444,8 +444,8 @@ class SIFBuildTile : public SIFormat } // Get tile info - uint32_t firsttile = wxUINT32_SWAP_ON_BE(((uint32_t*)(mc.data() + headeroffset))[2]); - uint32_t lasttile = wxUINT32_SWAP_ON_BE(((uint32_t*)(mc.data() + headeroffset))[3]); + uint32_t firsttile = wxUINT32_SWAP_ON_BE((reinterpret_cast(mc.data() + headeroffset))[2]); + uint32_t lasttile = wxUINT32_SWAP_ON_BE((reinterpret_cast(mc.data() + headeroffset))[3]); // Set number of images info.numimages = 1 + lasttile - firsttile; @@ -485,8 +485,8 @@ class SIFBuildTile : public SIFormat info.format = id_; // Offsets are signed bytes, so they need a cast - info.offset_x = (int8_t)mc[o_offs + 1]; - info.offset_y = (int8_t)mc[o_offs + 2]; + info.offset_x = static_cast(mc[o_offs + 1]); + info.offset_y = static_cast(mc[o_offs + 2]); // Offsets are not computed from the same reference point, so convert them info.offset_x += (info.width >> 1); @@ -672,7 +672,7 @@ class SIFWolfPic : public SIFormat auto info = this->info(data, index); // Check data - if ((int)data.size() != 4 + info.width * info.height) + if (static_cast(data.size()) != 4 + info.width * info.height) return false; // Create image @@ -743,15 +743,15 @@ class SIFWolfSprite : public SIFormat // Read data auto cmdptr = reinterpret_cast(data.data() + 4); uint32_t i, x, y; - for (x = 0; x < (unsigned)info.width; ++x) + for (x = 0; x < static_cast(info.width); ++x) { auto linecmds = reinterpret_cast(data.data() + wxINT16_SWAP_ON_BE(*cmdptr)); cmdptr++; for (; wxINT16_SWAP_ON_BE(*linecmds); linecmds += 3) { i = (wxINT16_SWAP_ON_BE(linecmds[2]) >> 1) + wxINT16_SWAP_ON_BE(linecmds[1]); - for (y = (uint32_t)(wxINT16_SWAP_ON_BE(linecmds[2]) >> 1); - y < (uint32_t)(wxINT16_SWAP_ON_BE(linecmds[0]) / 2); + for (y = static_cast((wxINT16_SWAP_ON_BE(linecmds[2]) >> 1)); + y < static_cast((wxINT16_SWAP_ON_BE(linecmds[0]) / 2)); ++y, ++i) { img_data[y * info.width + x] = data[i]; diff --git a/src/Graphics/SImage/Formats/SIFRott.h b/src/Graphics/SImage/Formats/SIFRott.h index 3133df459..cfa53da50 100644 --- a/src/Graphics/SImage/Formats/SIFRott.h +++ b/src/Graphics/SImage/Formats/SIFRott.h @@ -18,7 +18,7 @@ class SIFRottGfx : public SIFormat SImage::Info info; // Read header - auto header = (const gfx::ROTTPatchHeader*)mc.data(); + auto header = reinterpret_cast(mc.data()); info.width = wxINT16_SWAP_ON_BE(header->width); info.height = wxINT16_SWAP_ON_BE(header->height); info.offset_x = wxINT16_SWAP_ON_BE(header->left) + (wxINT16_SWAP_ON_BE(header->origsize) / 2); @@ -64,7 +64,7 @@ class SIFRottGfx : public SIFormat uint16_t col_offset = col_offsets[c]; // Check column offset is valid - if (col_offset >= (unsigned)data.size()) + if (col_offset >= data.size()) return false; // Go to start of column @@ -305,7 +305,7 @@ class SIFRottPic : public SIFormat auto info = this->info(data, index); // Check data - if ((int)data.size() != 4 + info.width * info.height) + if (static_cast(data.size()) != 4 + info.width * info.height) return false; // Create image diff --git a/src/Graphics/SImage/Formats/SIFZDoom.h b/src/Graphics/SImage/Formats/SIFZDoom.h index e472f7935..1ef041366 100644 --- a/src/Graphics/SImage/Formats/SIFZDoom.h +++ b/src/Graphics/SImage/Formats/SIFZDoom.h @@ -12,7 +12,7 @@ class SIFImgz : public SIFormat SImage::Info info; // Get width & height - auto header = (gfx::IMGZHeader*)mc.data(); + auto header = reinterpret_cast(mc.data()); info.width = wxINT16_SWAP_ON_BE(header->width); info.height = wxINT16_SWAP_ON_BE(header->height); @@ -27,7 +27,7 @@ class SIFImgz : public SIFormat bool readImage(SImage& image, const MemChunk& data, int index) override { // Setup variables - auto header = (gfx::IMGZHeader*)data.data(); + auto header = reinterpret_cast(data.data()); int width = wxINT16_SWAP_ON_BE(header->width); int height = wxINT16_SWAP_ON_BE(header->height); int offset_x = wxINT16_SWAP_ON_BE(header->left); diff --git a/src/Graphics/SImage/SIFormat.cpp b/src/Graphics/SImage/SIFormat.cpp index bd8bbe6ed..7c32eeded 100644 --- a/src/Graphics/SImage/SIFormat.cpp +++ b/src/Graphics/SImage/SIFormat.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: https://slade.mancubus.net @@ -30,12 +30,14 @@ // // ----------------------------------------------------------------------------- #include "Main.h" -#include "App.h" #undef BOOL #include "Archive/Archive.h" -#include "Archive/EntryType/EntryType.h" -#include "General/Misc.h" #include "SIFormat.h" +#include + +#ifndef _WIN32 +#undef _WINDOWS_ // Undefine _WINDOWS_ that has been defined by FreeImage +#endif using namespace slade; @@ -111,7 +113,7 @@ class SIFGeneralImage : public SIFormat bool isThisFormat(const MemChunk& mc) override { - auto mem = FreeImage_OpenMemory((BYTE*)mc.data(), mc.size()); + auto mem = FreeImage_OpenMemory(const_cast(mc.data()), mc.size()); auto fif = FreeImage_GetFileTypeFromMemory(mem, 0); FreeImage_CloseMemory(mem); return fif != FIF_UNKNOWN; @@ -192,7 +194,7 @@ class SIFGeneralImage : public SIFormat FIBITMAP* getFIInfo(const MemChunk& data, SImage::Info& info) const { // Get FreeImage bitmap info from entry data - auto mem = FreeImage_OpenMemory((BYTE*)data.data(), data.size()); + auto mem = FreeImage_OpenMemory(const_cast(data.data()), data.size()); auto fif = FreeImage_GetFileTypeFromMemory(mem, 0); auto bm = FreeImage_LoadFromMemory(fif, mem, 0); FreeImage_CloseMemory(mem); @@ -337,7 +339,7 @@ class SIFRaw : public SIFormat { for (unsigned a = 0; a < n_valid_flat_sizes; a++) { - if ((int)valid_flat_size[a][0] == width && (int)valid_flat_size[a][1] == height + if (static_cast(valid_flat_size[a][0]) == width && static_cast(valid_flat_size[a][1]) == height && (valid_flat_size[a][2] == 1 || gfx_extraconv)) return true; } @@ -398,8 +400,8 @@ class SIFRawFlat : public SIFRaw // Otherwise, check if it can be cropped to a valid size for (unsigned a = 0; a < n_valid_flat_sizes; a++) - if (((unsigned)width >= valid_flat_size[a][0] && (unsigned)height >= valid_flat_size[a][1] - && valid_flat_size[a][2] == 1) + if ((static_cast(width) >= valid_flat_size[a][0] + && static_cast(height) >= valid_flat_size[a][1] && valid_flat_size[a][2] == 1) || gfx_extraconv) return Writable::Convert; @@ -432,13 +434,14 @@ class SIFRawFlat : public SIFRaw bool writable = (valid_flat_size[a][2] == 1 || gfx_extraconv); // Check for exact match (no need to crop) - if (image.width() == (int)valid_flat_size[a][0] && image.height() == (int)valid_flat_size[a][1] && writable) + if (image.width() == static_cast(valid_flat_size[a][0]) + && image.height() == static_cast(valid_flat_size[a][1]) && writable) return true; // If the flat will fit within this size, crop to the previous size // (this works because flat sizes list is in size-order) - if (image.width() <= (int)valid_flat_size[a][0] && image.height() <= (int)valid_flat_size[a][1] && width > 0 - && height > 0) + if (image.width() <= static_cast(valid_flat_size[a][0]) + && image.height() <= static_cast(valid_flat_size[a][1]) && width > 0 && height > 0) { image.crop(0, 0, width, height); return true; @@ -486,7 +489,10 @@ class SIFRawFlat : public SIFRaw // SIFormat class constructor // ---------------------------------------------------------------------------- SIFormat::SIFormat(string_view id, string_view name, string_view ext, uint8_t reliability) : - id_{ id }, name_{ name }, extension_{ ext }, reliability_{ reliability } + id_{ id }, + name_{ name }, + extension_{ ext }, + reliability_{ reliability } { // Add to list of formats simage_formats.push_back(this); diff --git a/src/Graphics/SImage/SIFormat.h b/src/Graphics/SImage/SIFormat.h index 5d333e991..16f62cbee 100644 --- a/src/Graphics/SImage/SIFormat.h +++ b/src/Graphics/SImage/SIFormat.h @@ -89,7 +89,7 @@ class SIFormat } static void initFormats(); - static SIFormat* getFormat(string_view name); + static SIFormat* getFormat(string_view id); static SIFormat* determineFormat(const MemChunk& mc); static SIFormat* unknownFormat(); static SIFormat* rawFormat(); diff --git a/src/Graphics/SImage/SImage.cpp b/src/Graphics/SImage/SImage.cpp index 851601525..14d0d9b79 100644 --- a/src/Graphics/SImage/SImage.cpp +++ b/src/Graphics/SImage/SImage.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: https://slade.mancubus.net @@ -209,10 +209,10 @@ bool SImage::putIndexedData(MemChunk& mc) const switch (type_) { - case Type::RGBA: return false; // Cannot do this for trucolor graphics. + case Type::RGBA: return false; // Cannot do this for trucolor graphics. case Type::PalMask: case Type::AlphaMap: return mc.write(data_.data(), data_.size()); - default: return false; + default: return false; } } @@ -884,7 +884,7 @@ bool SImage::cutoffMask(uint8_t threshold) // Sets the pixel at [x],[y] to [colour]. // Returns false if the position is out of range, true otherwise // ----------------------------------------------------------------------------- -bool SImage::setPixel(int x, int y, ColRGBA colour, Palette* pal) +bool SImage::setPixel(int x, int y, ColRGBA colour, const Palette* pal) { // Check position if (x < 0 || x >= width_ || y < 0 || y >= height_) @@ -1046,10 +1046,10 @@ bool SImage::rotate(int angle) switch (angle) { // Urgh maths... - case 90: j = (((new_height - 1) - (i % width_)) * new_width) + (i / width_); break; + case 90: j = (((new_height - 1) - (i % width_)) * new_width) + (i / width_); break; case 180: j = (numpixels - 1) - i; break; case 270: j = ((i % width_) * new_width) + ((new_width - 1) - (i / width_)); break; - default: return false; + default: return false; } if (j >= numpixels) { @@ -1390,7 +1390,7 @@ bool SImage::applyTranslation(string_view tr, Palette* pal, bool truecolor) // If the image is paletted, the resulting pixel colour is converted to its // nearest match in [pal] // ----------------------------------------------------------------------------- -bool SImage::drawPixel(int x, int y, ColRGBA colour, const DrawProps& properties, Palette* pal) +bool SImage::drawPixel(int x, int y, ColRGBA colour, const DrawProps& properties, const Palette* pal) { // Check valid coords if (x < 0 || y < 0 || x >= width_ || y >= height_) @@ -1511,7 +1511,7 @@ bool SImage::drawImage( int y_pos, const DrawProps& properties, const Palette* pal_src, - Palette* pal_dest) + const Palette* pal_dest) { // Check images if (!data_.hasData() || !img.data_.hasData()) @@ -1585,7 +1585,7 @@ bool SImage::drawImage( // If the image is paletted, each pixel will be set to its nearest matching // colour in [pal] // ----------------------------------------------------------------------------- -bool SImage::colourise(ColRGBA colour, Palette* pal, int start, int stop) +bool SImage::colourise(ColRGBA colour, const Palette* pal, int start, int stop) { // Can't do this with alpha maps if (type_ == Type::AlphaMap) @@ -1636,7 +1636,7 @@ bool SImage::colourise(ColRGBA colour, Palette* pal, int start, int stop) // If the image is paletted, each pixel will be set to its nearest matching // colour in [pal] // ----------------------------------------------------------------------------- -bool SImage::tint(ColRGBA colour, float amount, Palette* pal, int start, int stop) +bool SImage::tint(ColRGBA colour, float amount, const Palette* pal, int start, int stop) { // Can't do this with alpha maps if (type_ == Type::AlphaMap) diff --git a/src/Graphics/SImage/SImage.h b/src/Graphics/SImage/SImage.h index 95f322fb7..fc38c60e4 100644 --- a/src/Graphics/SImage/SImage.h +++ b/src/Graphics/SImage/SImage.h @@ -142,7 +142,7 @@ class SImage bool cutoffMask(uint8_t threshold); // Image modification - bool setPixel(int x, int y, ColRGBA colour, Palette* pal = nullptr); + bool setPixel(int x, int y, ColRGBA colour, const Palette* pal = nullptr); bool setPixel(int x, int y, uint8_t pal_index, uint8_t alpha = 255); bool imgconv(); bool rotate(int angle); @@ -153,16 +153,16 @@ class SImage bool setImageData(const uint8_t* ndata, unsigned ndata_size, int nwidth, int nheight, Type ntype); bool applyTranslation(Translation* tr, Palette* pal = nullptr, bool truecolor = false); bool applyTranslation(string_view tr, Palette* pal = nullptr, bool truecolor = false); - bool drawPixel(int x, int y, ColRGBA colour, const DrawProps& properties, Palette* pal); + bool drawPixel(int x, int y, ColRGBA colour, const DrawProps& properties, const Palette* pal); bool drawImage( const SImage& img, int x, int y, const DrawProps& properties, const Palette* pal_src = nullptr, - Palette* pal_dest = nullptr); - bool colourise(ColRGBA colour, Palette* pal = nullptr, int start = -1, int stop = -1); - bool tint(ColRGBA colour, float amount, Palette* pal = nullptr, int start = -1, int stop = -1); + const Palette* pal_dest = nullptr); + bool colourise(ColRGBA colour, const Palette* pal = nullptr, int start = -1, int stop = -1); + bool tint(ColRGBA colour, float amount, const Palette* pal = nullptr, int start = -1, int stop = -1); bool adjust(); bool mirrorpad(); diff --git a/src/Graphics/SImage/SImageFormats.cpp b/src/Graphics/SImage/SImageFormats.cpp index bfd320eba..402e96d57 100644 --- a/src/Graphics/SImage/SImageFormats.cpp +++ b/src/Graphics/SImage/SImageFormats.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: https://slade.mancubus.net @@ -38,7 +38,6 @@ #include "SImage.h" #include "Utility/Memory.h" #undef BOOL -#include "General/Misc.h" #include "SIFormat.h" #include "thirdparty/lunasvg/include/lunasvg.h" diff --git a/src/Graphics/Translation.cpp b/src/Graphics/Translation.cpp index 7b324f023..27eba37be 100644 --- a/src/Graphics/Translation.cpp +++ b/src/Graphics/Translation.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -451,7 +451,7 @@ void Translation::copy(const Translation& copy) // ----------------------------------------------------------------------------- // Returns the translation range at [index] // ----------------------------------------------------------------------------- -TransRange* Translation::range(unsigned index) +TransRange* Translation::range(unsigned index) const { if (index >= translations_.size()) return nullptr; @@ -462,7 +462,7 @@ TransRange* Translation::range(unsigned index) // ----------------------------------------------------------------------------- // Apply the translation to the given color // ----------------------------------------------------------------------------- -ColRGBA Translation::translate(const ColRGBA& col, Palette* pal) +ColRGBA Translation::translate(const ColRGBA& col, const Palette* pal) const { ColRGBA colour(col); if (pal == nullptr) @@ -647,12 +647,12 @@ TransRange* Translation::addRange(TransRange::Type type, int pos, int range_star TransRange::IndexRange range{ range_start, range_end }; switch (type) { - case TransRange::Type::Colour: tr = std::make_unique(range); break; - case TransRange::Type::Desat: tr = std::make_unique(range); break; - case TransRange::Type::Blend: tr = std::make_unique(range); break; - case TransRange::Type::Tint: tr = std::make_unique(range); break; + case TransRange::Type::Colour: tr = std::make_unique(range); break; + case TransRange::Type::Desat: tr = std::make_unique(range); break; + case TransRange::Type::Blend: tr = std::make_unique(range); break; + case TransRange::Type::Tint: tr = std::make_unique(range); break; case TransRange::Type::Special: tr = std::make_unique(range); break; - default: tr = std::make_unique(range, range); break; + default: tr = std::make_unique(range, range); break; } // Add to list @@ -696,7 +696,7 @@ void Translation::swapRanges(int pos1, int pos2) // Apply one of the special colour blending modes from ZDoom: // Desaturate, Ice, Inverse, Blue, Gold, Green, Red. // ----------------------------------------------------------------------------- -ColRGBA Translation::specialBlend(const ColRGBA& col, uint8_t type, Palette* pal) +ColRGBA Translation::specialBlend(const ColRGBA& col, uint8_t type, const Palette* pal) { // Abort just in case if (type == SpecialBlend::Invalid) @@ -765,6 +765,7 @@ ColRGBA Translation::specialBlend(const ColRGBA& col, uint8_t type, Palette* pal // Hacx invulnerability // starts black, ends blue eb = 1.5; + break; default: break; } // Apply new colour @@ -815,19 +816,19 @@ string Translation::getPredefined(string_view def) else if (def == "\"heretic8\"") def = "\"225:240=95:110\""; else if (def == "\"strife0\"") - def = "\"32:63=0:31\", \"128:143=64:79\", \"241:246=224:229\", \"247:251=241:245\""; + def = R"("32:63=0:31", "128:143=64:79", "241:246=224:229", "247:251=241:245")"; else if (def == "\"strife1\"") - def = "\"32:63=0:31\", \"128:143=176:191\""; + def = R"("32:63=0:31", "128:143=176:191")"; else if (def == "\"strife2\"") - def = "\"32:47=208:223\", \"48:63=208:223\", \"128:143=16:31\""; + def = R"("32:47=208:223", "48:63=208:223", "128:143=16:31")"; else if (def == "\"strife3\"") - def = "\"32:47=208:223\", \"48:63=208:223\", \"128:143=48:63\""; + def = R"("32:47=208:223", "48:63=208:223", "128:143=48:63")"; else if (def == "\"strife4\"") - def = "\"32:63=0:31\", \"80:95=128:143\", \"128:143=80:95\", \"192:223=160:191\""; + def = R"("32:63=0:31", "80:95=128:143", "128:143=80:95", "192:223=160:191")"; else if (def == "\"strife5\"") - def = "\"32:63=0:31\", \"80:95=16:31\", \"128:143=96:111\", \"192:223=32:63\""; + def = R"("32:63=0:31", "80:95=16:31", "128:143=96:111", "192:223=32:63")"; else if (def == "\"strife6\"") - def = "\"32:63=0:31\", \"80:95=64:79\", \"128:143=144:159\", \"192=1\", \"193:223=1:31\""; + def = R"("32:63=0:31", "80:95=64:79", "128:143=144:159", "192=1", "193:223=1:31")"; else if (def == "\"chex0\"") def = "\"192:207=112:127\""; else if (def == "\"chex1\"") @@ -848,19 +849,19 @@ string Translation::getPredefined(string_view def) "\"112:113=171:171\", \"114:114=172:172\", \"115:122=173:187\", \"123:124=188:189\", \"125:126=45:47\", " "\"127:127=1:1\""; else if (def == "\"dirt\"") - def = "\"112:117=128:133\", \"118:120=135:137\", \"121:123=139:143\", \"124:125=237:239\", \"126:127=1:2\""; + def = R"("112:117=128:133", "118:120=135:137", "121:123=139:143", "124:125=237:239", "126:127=1:2")"; else if (def == "\"blue\"") - def = "\"112:121=197:206\", \"122:127=240:245"; + def = R"("112:121=197:206", "122:127=240:245)"; else if (def == "\"gold\"") - def = "\"112:113=160:160\", \"114:119=161:166\", \"120:123=236:239\", \"124:125=1:2\", \"126:127=7:8\""; + def = R"("112:113=160:160", "114:119=161:166", "120:123=236:239", "124:125=1:2", "126:127=7:8")"; else if (def == "\"sea\"") - def = "\"112:112=91:91\", \"113:114=94:95\", \"115:122=152:159\", \"123:126=9:12\", \"127:127=8:8\""; + def = R"("112:112=91:91", "113:114=94:95", "115:122=152:159", "123:126=9:12", "127:127=8:8")"; else if (def == "\"black\"") - def = "\"112:112=101:101\", \"113:121=103:111\", \"122:125=5:8\", \"126:127=0:0\""; + def = R"("112:112=101:101", "113:121=103:111", "122:125=5:8", "126:127=0:0")"; else if (def == "\"purple\"") - def = "\"112:113=4:4\", \"114:115=170:170\", \"116:125=250:254\", \"126:127=46:46\""; + def = R"("112:113=4:4", "114:115=170:170", "116:125=250:254", "126:127=46:46")"; else if (def == "\"vomit\"") - def = "\"112:119=209:216\", \"120:121=218:220\", \"122:124=69:75\", \"125:127=237:239\""; + def = R"("112:119=209:216", "120:121=218:220", "122:124=69:75", "125:127=237:239")"; else if (def == "\"pink\"") def = "\"112:113=16:17\", \"114:117=19:25\", \"118:119=27:28\", \"120:124=30:38\", \"125:126=41:43\", " @@ -870,7 +871,7 @@ string Translation::getPredefined(string_view def) "\"112:112=4:4\", \"113:118=48:63\", \"119:119=65:65\", \"120:124=68:76\", \"125:126=77:79\", " "\"127:127=1:1\""; else if (def == "\"white\"") - def = "\"112:112=4:4\", \"113:115=80:82\", \"116:117=84:86\", \"118:120=89:93\", \"121:127=96:108\""; + def = R"("112:112=4:4", "113:115=80:82", "116:117=84:86", "118:120=89:93", "121:127=96:108")"; // And why not this one too else if (def == "\"stealth\"") def = "\"0:255=%[0.00,0.00,0.00]:[1.31,0.84,0.84]\""; diff --git a/src/Graphics/Translation.h b/src/Graphics/Translation.h index ef217bc8f..2bbbcee21 100644 --- a/src/Graphics/Translation.h +++ b/src/Graphics/Translation.h @@ -1,4 +1,5 @@ #pragma once + #include "Utility/Colour.h" namespace slade @@ -25,7 +26,7 @@ class TransRange uint8_t start = 0; uint8_t end = 0; - IndexRange(int start, int end) : start{ (uint8_t)start }, end{ (uint8_t)end } {} + IndexRange(int start, int end) : start{ static_cast(start) }, end{ static_cast(end) } {} string asText() const { return fmt::format("{}:{}", start, end); } }; @@ -273,20 +274,20 @@ class Translation bool isEmpty() const { return built_in_name_.empty() && translations_.empty(); } unsigned nRanges() const { return translations_.size(); } - TransRange* range(unsigned index); + TransRange* range(unsigned index) const; const string& builtInName() const { return built_in_name_; } uint8_t desaturationAmount() const { return desat_amount_; } void setBuiltInName(string_view name) { built_in_name_ = name; } void setDesaturationAmount(uint8_t amount) { desat_amount_ = amount; } - ColRGBA translate(const ColRGBA& col, Palette* pal = nullptr); + ColRGBA translate(const ColRGBA& col, const Palette* pal = nullptr) const; TransRange* addRange(TransRange::Type type, int pos = -1, int range_start = 0, int range_end = 0); void removeRange(int pos); void swapRanges(int pos1, int pos2); - static ColRGBA specialBlend(const ColRGBA& col, uint8_t type, Palette* pal = nullptr); + static ColRGBA specialBlend(const ColRGBA& col, uint8_t type, const Palette* pal = nullptr); static string getPredefined(string_view def); private: diff --git a/src/MainEditor/ArchiveOperations.cpp b/src/MainEditor/ArchiveOperations.cpp index d0e733815..8d9da4328 100644 --- a/src/MainEditor/ArchiveOperations.cpp +++ b/src/MainEditor/ArchiveOperations.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -37,13 +37,13 @@ #include "Archive/Formats/WadArchive.h" #include "General/Console.h" #include "General/ResourceManager.h" +#include "Graphics/CTexture/PatchTable.h" #include "Graphics/CTexture/TextureXList.h" #include "MainEditor/MainEditor.h" #include "MainEditor/UI/MainWindow.h" #include "SLADEMap/MapFormat/Doom64MapFormat.h" #include "SLADEMap/MapFormat/DoomMapFormat.h" #include "SLADEMap/MapFormat/HexenMapFormat.h" -#include "SLADEMap/MapFormat/Doom32XMapFormat.h" #include "SLADEMap/MapObject/MapSector.h" #include "UI/Dialogs/ExtMessageDialog.h" #include "UI/WxUtils.h" @@ -402,7 +402,7 @@ void archiveoperations::removeEntriesUnchangedFromIWAD(Archive* archive) // Checks entries of the same name from the base resource archive. Also checks // texture definitions. This helps know what your archive overrides. // ----------------------------------------------------------------------------- -bool archiveoperations::checkOverriddenEntriesInIWAD(Archive* archive) +bool archiveoperations::checkOverriddenEntriesInIWAD(Archive* archive) { // Do nothing if there is no base resource archive, // or if the archive *is* the base resource archive. @@ -416,9 +416,9 @@ bool archiveoperations::checkOverriddenEntriesInIWAD(Archive* archive) // Init search options Archive::SearchOptions search; - ArchiveEntry* other = nullptr; - wxString overrides = ""; - size_t count = 0; + ArchiveEntry* other = nullptr; + wxString overrides = ""; + size_t count = 0; // Go through list for (auto& entry : entries) @@ -465,9 +465,9 @@ bool archiveoperations::checkOverriddenEntriesInIWAD(Archive* archive) // Find all texture entries - std::unordered_map braTextureEntries; - std::unordered_multimap> duplicate_texture_entries; - std::set found_duplicate_textures; + std::unordered_map braTextureEntries; + std::unordered_multimap> duplicate_texture_entries; + std::set found_duplicate_textures; Archive::SearchOptions pnamesopt; pnamesopt.match_type = EntryType::fromId("pnames"); @@ -501,7 +501,7 @@ bool archiveoperations::checkOverriddenEntriesInIWAD(Archive* archive) } // If we ended up not loading textures from base resource archive - if (!braTextureEntries.size()) + if (braTextureEntries.empty()) { log::error("Base resource archive has no texture entries to compare against"); return true; @@ -515,9 +515,8 @@ bool archiveoperations::checkOverriddenEntriesInIWAD(Archive* archive) if (pnames) ptable.loadPNAMES(pnames); - auto processTextureList = [&found_duplicate_textures, - &duplicate_texture_entries, - &braTextureEntries](ArchiveEntry* textureEntry, TextureXList& textureList) + auto processTextureList = [&found_duplicate_textures, &duplicate_texture_entries, &braTextureEntries]( + ArchiveEntry* textureEntry, TextureXList& textureList) { for (unsigned a = 0; a < textureList.textures().size(); a++) { @@ -555,11 +554,11 @@ bool archiveoperations::checkOverriddenEntriesInIWAD(Archive* archive) processTextureList(textureEntry, textureList); } - if (found_duplicate_textures.size()) + if (!found_duplicate_textures.empty()) { wxString dups = ""; - for (string duplicate_entry : found_duplicate_textures) + for (const string& duplicate_entry : found_duplicate_textures) { dups += wxString::Format("\n%s", duplicate_entry); @@ -569,17 +568,18 @@ bool archiveoperations::checkOverriddenEntriesInIWAD(Archive* archive) ++entry_iter) { ArchiveEntry* duplicated_entry = entry_iter->second.first; - ArchiveEntry* bra_entry = entry_iter->second.second; - dups += wxString::Format("\n\tThis Archive Asset Path: %s%s", duplicated_entry->path(), duplicated_entry->name()); + ArchiveEntry* bra_entry = entry_iter->second.second; + dups += wxString::Format( + "\n\tThis Archive Asset Path: %s%s", duplicated_entry->path(), duplicated_entry->name()); dups += wxString::Format("\n\tIwad Asset Path: %s%s", bra_entry->path(), bra_entry->name()); } } // Display list of duplicate entry names - ExtMessageDialog msg(theMainWindow, "Overridden Texture Entries"); - msg.setExt(dups); - msg.setMessage("The following textures are overridden:"); - msg.ShowModal(); + ExtMessageDialog msg_dialog(theMainWindow, "Overridden Texture Entries"); + msg_dialog.setExt(dups); + msg_dialog.setMessage("The following textures are overridden:"); + msg_dialog.ShowModal(); } else { @@ -595,10 +595,10 @@ bool archiveoperations::checkOverriddenEntriesInIWAD(Archive* archive) // ----------------------------------------------------------------------------- // Checks entries of the same name from the base resource archive. Also checks // texture definitions. This helps know what your archive overrides. -// This is a ZDoom version that has additional behavior for checking across +// This is a ZDoom version that has additional behavior for checking across // flats, patches, and other assets. // ----------------------------------------------------------------------------- -bool archiveoperations::checkZDoomOverriddenEntriesInIWAD(Archive* archive) +bool archiveoperations::checkZDoomOverriddenEntriesInIWAD(Archive* archive) { // Do nothing if there is no base resource archive, // or if the archive *is* the base resource archive. @@ -616,7 +616,7 @@ bool archiveoperations::checkZDoomOverriddenEntriesInIWAD(Archive* archive) auto braPnames = bra->findLast(pnames_opt); - auto process_entries = [&archiveTexEntries](const vector archive_entries) + auto process_entries = [&archiveTexEntries](const vector& archive_entries) { for (auto& archive_entry : archive_entries) { @@ -632,7 +632,7 @@ bool archiveoperations::checkZDoomOverriddenEntriesInIWAD(Archive* archive) auto process_patch_table = [&archiveTexEntries](ArchiveEntry* pnames_entry, const PatchTable& patch_table) { - for (int patchIndex = 0; patchIndex < patch_table.nPatches(); ++patchIndex) + for (int patchIndex = 0; patchIndex < patch_table.nPatches(); ++patchIndex) { string patch_name = string(patch_table.patchName(patchIndex)); patch_name = strutil::upperIP(patch_name); @@ -641,8 +641,7 @@ bool archiveoperations::checkZDoomOverriddenEntriesInIWAD(Archive* archive) } }; - auto process_texture_list = - [&archiveTexEntries](ArchiveEntry* texture_archive_entry, TextureXList& texture_list) + auto process_texture_list = [&archiveTexEntries](ArchiveEntry* texture_archive_entry, TextureXList& texture_list) { for (unsigned texture_index = 0; texture_index < texture_list.size(); texture_index++) { @@ -673,7 +672,7 @@ bool archiveoperations::checkZDoomOverriddenEntriesInIWAD(Archive* archive) process_entries(archive->findAll(search_opt)); } - auto pnames = archive->findLast(pnames_opt); + auto pnames = archive->findLast(pnames_opt); // Load patch table if (pnames) @@ -682,7 +681,7 @@ bool archiveoperations::checkZDoomOverriddenEntriesInIWAD(Archive* archive) ptable.loadPNAMES(pnames); // Don't process the patch table if we loaded it from the iWad - if (pnames != braPnames) + if (pnames != braPnames) { process_patch_table(pnames, ptable); } @@ -715,7 +714,7 @@ bool archiveoperations::checkZDoomOverriddenEntriesInIWAD(Archive* archive) } auto process_bra_entries = [&archiveTexEntries, &overiddenBraTexEntries, &overiddenBraTexNames, &braPnames]( - const vector archive_entries) + const vector& archive_entries) { for (auto& archive_entry : archive_entries) { @@ -774,8 +773,7 @@ bool archiveoperations::checkZDoomOverriddenEntriesInIWAD(Archive* archive) auto iter = archiveTexEntries.find(texture_name); // If the duplicate is the bra pnames, don't mark it as overridden - if (iter != archiveTexEntries.end() - && iter->second != braPnames) + if (iter != archiveTexEntries.end() && iter->second != braPnames) { overiddenBraTexEntries.emplace(texture_name, texture_archive_entry); overiddenBraTexNames.insert(texture_name); @@ -840,7 +838,7 @@ bool archiveoperations::checkZDoomOverriddenEntriesInIWAD(Archive* archive) wxString dups = ""; - for (string overriddenTexName : overiddenBraTexNames) + for (const string& overriddenTexName : overiddenBraTexNames) { dups += wxString::Format("\n%s", overriddenTexName); @@ -1396,7 +1394,7 @@ void archiveoperations::removeUnusedZDoomTextures(Archive* archive) // from the heap and we get huge memory issues while referencing a dangling pointer auto ptr_archive = archive->formatId() == "folder" ? app::archiveManager().openDirArchive(archive->filename(), false, true) : - app::archiveManager().openArchive(archive->filename(), false, true); + app::archiveManager().openArchive(archive->filename(), false, true); archive = ptr_archive.get(); // --- Build list of used textures --- @@ -1821,8 +1819,9 @@ void archiveoperations::removeUnusedZDoomTextures(Archive* archive) wxMessageBox(wxString::Format("Removed %d unused flats", n_removed)); - auto process_texture_list = [archive, &used_textures, &exclude_tex, &unused_tex, &selection, &n_removed]( - ArchiveEntry* texture_archive_entry, TextureXList& texture_list, PatchTable* ptable) + auto process_texture_list = + [archive, &used_textures, &exclude_tex, &unused_tex, &selection, &n_removed]( + ArchiveEntry* texture_archive_entry, TextureXList& texture_list, const PatchTable* ptable) { for (unsigned texture_index = 0; texture_index < texture_list.size(); texture_index++) { @@ -1934,12 +1933,12 @@ void archiveoperations::removeUnusedZDoomTextures(Archive* archive) app::archiveManager().closeArchive(archive); } -bool archiveoperations::checkDuplicateZDoomTextures(Archive* archive) +bool archiveoperations::checkDuplicateZDoomTextures(Archive* archive) { std::unordered_multimap found_entries; - std::set found_duplicates; + std::set found_duplicates; - auto process_entries = [&found_entries, &found_duplicates](const vector archive_entries) + auto process_entries = [&found_entries, &found_duplicates](const vector& archive_entries) { for (auto& archive_entry : archive_entries) { @@ -1947,7 +1946,7 @@ bool archiveoperations::checkDuplicateZDoomTextures(Archive* archive) if (archive_entry->size() == 0) continue; - string entry_name{archive_entry->upperNameNoExt()}; + string entry_name{ archive_entry->upperNameNoExt() }; if (found_entries.find(entry_name) != found_entries.end()) { @@ -1975,8 +1974,8 @@ bool archiveoperations::checkDuplicateZDoomTextures(Archive* archive) } }; - auto process_texture_list = [&found_entries, &found_duplicates]( - ArchiveEntry* texture_archive_entry, TextureXList& texture_list) + auto process_texture_list = + [&found_entries, &found_duplicates](ArchiveEntry* texture_archive_entry, TextureXList& texture_list) { for (unsigned texture_index = 0; texture_index < texture_list.size(); texture_index++) { @@ -1987,7 +1986,7 @@ bool archiveoperations::checkDuplicateZDoomTextures(Archive* archive) auto texture = texture_list.texture(texture_index); string texture_name = string(texture->name()); - texture_name = strutil::upperIP(texture_name); + texture_name = strutil::upperIP(texture_name); if (found_entries.find(texture_name) != found_entries.end()) { @@ -1999,7 +1998,7 @@ bool archiveoperations::checkDuplicateZDoomTextures(Archive* archive) }; // Find all textures - { + { Archive::SearchOptions search_opt; search_opt.match_namespace = "textures"; process_entries(archive->findAll(search_opt)); @@ -2016,7 +2015,7 @@ bool archiveoperations::checkDuplicateZDoomTextures(Archive* archive) pnames_opt.match_type = EntryType::fromId("pnames"); auto pnames = archive->findLast(pnames_opt); - // Load patch table + // Load patch table if (pnames) { PatchTable ptable; @@ -2051,7 +2050,7 @@ bool archiveoperations::checkDuplicateZDoomTextures(Archive* archive) } } - if (found_duplicates.empty()) + if (found_duplicates.empty()) { wxMessageBox("No duplicated textures exist"); return false; @@ -2059,14 +2058,14 @@ bool archiveoperations::checkDuplicateZDoomTextures(Archive* archive) wxString dups = ""; - for (string duplicate_entry : found_duplicates) + for (const string& duplicate_entry : found_duplicates) { dups += wxString::Format("\n%s", duplicate_entry); auto duplicated_entries_range = found_entries.equal_range(duplicate_entry); for (auto entry_iter = duplicated_entries_range.first; entry_iter != duplicated_entries_range.second; - ++entry_iter) + ++entry_iter) { ArchiveEntry* duplicated_entry = entry_iter->second; dups += wxString::Format("\n\t%s%s", duplicated_entry->path(), duplicated_entry->name()); @@ -2100,7 +2099,7 @@ bool archiveoperations::checkDuplicateZDoomPatches(Archive* archive) for (const PatchTable::Patch& patch_entry : ptable.patches()) { string entry_name = string(patch_entry.name); - entry_name = strutil::upperIP(entry_name); + entry_name = strutil::upperIP(entry_name); if (found_entries.find(entry_name) != found_entries.end()) { @@ -2141,7 +2140,7 @@ bool archiveoperations::checkDuplicateZDoomPatches(Archive* archive) wxString dups = ""; - for (string duplicate_entry : found_duplicates) + for (const string& duplicate_entry : found_duplicates) { dups += wxString::Format("\n%s", duplicate_entry); @@ -2275,7 +2274,7 @@ size_t replaceThingsHexen(ArchiveEntry* entry, int oldtype, int newtype) return changed; } -size_t replaceThingsUDMF(ArchiveEntry* entry, int oldtype, int newtype) +size_t replaceThingsUDMF(const ArchiveEntry* entry, int oldtype, int newtype) { if (entry == nullptr) return 0; @@ -2363,11 +2362,11 @@ size_t archiveoperations::replaceThings(Archive* archive, int oldtype, int newty { switch (map.format) { - case MapFormat::Doom: achanged = replaceThingsDoom(things, oldtype, newtype); break; - case MapFormat::Hexen: achanged = replaceThingsHexen(things, oldtype, newtype); break; + case MapFormat::Doom: achanged = replaceThingsDoom(things, oldtype, newtype); break; + case MapFormat::Hexen: achanged = replaceThingsHexen(things, oldtype, newtype); break; case MapFormat::Doom64: achanged = replaceThingsDoom64(things, oldtype, newtype); break; - case MapFormat::UDMF: achanged = replaceThingsUDMF(things, oldtype, newtype); break; - default: log::warning("Unknown map format for " + m_head->name()); break; + case MapFormat::UDMF: achanged = replaceThingsUDMF(things, oldtype, newtype); break; + default: log::warning("Unknown map format for " + m_head->name()); break; } } } @@ -2407,7 +2406,7 @@ CONSOLE_COMMAND(convertmapchex1to3, 0, false) { 54, 9058 }, // 10 ChexBananaTree ==> TreeBanana (PropSpaceship -- must go before its own // replacement) { 48, - 54 }, // 11 ChexSpaceship ==> PropSpaceship (PropTechPillar -- must go after banana tree + 54 }, // 11 ChexSpaceship ==> PropSpaceship (PropTechPillar -- must go after banana tree // replacement) { 55, 42 }, // 12 ChexLightColumn ==> LabCoil (PropShortBlueTorch) { 56, 26 }, // 13 ChexCivilian2 ==> PropCaptive2 (PropShortGreenTorch) @@ -2415,7 +2414,7 @@ CONSOLE_COMMAND(convertmapchex1to3, 0, false) { 3002, 58 }, // 15 F.CycloptisCommonus ==> F.CycloptisCommonusV3 (FlemoidusStridicus) { 3003, 69 }, // 16 Flembrane ==> FlembraneV3 (FlemoidusMaximus) { 33, - 53 }, // 17 ChexMineCart ==> PropBazoikCart (none, but the sprite is modified otherwise) + 53 }, // 17 ChexMineCart ==> PropBazoikCart (none, but the sprite is modified otherwise) { 27, 81 }, // 18 "HeadOnAStick" ==> PropSmallBrush { 53, 75 }, // 19 "Meat5" ==> PropStalagtite2 { 49, 63 }, // 20 Redundant bats @@ -2609,24 +2608,24 @@ size_t replaceSpecialsHexen( return changed; } size_t replaceSpecialsUDMF( - ArchiveEntry* entry, - int oldtype, - int newtype, - bool arg0, - bool arg1, - bool arg2, - bool arg3, - bool arg4, - int oldarg0, - int oldarg1, - int oldarg2, - int oldarg3, - int oldarg4, - int newarg0, - int newarg1, - int newarg2, - int newarg3, - int newarg4) + const ArchiveEntry* entry, + int oldtype, + int newtype, + bool arg0, + bool arg1, + bool arg2, + bool arg3, + bool arg4, + int oldarg0, + int oldarg1, + int oldarg2, + int oldarg3, + int oldarg4, + int newarg0, + int newarg1, + int newarg2, + int newarg3, + int newarg4) { if (entry == nullptr) return 0; @@ -2849,10 +2848,10 @@ CONSOLE_COMMAND(replacespecials, 2, true) { case 12: arg4 = strutil::toInt(args[oldtail--], oldarg4) && strutil::toInt(args[newtail--], newarg4); case 10: arg3 = strutil::toInt(args[oldtail--], oldarg3) && strutil::toInt(args[newtail--], newarg3); - case 8: arg2 = strutil::toInt(args[oldtail--], oldarg2) && strutil::toInt(args[newtail--], newarg2); - case 6: arg1 = strutil::toInt(args[oldtail--], oldarg1) && strutil::toInt(args[newtail--], newarg1); - case 4: arg0 = strutil::toInt(args[oldtail--], oldarg0) && strutil::toInt(args[newtail--], newarg0); - case 2: run = strutil::toInt(args[oldtail--], oldtype) && strutil::toInt(args[newtail--], newtype); break; + case 8: arg2 = strutil::toInt(args[oldtail--], oldarg2) && strutil::toInt(args[newtail--], newarg2); + case 6: arg1 = strutil::toInt(args[oldtail--], oldarg1) && strutil::toInt(args[newtail--], newarg1); + case 4: arg0 = strutil::toInt(args[oldtail--], oldarg0) && strutil::toInt(args[newtail--], newarg0); + case 2: run = strutil::toInt(args[oldtail--], oldtype) && strutil::toInt(args[newtail--], newtype); break; default: log::warning(wxString::Format("Invalid number of arguments: %d", fullarg)); } } @@ -3083,14 +3082,14 @@ size_t replaceWallsDoom64( return changed; } size_t replaceTexturesUDMF( - ArchiveEntry* entry, - const wxString& oldtex, - const wxString& newtex, - bool floor, - bool ceiling, - bool lower, - bool middle, - bool upper) + const ArchiveEntry* entry, + const wxString& oldtex, + const wxString& newtex, + bool floor, + bool ceiling, + bool lower, + bool middle, + bool upper) { if (entry == nullptr) return 0; diff --git a/src/MainEditor/ArchiveOperations.h b/src/MainEditor/ArchiveOperations.h index c2042d2a3..bde3ade0b 100644 --- a/src/MainEditor/ArchiveOperations.h +++ b/src/MainEditor/ArchiveOperations.h @@ -1,6 +1,9 @@ #pragma once -#include "Archive/Archive.h" +namespace slade +{ +class Archive; +} namespace slade::archiveoperations { @@ -23,8 +26,8 @@ bool checkZDoomOverriddenEntriesInIWAD(Archive* archive); size_t replaceThings(Archive* archive, int oldtype, int newtype); size_t replaceTextures( Archive* archive, - const wxString& oldname, - const wxString& newname, + const wxString& oldtex, + const wxString& newtex, bool floor = false, bool ceiling = false, bool lower = false, diff --git a/src/MainEditor/BinaryControlLump.h b/src/MainEditor/BinaryControlLump.h index c73e5b7dd..30dc5e0c7 100644 --- a/src/MainEditor/BinaryControlLump.h +++ b/src/MainEditor/BinaryControlLump.h @@ -13,11 +13,11 @@ namespace slade namespace animtype { - static const int FLAT = 0; - static const int TEXTURE = 1; - static const int MASK = 1; - static const int DECALS = 2; // ZDoom uses bit 1 to flag whether decals are allowed. - static const int STOP = 255; + static constexpr int FLAT = 0; + static constexpr int TEXTURE = 1; + static constexpr int MASK = 1; + static constexpr int DECALS = 2; // ZDoom uses bit 1 to flag whether decals are allowed. + static constexpr int STOP = 255; } // namespace animtype // The format of an entry in an ANIMATED lump @@ -35,11 +35,11 @@ struct AnimatedEntry namespace switchtype { - static const int STOP = wxINT16_SWAP_ON_BE(0); - static const int DEMO = wxINT16_SWAP_ON_BE(1); - static const int FULL = wxINT16_SWAP_ON_BE(2); - static const int COMM = wxINT16_SWAP_ON_BE(3); - static const int OOPS = wxINT16_SWAP_ON_BE(4); + static constexpr int STOP = wxINT16_SWAP_ON_BE(0); + static constexpr int DEMO = wxINT16_SWAP_ON_BE(1); + static constexpr int FULL = wxINT16_SWAP_ON_BE(2); + static constexpr int COMM = wxINT16_SWAP_ON_BE(3); + static constexpr int OOPS = wxINT16_SWAP_ON_BE(4); } // namespace switchtype struct SwitchesEntry diff --git a/src/MainEditor/Conversions.cpp b/src/MainEditor/Conversions.cpp index 0d8bb2d8f..77243c04b 100644 --- a/src/MainEditor/Conversions.cpp +++ b/src/MainEditor/Conversions.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -215,7 +215,7 @@ uint8_t stereoToMono(uint8_t left, uint8_t right) val /= 2; if (val > 255) val = 255; - return (uint8_t)val; + return static_cast(val); } // The following two functions are adapted from Sun Microsystem's g711.cpp code. @@ -235,8 +235,8 @@ int16_t alawToLinear(uint8_t alaw) seg = (alaw & SEG_MASK) >> SEG_SHIFT; switch (seg) { - case 0: t += 8; break; - case 1: t += 0x108; break; + case 0: t += 8; break; + case 1: t += 0x108; break; default: t += 0x108; t <<= seg - 1; } return ((alaw & SIGN_BIT) ? t : -t); @@ -430,11 +430,11 @@ bool conversion::wavToDoomSnd(const MemChunk& in, MemChunk& out) // Warn if (wavbps > 1 || wavfmt != WAV_PCM || fmtchunk.channels == 2) { - if (!(wxMessageBox( - "Warning: conversion will result in loss of metadata and audio quality. Do you wish to proceed?", - "Conversion warning", - wxOK | wxCANCEL) - == wxOK)) + if (wxMessageBox( + "Warning: conversion will result in loss of metadata and audio quality. Do you wish to proceed?", + "Conversion warning", + wxOK | wxCANCEL) + != wxOK) { global::error = "Conversion aborted by user"; return false; @@ -480,7 +480,7 @@ bool conversion::wavToDoomSnd(const MemChunk& in, MemChunk& out) else if (wavbps == 3) data[i] = pcm24to8bits(val); else if (wavbps == 2) - data[i] = pcm16to8bits((int16_t)val); + data[i] = pcm16to8bits(static_cast(val)); } } @@ -647,6 +647,7 @@ bool conversion::vocToWav(const MemChunk& in, MemChunk& out) } datasize += blocksize - 12; break; + default: break; } i += blocksize; } @@ -1262,6 +1263,7 @@ bool conversion::auSndToWav(const MemChunk& in, MemChunk& out) samples[i * 4 + 2] = samples[i * 4 + 1]; samples[i * 4 + 1] = swapval; break; + default: break; } } } @@ -1308,7 +1310,7 @@ bool conversion::auSndToWav(const MemChunk& in, MemChunk& out) bool conversion::voxToKvx(const MemChunk& in, MemChunk& out) { -#define AT(x, y, z) (((x)*length + (y)) * height + (z)) +#define AT(x, y, z) (((x) * length + (y)) * height + (z)) constexpr uint8_t LEFT = 1; constexpr uint8_t RIGHT = 2; diff --git a/src/MainEditor/EntryOperations.cpp b/src/MainEditor/EntryOperations.cpp index 35e9ccaff..ac69a8ad3 100644 --- a/src/MainEditor/EntryOperations.cpp +++ b/src/MainEditor/EntryOperations.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -38,6 +38,7 @@ #include "BinaryControlLump.h" #include "General/Console.h" #include "General/Misc.h" +#include "Graphics/CTexture/TextureXList.h" #include "Graphics/Graphics.h" #include "Graphics/SImage/SIFormat.h" #include "MainEditor/MainEditor.h" diff --git a/src/MainEditor/ExternalEditManager.cpp b/src/MainEditor/ExternalEditManager.cpp index ea474909f..a97d18d00 100644 --- a/src/MainEditor/ExternalEditManager.cpp +++ b/src/MainEditor/ExternalEditManager.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -60,7 +60,10 @@ class ExternalEditFileMonitor : public FileMonitor { public: ExternalEditFileMonitor(ArchiveEntry& entry, ExternalEditManager* manager) : - FileMonitor("", false), entry_(&entry), archive_{ entry.parent() }, manager_(manager) + FileMonitor("", false), + entry_(&entry), + archive_{ entry.parent() }, + manager_(manager) { // Stop monitoring if the entry is removed sc_entry_removed_ = archive_->signals().entry_removed.connect( @@ -190,7 +193,6 @@ class GfxExternalFileMonitor : public ExternalEditFileMonitor } private: - string gfx_format_; Vec2i offsets_; Palette palette_; }; @@ -273,7 +275,8 @@ class SfxExternalFileMonitor : public ExternalEditFileMonitor { public: SfxExternalFileMonitor(ArchiveEntry& entry, ExternalEditManager* manager) : - ExternalEditFileMonitor(entry, manager), doom_sound_(true) + ExternalEditFileMonitor(entry, manager), + doom_sound_(true) { } ~SfxExternalFileMonitor() override = default; @@ -432,7 +435,7 @@ bool ExternalEditManager::openEntryExternal(ArchiveEntry& entry, string_view edi } // Run external editor - auto command = fmt::format("\"{}\" \"{}\"", exe_path, monitor->filename()); + auto command = fmt::format(R"("{}" "{}")", exe_path, monitor->filename()); long success = wxExecute(command, wxEXEC_ASYNC, monitor->process()); if (success == 0) { diff --git a/src/MainEditor/MainEditor.cpp b/src/MainEditor/MainEditor.cpp index 4b68691b3..cd33f4035 100644 --- a/src/MainEditor/MainEditor.cpp +++ b/src/MainEditor/MainEditor.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -113,7 +113,7 @@ vector maineditor::currentEntrySelection() // ----------------------------------------------------------------------------- // Opens the texture editor for the current archive tab // ----------------------------------------------------------------------------- -void maineditor::openTextureEditor(Archive* archive, ArchiveEntry* entry) +void maineditor::openTextureEditor(const Archive* archive, const ArchiveEntry* entry) { main_window->archiveManagerPanel()->openTextureTab(app::archiveManager().archiveIndex(archive), entry); } @@ -129,7 +129,7 @@ void maineditor::openMapEditor(Archive* archive) // ----------------------------------------------------------------------------- // Shows the tab for [archive], opening a new tab for it if needed // ----------------------------------------------------------------------------- -void ::maineditor::openArchiveTab(Archive* archive) +void ::maineditor::openArchiveTab(const Archive* archive) { main_window->archiveManagerPanel()->openTab(archive); } diff --git a/src/MainEditor/MainEditor.h b/src/MainEditor/MainEditor.h index ff13e740e..99b2ab527 100644 --- a/src/MainEditor/MainEditor.h +++ b/src/MainEditor/MainEditor.h @@ -34,9 +34,9 @@ namespace maineditor ArchivePanel* currentArchivePanel(); EntryPanel* currentEntryPanel(); - void openTextureEditor(Archive* archive, ArchiveEntry* entry = nullptr); + void openTextureEditor(const Archive* archive, const ArchiveEntry* entry = nullptr); void openMapEditor(Archive* archive); - void openArchiveTab(Archive* archive); + void openArchiveTab(const Archive* archive); void openEntry(ArchiveEntry* entry); bool saveArchiveAs(Archive* archive); diff --git a/src/MainEditor/UI/ArchiveManagerPanel.cpp b/src/MainEditor/UI/ArchiveManagerPanel.cpp index b09694f29..1c54c97dc 100644 --- a/src/MainEditor/UI/ArchiveManagerPanel.cpp +++ b/src/MainEditor/UI/ArchiveManagerPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -49,8 +49,8 @@ #include "UI/Controls/STabCtrl.h" #include "UI/Dialogs/DirArchiveUpdateDialog.h" #include "UI/Dialogs/NewArchiveDiaog.h" +#include "UI/Lists/ListView.h" #include "UI/WxUtils.h" -#include "Utility/FileUtils.h" #include "Utility/StringUtils.h" using namespace slade; @@ -111,7 +111,7 @@ DirArchiveCheck::DirArchiveCheck(wxEvtHandler* handler, DirArchive* archive) : // ----------------------------------------------------------------------------- // Register a change to a file, as long as it hasn't been ignored // ----------------------------------------------------------------------------- -void DirArchiveCheck::addChange(DirEntryChange change) +void DirArchiveCheck::addChange(const DirEntryChange& change) { if (!dynamic_cast(change_list_.archive)->shouldIgnoreEntryChange(change)) change_list_.changes.push_back(change); @@ -225,7 +225,8 @@ wxThread::ExitCode DirArchiveCheck::Entry() // the filters are always shown if any are defined. // ----------------------------------------------------------------------------- WMFileBrowser::WMFileBrowser(wxWindow* parent, ArchiveManagerPanel* wm, int id) : - wxGenericDirCtrl(parent, id, wxDirDialogDefaultFolderStr), parent{ wm } + wxGenericDirCtrl(parent, id, wxDirDialogDefaultFolderStr), + parent{ wm } { // Connect a custom event for when an item in the file tree is activated auto tree_ctrl = wxGenericDirCtrl::GetTreeCtrl(); @@ -263,7 +264,8 @@ void WMFileBrowser::onItemActivated(wxTreeEvent& e) // ArchiveManagerPanel class constructor // ----------------------------------------------------------------------------- ArchiveManagerPanel::ArchiveManagerPanel(wxWindow* parent, STabCtrl* nb_archives) : - DockPanel(parent), stc_archives_{ nb_archives } + DockPanel(parent), + stc_archives_{ nb_archives } { // Create main sizer auto vbox = new wxBoxSizer(wxVERTICAL); @@ -272,7 +274,7 @@ ArchiveManagerPanel::ArchiveManagerPanel(wxWindow* parent, STabCtrl* nb_archives // Create/setup tabs stc_tabs_ = new STabCtrl(this, false); stc_tabs_->SetInitialSize(wxSize(ui::scalePx(224), -1)); - vbox->Add(stc_tabs_, 1, wxEXPAND | wxALL, ui::pad()); + vbox->Add(stc_tabs_, wxutil::sfWithBorder(1).Expand()); // Open archives tab panel_am_ = new wxPanel(stc_tabs_); @@ -302,7 +304,7 @@ ArchiveManagerPanel::ArchiveManagerPanel(wxWindow* parent, STabCtrl* nb_archives } list_bookmarks_->SetImageList(bm_image_list, wxIMAGE_LIST_SMALL); menu_bookmarks_ = new wxMenu(); - panel_bm->GetSizer()->Add(list_bookmarks_, 1, wxEXPAND | wxALL, ui::pad()); + panel_bm->GetSizer()->Add(list_bookmarks_, wxutil::sfWithBorder(1).Expand()); refreshBookmarkList(); stc_tabs_->AddPage(panel_bm, "Bookmarks", true); @@ -314,7 +316,7 @@ ArchiveManagerPanel::ArchiveManagerPanel(wxWindow* parent, STabCtrl* nb_archives auto panel = new wxPanel(stc_tabs_); panel->SetSizer(new wxBoxSizer(wxVERTICAL)); file_browser_ = new WMFileBrowser(panel, this, -1); - panel->GetSizer()->Add(file_browser_, 1, wxEXPAND | wxALL, ui::pad()); + panel->GetSizer()->Add(file_browser_, wxutil::sfWithBorder(1).Expand()); stc_tabs_->AddPage(panel, "File Browser"); } @@ -352,9 +354,9 @@ void ArchiveManagerPanel::createArchivesPanel() panel_archives_ = new wxPanel(panel_am_, -1); auto vbox = new wxBoxSizer(wxVERTICAL); panel_archives_->SetSizer(vbox); - vbox->Add(new wxStaticText(panel_archives_, -1, "Open Archives:"), 0, wxEXPAND); + vbox->Add(new wxStaticText(panel_archives_, -1, "Open Archives:"), wxSizerFlags().Expand()); list_archives_ = new ListView(panel_archives_, -1); - vbox->Add(list_archives_, 1, wxEXPAND | wxTOP, ui::px(ui::Size::PadMinimum)); + vbox->Add(list_archives_, wxutil::sfWithMinBorder(1, wxTOP).Expand()); } // ----------------------------------------------------------------------------- @@ -365,9 +367,9 @@ void ArchiveManagerPanel::createRecentPanel() panel_rf_ = new wxPanel(panel_am_, -1); auto vbox = new wxBoxSizer(wxVERTICAL); panel_rf_->SetSizer(vbox); - vbox->Add(new wxStaticText(panel_rf_, -1, "Recent Files:"), 0, wxEXPAND); + vbox->Add(new wxStaticText(panel_rf_, -1, "Recent Files:"), wxSizerFlags().Expand()); list_recent_ = new ListView(panel_rf_, -1); - vbox->Add(list_recent_, 1, wxEXPAND | wxTOP, ui::px(ui::Size::PadMinimum)); + vbox->Add(list_recent_, wxutil::sfWithMinBorder(1, wxTOP).Expand()); // Setup image list auto list = wxutil::createSmallImageList(); @@ -387,8 +389,8 @@ void ArchiveManagerPanel::layoutNormal() auto vbox = new wxBoxSizer(wxVERTICAL); panel_am_->SetSizer(vbox); - vbox->Add(panel_archives_, 1, wxEXPAND | wxALL, ui::pad()); - vbox->Add(panel_rf_, 1, wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, ui::pad()); + vbox->Add(panel_archives_, wxutil::sfWithBorder(1).Expand()); + vbox->Add(panel_rf_, wxutil::sfWithBorder(1, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); } // ----------------------------------------------------------------------------- @@ -400,8 +402,8 @@ void ArchiveManagerPanel::layoutHorizontal() auto hbox = new wxBoxSizer(wxHORIZONTAL); panel_am_->SetSizer(hbox); - hbox->Add(panel_archives_, 1, wxEXPAND | wxALL, ui::pad()); - hbox->Add(panel_rf_, 1, wxEXPAND | wxTOP | wxRIGHT | wxBOTTOM, ui::pad()); + hbox->Add(panel_archives_, wxutil::sfWithBorder(1).Expand()); + hbox->Add(panel_rf_, wxutil::sfWithBorder(1, wxTOP | wxRIGHT | wxBOTTOM).Expand()); } // ----------------------------------------------------------------------------- @@ -596,7 +598,7 @@ void ArchiveManagerPanel::updateArchiveTabTitle(int index) const // ----------------------------------------------------------------------------- // Updates the title of the tab for [entry] // ----------------------------------------------------------------------------- -void ArchiveManagerPanel::updateEntryTabTitle(ArchiveEntry* entry) const +void ArchiveManagerPanel::updateEntryTabTitle(const ArchiveEntry* entry) const { for (unsigned i = 0; i < stc_archives_->GetPageCount(); ++i) { @@ -623,7 +625,7 @@ void ArchiveManagerPanel::updateEntryTabTitle(ArchiveEntry* entry) const bool ArchiveManagerPanel::isArchiveTab(int tab_index) const { // Check that tab index is in range - if ((unsigned)tab_index >= stc_archives_->GetPageCount()) + if (static_cast(tab_index) >= stc_archives_->GetPageCount()) return false; // Check the page's name @@ -637,7 +639,7 @@ bool ArchiveManagerPanel::isArchiveTab(int tab_index) const bool ArchiveManagerPanel::isEntryTab(int tab_index) const { // Check that tab index is in range - if ((unsigned)tab_index >= stc_archives_->GetPageCount()) + if (static_cast(tab_index) >= stc_archives_->GetPageCount()) return false; // Check the page's name @@ -651,7 +653,7 @@ bool ArchiveManagerPanel::isEntryTab(int tab_index) const bool ArchiveManagerPanel::isTextureEditorTab(int tab_index) const { // Check that tab index is in range - if ((unsigned)tab_index >= stc_archives_->GetPageCount()) + if (static_cast(tab_index) >= stc_archives_->GetPageCount()) return false; // Check the page's name @@ -665,7 +667,7 @@ bool ArchiveManagerPanel::isTextureEditorTab(int tab_index) const Archive* ArchiveManagerPanel::archiveForTab(int tab_index) const { // Check the index is valid - if (tab_index < 0 || (unsigned)tab_index >= stc_archives_->GetPageCount()) + if (tab_index < 0 || static_cast(tab_index) >= stc_archives_->GetPageCount()) return nullptr; // Check the specified tab is actually an archive tab @@ -803,7 +805,7 @@ void ArchiveManagerPanel::openTab(int archive_index) const // ----------------------------------------------------------------------------- // Returns the ArchivePanel for [archive], or null if none is open // ----------------------------------------------------------------------------- -ArchivePanel* ArchiveManagerPanel::tabForArchive(Archive* archive) const +ArchivePanel* ArchiveManagerPanel::tabForArchive(const Archive* archive) const { // Check archive was given if (!archive) @@ -829,7 +831,7 @@ ArchivePanel* ArchiveManagerPanel::tabForArchive(Archive* archive) const // ----------------------------------------------------------------------------- // Opens a new tab for the archive // ----------------------------------------------------------------------------- -void ArchiveManagerPanel::openTab(Archive* archive) const +void ArchiveManagerPanel::openTab(const Archive* archive) const { auto sp_archive = app::archiveManager().shareArchive(archive); if (sp_archive) @@ -888,7 +890,7 @@ void ArchiveManagerPanel::closeTab(int archive_index) const // Opens a new texture editor tab for the archive at [archive_index] in the // archive manager // ----------------------------------------------------------------------------- -void ArchiveManagerPanel::openTextureTab(int archive_index, ArchiveEntry* entry) const +void ArchiveManagerPanel::openTextureTab(int archive_index, const ArchiveEntry* entry) const { auto archive = app::archiveManager().getArchive(archive_index); @@ -984,7 +986,7 @@ void ArchiveManagerPanel::closeTextureTab(int archive_index) const // ----------------------------------------------------------------------------- // Redirects to the separated tab with given entry if exists // ----------------------------------------------------------------------------- -bool ArchiveManagerPanel::redirectToTab(ArchiveEntry* entry) const +bool ArchiveManagerPanel::redirectToTab(const ArchiveEntry* entry) const { for (unsigned a = 0; a < stc_archives_->GetPageCount(); a++) { @@ -1007,7 +1009,7 @@ bool ArchiveManagerPanel::redirectToTab(ArchiveEntry* entry) const // ----------------------------------------------------------------------------- // Returns true if [entry] is open in a tab // ----------------------------------------------------------------------------- -bool ArchiveManagerPanel::entryIsOpenInTab(ArchiveEntry* entry) const +bool ArchiveManagerPanel::entryIsOpenInTab(const ArchiveEntry* entry) const { for (unsigned a = 0; a < stc_archives_->GetPageCount(); a++) { @@ -1134,7 +1136,7 @@ void ArchiveManagerPanel::openEntryTab(ArchiveEntry* entry) const // ----------------------------------------------------------------------------- // Closes the EntryPanel tab for [entry] // ----------------------------------------------------------------------------- -void ArchiveManagerPanel::closeEntryTab(ArchiveEntry* entry) const +void ArchiveManagerPanel::closeEntryTab(const ArchiveEntry* entry) const { // Go through tabs for (unsigned a = 0; a < stc_archives_->GetPageCount(); a++) @@ -1158,7 +1160,7 @@ void ArchiveManagerPanel::closeEntryTab(ArchiveEntry* entry) const // ----------------------------------------------------------------------------- // Closes any EntryPanel tabs for entries in [parent] // ----------------------------------------------------------------------------- -void ArchiveManagerPanel::closeEntryTabs(Archive* parent) const +void ArchiveManagerPanel::closeEntryTabs(const Archive* parent) const { // Check archive was given if (!parent) @@ -1199,7 +1201,7 @@ void ArchiveManagerPanel::openFile(const wxString& filename) const auto new_archive = app::archiveManager().openArchive(filename.ToStdString()); sw.Pause(); - log::info(wxString::Format("Opening took %d ms", (int)sw.Time())); + log::info(wxString::Format("Opening took %d ms", static_cast(sw.Time()))); // Hide splash screen ui::hideSplash(); @@ -1241,7 +1243,7 @@ void ArchiveManagerPanel::openDirAsArchive(const wxString& dir) const auto new_archive = app::archiveManager().openDirArchive(dir.ToStdString()); sw.Pause(); - log::info(wxString::Format("Opening took %d ms", (int)sw.Time())); + log::info(wxString::Format("Opening took %d ms", static_cast(sw.Time()))); // Hide splash screen ui::hideSplash(); @@ -1441,7 +1443,7 @@ void ArchiveManagerPanel::createNewArchive(const wxString& format) const // If there are any unsaved entry changes in [archive]'s ArchivePanel tab, // saves the changes (or not, depending on user settings) // ----------------------------------------------------------------------------- -bool ArchiveManagerPanel::saveEntryChanges(Archive* archive) const +bool ArchiveManagerPanel::saveEntryChanges(const Archive* archive) const { bool changes = false; @@ -1735,7 +1737,7 @@ bool ArchiveManagerPanel::closeSelection() // Close all selected archives, starting from the last bool all_closed = true; - for (size_t a = selected_archives.size() - 1; (signed)a >= 0; --a) + for (size_t a = selected_archives.size() - 1; static_cast(a) >= 0; --a) { if (!closeArchive(selected_archives[a])) all_closed = false; @@ -1940,7 +1942,7 @@ bool ArchiveManagerPanel::handleAction(string_view id) void ArchiveManagerPanel::updateBookmarkListItem(int index) const { // Only valid indices - if (index < 0 || (unsigned)index >= app::archiveManager().numBookmarks()) + if (index < 0 || static_cast(index) >= app::archiveManager().numBookmarks()) return; auto entry = app::archiveManager().getBookmark(index); @@ -1960,9 +1962,9 @@ void ArchiveManagerPanel::updateBookmarkListItem(int index) const switch (entry->state()) { case ArchiveEntry::State::Unmodified: list_bookmarks_->setItemStatus(index, ItemStatus::Normal); break; - case ArchiveEntry::State::Modified: list_bookmarks_->setItemStatus(index, ItemStatus::Modified); break; - case ArchiveEntry::State::New: list_bookmarks_->setItemStatus(index, ItemStatus::New); break; - default: list_bookmarks_->setItemStatus(index, ItemStatus::Error); break; + case ArchiveEntry::State::Modified: list_bookmarks_->setItemStatus(index, ItemStatus::Modified); break; + case ArchiveEntry::State::New: list_bookmarks_->setItemStatus(index, ItemStatus::New); break; + default: list_bookmarks_->setItemStatus(index, ItemStatus::Error); break; } } @@ -1972,8 +1974,7 @@ void ArchiveManagerPanel::updateBookmarkListItem(int index) const void ArchiveManagerPanel::refreshBookmarkList() const { // Get first bookmark menu id - auto a_bookmark = SAction::fromId("aman_bookmark_menu"); - int id_bm_start = a_bookmark->wxId(); + auto a_bookmark = SAction::fromId("aman_bookmark_menu"); // Clear the list list_bookmarks_->ClearAll(); diff --git a/src/MainEditor/UI/ArchiveManagerPanel.h b/src/MainEditor/UI/ArchiveManagerPanel.h index e73081f01..0ec68c000 100644 --- a/src/MainEditor/UI/ArchiveManagerPanel.h +++ b/src/MainEditor/UI/ArchiveManagerPanel.h @@ -1,15 +1,17 @@ #pragma once -#include "Archive/Formats/DirArchive.h" #include "General/SAction.h" #include "General/Sigslot.h" #include "UI/Controls/DockPanel.h" -#include "UI/Lists/ListView.h" wxDECLARE_EVENT(wxEVT_COMMAND_DIRARCHIVECHECK_COMPLETED, wxThreadEvent); namespace slade { +class ListView; +class ArchiveEntry; +class DirArchive; +struct DirEntryChange; class ArchiveManagerPanel; class ArchivePanel; class Archive; @@ -44,7 +46,10 @@ class DirArchiveCheck : public wxThread const wxString& file_path = "", bool is_dir = false, time_t file_modified = 0) : - entry_path{ entry_path }, file_path{ file_path }, is_dir{ is_dir }, file_modified{ file_modified } + entry_path{ entry_path }, + file_path{ file_path }, + is_dir{ is_dir }, + file_modified{ file_modified } { } }; @@ -56,7 +61,7 @@ class DirArchiveCheck : public wxThread DirArchiveChangeList change_list_; bool ignore_hidden_ = true; - void addChange(DirEntryChange change); + void addChange(const DirEntryChange& change); }; class WMFileBrowser : public wxGenericDirCtrl @@ -94,7 +99,7 @@ class ArchiveManagerPanel : public DockPanel, SActionHandler void updateRecentListItem(int index) const; void updateBookmarkListItem(int index) const; void updateArchiveTabTitle(int index) const; - void updateEntryTabTitle(ArchiveEntry* entry) const; + void updateEntryTabTitle(const ArchiveEntry* entry) const; bool isArchiveTab(int tab_index) const; bool isEntryTab(int tab_index) const; bool isTextureEditorTab(int tab_index) const; @@ -109,20 +114,20 @@ class ArchiveManagerPanel : public DockPanel, SActionHandler vector currentEntrySelection() const; void openTab(int archive_index) const; - ArchivePanel* tabForArchive(Archive* archive) const; - void openTab(Archive* archive) const; + ArchivePanel* tabForArchive(const Archive* archive) const; + void openTab(const Archive* archive) const; void closeTab(int archive_index) const; - void openTextureTab(int archive_index, ArchiveEntry* entry = nullptr) const; + void openTextureTab(int archive_index, const ArchiveEntry* entry = nullptr) const; TextureXEditor* textureTabForArchive(int archive_index) const; void closeTextureTab(int archive_index) const; void openEntryTab(ArchiveEntry* entry) const; - void closeEntryTab(ArchiveEntry* entry) const; - void closeEntryTabs(Archive* parent) const; + void closeEntryTab(const ArchiveEntry* entry) const; + void closeEntryTabs(const Archive* parent) const; void openFile(const wxString& filename) const; void openFiles(const wxArrayString& files) const; void openDirAsArchive(const wxString& dir) const; - bool redirectToTab(ArchiveEntry* entry) const; - bool entryIsOpenInTab(ArchiveEntry* entry) const; + bool redirectToTab(const ArchiveEntry* entry) const; + bool entryIsOpenInTab(const ArchiveEntry* entry) const; void closeCurrentTab(); bool saveCurrentTab() const; @@ -131,7 +136,7 @@ class ArchiveManagerPanel : public DockPanel, SActionHandler bool redo() const; // Single archive actions - bool saveEntryChanges(Archive* archive) const; + bool saveEntryChanges(const Archive* archive) const; bool saveArchive(Archive* archive) const; bool saveArchiveAs(Archive* archive) const; bool beforeCloseArchive(Archive* archive); diff --git a/src/MainEditor/UI/ArchivePanel.cpp b/src/MainEditor/UI/ArchivePanel.cpp index f16842a65..bc942d957 100644 --- a/src/MainEditor/UI/ArchivePanel.cpp +++ b/src/MainEditor/UI/ArchivePanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -56,6 +56,7 @@ #include "MainEditor/ArchiveOperations.h" #include "MainEditor/Conversions.h" #include "MainEditor/EntryOperations.h" +#include "MainEditor/ExternalEditManager.h" #include "MainEditor/MainEditor.h" #include "MainEditor/UI/MainWindow.h" #include "MapEditor/MapEditor.h" @@ -252,9 +253,9 @@ class ChoosePaletteDialog : public wxDialog // Add choose pal_chooser_ = new PaletteChooser(this, -1); - sizer->Add(pal_chooser_, 0, wxEXPAND | wxALL, 4); + sizer->Add(pal_chooser_, wxutil::sfWithBorder().Expand()); - sizer->Add(CreateButtonSizer(wxOK | wxCANCEL), 0, wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, 4); + sizer->Add(CreateButtonSizer(wxOK | wxCANCEL), wxutil::sfWithBorder(0, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); // Init layout wxDialog::Layout(); @@ -280,7 +281,8 @@ class EntryTreeClipboardItem : public ClipboardItem { public: EntryTreeClipboardItem(const vector& entries, const vector& dirs) : - ClipboardItem(Type::EntryTree), tree_{ new ArchiveDir("") } + ClipboardItem(Type::EntryTree), + tree_{ new ArchiveDir("") } { // Copy entries for (auto& entry : entries) @@ -357,7 +359,7 @@ void initNamespaceVector(vector& ns, bool flathack) // Checks through a MapDesc vector and returns which one, if any, the entry // index is in, -1 otherwise // ----------------------------------------------------------------------------- -int isInMap(size_t index, const vector& maps) +int isInMap(size_t index, const vector& maps) { for (size_t m = 0; m < maps.size(); ++m) { @@ -381,11 +383,7 @@ int isInMap(size_t index, const vector& maps) // namespace vector. Also hacks around a bit to put less entries in the global // namespace and allow sorting a bit by categories. // ----------------------------------------------------------------------------- -size_t getNamespaceNumber( - const ArchiveEntry* entry, - size_t index, - vector& ns, - const vector& maps) +size_t getNamespaceNumber(const ArchiveEntry* entry, size_t index, vector& ns, const vector& maps) { auto ens = entry->parent()->detectNamespace(index); if (strutil::equalCI(ens, "global")) @@ -424,7 +422,10 @@ size_t getNamespaceNumber( // ArchivePanel class constructor // ----------------------------------------------------------------------------- ArchivePanel::ArchivePanel(wxWindow* parent, shared_ptr& archive) : - wxPanel(parent, -1), archive_{ archive }, undo_manager_{ new UndoManager() }, ee_manager_{ new ExternalEditManager } + wxPanel(parent, -1), + archive_{ archive }, + undo_manager_{ new UndoManager() }, + ee_manager_{ new ExternalEditManager } { setup(archive.get()); bindEvents(archive.get()); @@ -433,7 +434,7 @@ ArchivePanel::ArchivePanel(wxWindow* parent, shared_ptr& archive) : // ----------------------------------------------------------------------------- // Setup the panel controls and layout // ----------------------------------------------------------------------------- -void ArchivePanel::setup(Archive* archive) +void ArchivePanel::setup(const Archive* archive) { // Create controls splitter_ = new ui::Splitter(this, -1, wxSP_3DSASH | wxSP_LIVE_UPDATE); @@ -452,7 +453,7 @@ void ArchivePanel::setup(Archive* archive) // Setup splitter splitter_->SetMinimumPaneSize(ui::scalePx(300)); - m_hbox->Add(splitter_, wxSizerFlags(1).Expand().Border(wxALL, ui::pad())); + m_hbox->Add(splitter_, wxutil::sfWithBorder(1).Expand()); int split_pos = ap_splitter_position_list; if (archive && archive->formatDesc().supports_dirs) split_pos = ap_splitter_position_tree; @@ -526,7 +527,6 @@ wxPanel* ArchivePanel::createEntryListPanel(wxWindow* parent) auto* panel = new wxPanel(parent); auto archive = archive_.lock(); bool has_dirs = archive->formatDesc().supports_dirs; - auto min_pad = ui::px(ui::Size::PadMinimum); // Create & set sizer & border auto* hbox = new wxBoxSizer(wxHORIZONTAL); @@ -614,19 +614,19 @@ wxPanel* ArchivePanel::createEntryListPanel(wxWindow* parent) panel_filter_->Show(elist_show_filter); // Layout entry list - hbox->Add(toolbar_elist_, 0, wxEXPAND); - hbox->AddSpacer(min_pad); + hbox->Add(toolbar_elist_, wxSizerFlags().Expand()); + hbox->AddSpacer(ui::padMin()); auto* vbox = new wxBoxSizer(wxVERTICAL); - hbox->Add(vbox, 1, wxEXPAND | wxRIGHT, min_pad); + hbox->Add(vbox, wxutil::sfWithMinBorder(1, wxRIGHT).Expand()); if (etree_path_) { - vbox->Add(etree_path_, 0, wxEXPAND); - vbox->AddSpacer(min_pad); - vbox->Add(entry_tree_, 1, wxEXPAND); + vbox->Add(etree_path_, wxSizerFlags().Expand()); + vbox->AddSpacer(ui::padMin()); + vbox->Add(entry_tree_, wxSizerFlags(1).Expand()); } else - vbox->Add(entry_tree_, 1, wxEXPAND); - vbox->Add(panel_filter_, 0, wxEXPAND | wxTOP, ui::pad()); + vbox->Add(entry_tree_, wxSizerFlags(1).Expand()); + vbox->Add(panel_filter_, wxutil::sfWithBorder(0, wxTOP).Expand()); return panel; } @@ -2165,7 +2165,7 @@ bool ArchivePanel::gfxTint() undo_manager_->endRecord(true); } last_tint_colour = gtd.colour().toString(ColRGBA::StringFormat::RGB); - last_tint_amount = (int)(gtd.amount() * 100.0f); + last_tint_amount = static_cast(gtd.amount() * 100.0f); maineditor::currentEntryPanel()->callRefresh(); return true; @@ -2894,7 +2894,7 @@ bool ArchivePanel::openEntry(ArchiveEntry* entry, bool force) // ----------------------------------------------------------------------------- // Opens [entry] in the text editor panel // ----------------------------------------------------------------------------- -bool ArchivePanel::openEntryAsText(ArchiveEntry* entry) +bool ArchivePanel::openEntryAsText(const ArchiveEntry* entry) { // Check entry was given if (!entry) @@ -2916,7 +2916,7 @@ bool ArchivePanel::openEntryAsText(ArchiveEntry* entry) // ----------------------------------------------------------------------------- // Opens [entry] in the hex editor panel // ----------------------------------------------------------------------------- -bool ArchivePanel::openEntryAsHex(ArchiveEntry* entry) +bool ArchivePanel::openEntryAsHex(const ArchiveEntry* entry) { // Check entry was given if (!entry) @@ -2960,6 +2960,14 @@ void ArchivePanel::focusOnEntry(ArchiveEntry* entry) const entry_tree_->SetSelections(wxDataViewItemArray(1, item)); } +// ----------------------------------------------------------------------------- +// Sets focus to the entry list +// ----------------------------------------------------------------------------- +void ArchivePanel::focusEntryList() const +{ + entry_tree_->SetFocus(); +} + // ----------------------------------------------------------------------------- // Show an entry panel appropriate to the current entry // ----------------------------------------------------------------------------- @@ -4307,6 +4315,17 @@ void ArchivePanel::onBtnClearFilter(wxCommandEvent& e) // ----------------------------------------------------------------------------- +// ----------------------------------------------------------------------------- +// EntryDataUS class constructor +// ----------------------------------------------------------------------------- +EntryDataUS::EntryDataUS(ArchiveEntry* entry) : + path_{ entry->path() }, + index_{ entry->index() }, + archive_{ entry->parent() } +{ + data_.importMem(entry->rawData(), entry->size()); +} + // ----------------------------------------------------------------------------- // Swaps data between the entry and the undo step // ----------------------------------------------------------------------------- diff --git a/src/MainEditor/UI/ArchivePanel.h b/src/MainEditor/UI/ArchivePanel.h index 3969e3509..03cbb2ce2 100644 --- a/src/MainEditor/UI/ArchivePanel.h +++ b/src/MainEditor/UI/ArchivePanel.h @@ -1,20 +1,29 @@ #pragma once -#include "Archive/ArchiveEntry.h" #include "General/SAction.h" #include "General/UndoRedo.h" -#include "MainEditor/ExternalEditManager.h" -#include "UI/Lists/ArchiveEntryTree.h" -#include +// Forward declarations +class wxSplitterWindow; class wxStaticText; class wxBitmapButton; - namespace slade { +namespace ui +{ + class ArchivePathPanel; + class ArchiveEntryTree; +} // namespace ui +class ExternalEditManager; +class ArchiveDir; +class ArchiveEntry; +class Archive; class EntryPanel; class SToolBar; +} // namespace slade +namespace slade +{ class ArchivePanel : public wxPanel, SActionHandler { public: @@ -93,11 +102,11 @@ class ArchivePanel : public wxPanel, SActionHandler // UI related bool openDir(const shared_ptr& dir) const; bool openEntry(ArchiveEntry* entry, bool force = false); - bool openEntryAsText(ArchiveEntry* entry); - bool openEntryAsHex(ArchiveEntry* entry); + bool openEntryAsText(const ArchiveEntry* entry); + bool openEntryAsHex(const ArchiveEntry* entry); bool showEntryPanel(EntryPanel* new_area, bool ask_save = true); void focusOnEntry(ArchiveEntry* entry) const; - void focusEntryList() const { entry_tree_->SetFocus(); } + void focusEntryList() const; void refreshPanel(); void closeCurrentEntry(); wxMenu* createEntryOpenMenu(const wxString& category); @@ -131,17 +140,17 @@ class ArchivePanel : public wxPanel, SActionHandler wxSplitterWindow* splitter_ = nullptr; // Entry panels - EntryPanel* cur_area_ = nullptr; - EntryPanel* entry_area_ = nullptr; - EntryPanel* default_area_ = nullptr; - EntryPanel* text_area_ = nullptr; - EntryPanel* ansi_area_ = nullptr; - EntryPanel* gfx_area_ = nullptr; - EntryPanel* pal_area_ = nullptr; - EntryPanel* hex_area_ = nullptr; - EntryPanel* map_area_ = nullptr; - EntryPanel* audio_area_ = nullptr; - EntryPanel* data_area_ = nullptr; + EntryPanel* cur_area_ = nullptr; + EntryPanel* entry_area_ = nullptr; + EntryPanel* default_area_ = nullptr; + EntryPanel* text_area_ = nullptr; + EntryPanel* ansi_area_ = nullptr; + EntryPanel* gfx_area_ = nullptr; + EntryPanel* pal_area_ = nullptr; + EntryPanel* hex_area_ = nullptr; + EntryPanel* map_area_ = nullptr; + EntryPanel* audio_area_ = nullptr; + EntryPanel* data_area_ = nullptr; // Signal connections sigslot::scoped_connection sc_archive_saved_; @@ -176,7 +185,7 @@ class ArchivePanel : public wxPanel, SActionHandler void onBtnClearFilter(wxCommandEvent& e); private: - void setup(Archive* archive); + void setup(const Archive* archive); void bindEvents(Archive* archive); wxPanel* createEntryListPanel(wxWindow* parent); }; @@ -184,10 +193,7 @@ class ArchivePanel : public wxPanel, SActionHandler class EntryDataUS : public UndoStep { public: - EntryDataUS(ArchiveEntry* entry) : path_{ entry->path() }, index_{ entry->index() }, archive_{ entry->parent() } - { - data_.importMem(entry->rawData(), entry->size()); - } + EntryDataUS(ArchiveEntry* entry); bool swapData(); bool doUndo() override { return swapData(); } diff --git a/src/MainEditor/UI/EntryPanel/ANSIEntryPanel.cpp b/src/MainEditor/UI/EntryPanel/ANSIEntryPanel.cpp index cd4bd0f6e..6aa0755ea 100644 --- a/src/MainEditor/UI/EntryPanel/ANSIEntryPanel.cpp +++ b/src/MainEditor/UI/EntryPanel/ANSIEntryPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -51,7 +51,7 @@ ANSIEntryPanel::ANSIEntryPanel(wxWindow* parent) : EntryPanel(parent, "ansi") // Get the VGA font ansi_chardata_.assign(DATASIZE, 0); ansi_canvas_ = new ANSICanvas(this, -1); - sizer_main_->Add(ansi_canvas_, 1, wxEXPAND, 0); + sizer_main_->Add(ansi_canvas_, wxSizerFlags(1).Expand()); // Hide toolbar (no reason for it on this panel, yet) toolbar_->Show(false); diff --git a/src/MainEditor/UI/EntryPanel/ANSIEntryPanel.h b/src/MainEditor/UI/EntryPanel/ANSIEntryPanel.h index 3c76912c1..1485dab58 100644 --- a/src/MainEditor/UI/EntryPanel/ANSIEntryPanel.h +++ b/src/MainEditor/UI/EntryPanel/ANSIEntryPanel.h @@ -12,7 +12,7 @@ class ANSIEntryPanel : public EntryPanel ANSIEntryPanel(wxWindow* parent); ~ANSIEntryPanel() override = default; - static const int DATASIZE = 4000; + static constexpr int DATASIZE = 4000; protected: bool loadEntry(ArchiveEntry* entry) override; diff --git a/src/MainEditor/UI/EntryPanel/AudioEntryPanel.cpp b/src/MainEditor/UI/EntryPanel/AudioEntryPanel.cpp index e5892b8c0..699722108 100644 --- a/src/MainEditor/UI/EntryPanel/AudioEntryPanel.cpp +++ b/src/MainEditor/UI/EntryPanel/AudioEntryPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -37,6 +37,7 @@ #include "Audio/ModMusic.h" #include "Audio/Mp3Music.h" #include "Audio/Music.h" +#include "General/UI.h" #include "MainEditor/Conversions.h" #include "UI/Controls/SIconButton.h" #include "UI/WxUtils.h" @@ -74,10 +75,12 @@ AudioEntryPanel::AudioEntryPanel(wxWindow* parent) : mod_{ new audio::ModMusic() }, mp3_{ new audio::Mp3Music() } { + namespace wx = wxutil; + // Setup sizer auto sizer_gb = new wxGridBagSizer(ui::pad(), ui::pad()); sizer_main_->AddStretchSpacer(); - sizer_main_->Add(sizer_gb, 0, wxALIGN_CENTER); + sizer_main_->Add(sizer_gb, wxSizerFlags().Center()); sizer_main_->AddStretchSpacer(); // Add seekbar @@ -368,14 +371,7 @@ bool AudioEntryPanel::openAudio(MemChunk& audio, const wxString& filename) audio_type_ = Sound; // Enable play controls -#if (SFML_VERSION_MAJOR == 2 && SFML_VERSION_MINOR < 2) - // SFML before 2.2 has a bug where it reports an incorrect value for long sounds, so compute it ourselves then - setAudioDuration( - (sound_buffer->getSampleCount() / sound_buffer->getSampleRate()) - * (1000 / sound_buffer->getChannelCount())); -#else setAudioDuration(sound_buffer_->getDuration().asMilliseconds()); -#endif btn_play_->Enable(); btn_pause_->Enable(); btn_stop_->Enable(); @@ -511,10 +507,10 @@ void AudioEntryPanel::startStream() { case Sound: sound_->play(); break; case Music: music_->play(); break; - case Mod: mod_->play(); break; - case MIDI: audio::midiPlayer().play(); break; - case Mp3: mp3_->play(); break; - default: break; + case Mod: mod_->play(); break; + case MIDI: audio::midiPlayer().play(); break; + case Mp3: mp3_->play(); break; + default: break; } } @@ -527,10 +523,10 @@ void AudioEntryPanel::stopStream() const { case Sound: sound_->pause(); break; case Music: music_->pause(); break; - case Mod: mod_->pause(); break; - case MIDI: audio::midiPlayer().pause(); break; - case Mp3: mp3_->pause(); break; - default: break; + case Mod: mod_->pause(); break; + case MIDI: audio::midiPlayer().pause(); break; + case Mp3: mp3_->pause(); break; + default: break; } } @@ -543,10 +539,10 @@ void AudioEntryPanel::resetStream() const { case Sound: sound_->stop(); break; case Music: music_->stop(); break; - case Mod: mod_->stop(); break; - case MIDI: audio::midiPlayer().stop(); break; - case Mp3: mp3_->stop(); break; - default: break; + case Mod: mod_->stop(); break; + case MIDI: audio::midiPlayer().stop(); break; + case Mp3: mp3_->stop(); break; + default: break; } } @@ -568,17 +564,18 @@ bool AudioEntryPanel::updateInfo(ArchiveEntry& entry) const { size_t samplerate = mc.readL16(2); size_t samples = mc.readL16(4); - info += wxString::Format("%lu samples at %lu Hz", (unsigned long)samples, (unsigned long)samplerate); + info += wxString::Format( + "%lu samples at %lu Hz", static_cast(samples), static_cast(samplerate)); } else if (entry.type() == EntryType::fromId("snd_speaker")) { size_t samples = mc.readL16(2); - info += wxString::Format("%lu samples", (unsigned long)samples); + info += wxString::Format("%lu samples", static_cast(samples)); } else if (entry.type() == EntryType::fromId("snd_audiot")) { size_t samples = mc.readL16(0); - info += wxString::Format("%lu samples", (unsigned long)samples); + info += wxString::Format("%lu samples", static_cast(samples)); } else if (entry.type() == EntryType::fromId("snd_sun")) info += audio::getSunInfo(mc); @@ -712,10 +709,10 @@ void AudioEntryPanel::onTimer(wxTimerEvent& e) { case Sound: pos = sound_->getPlayingOffset().asMilliseconds(); break; case Music: pos = music_->getPlayingOffset().asMilliseconds(); break; - case Mod: pos = mod_->getPlayingOffset().asMilliseconds(); break; - case MIDI: pos = audio::midiPlayer().position(); break; - case Mp3: pos = mp3_->getPlayingOffset().asMilliseconds(); break; - default: break; + case Mod: pos = mod_->getPlayingOffset().asMilliseconds(); break; + case MIDI: pos = audio::midiPlayer().position(); break; + case Mp3: pos = mp3_->getPlayingOffset().asMilliseconds(); break; + default: break; } // Set slider @@ -742,10 +739,10 @@ void AudioEntryPanel::onSliderSeekChanged(wxCommandEvent& e) { case Sound: sound_->setPlayingOffset(sf::milliseconds(slider_seek_->GetValue())); break; case Music: music_->setPlayingOffset(sf::milliseconds(slider_seek_->GetValue())); break; - case Mod: mod_->setPlayingOffset(sf::milliseconds(slider_seek_->GetValue())); break; - case MIDI: audio::midiPlayer().setPosition(slider_seek_->GetValue()); break; - case Mp3: mp3_->setPlayingOffset(sf::milliseconds(slider_seek_->GetValue())); break; - default: break; + case Mod: mod_->setPlayingOffset(sf::milliseconds(slider_seek_->GetValue())); break; + case MIDI: audio::midiPlayer().setPosition(slider_seek_->GetValue()); break; + case Mp3: mp3_->setPlayingOffset(sf::milliseconds(slider_seek_->GetValue())); break; + default: break; } } @@ -760,9 +757,9 @@ void AudioEntryPanel::onSliderVolumeChanged(wxCommandEvent& e) { case Sound: sound_->setVolume(snd_volume); break; case Music: music_->setVolume(snd_volume); break; - case MIDI: audio::midiPlayer().setVolume(snd_volume); break; - case Mp3: mp3_->setVolume(snd_volume); break; - case Mod: mod_->setVolume(snd_volume); break; - default: break; + case MIDI: audio::midiPlayer().setVolume(snd_volume); break; + case Mp3: mp3_->setVolume(snd_volume); break; + case Mod: mod_->setVolume(snd_volume); break; + default: break; } } diff --git a/src/MainEditor/UI/EntryPanel/DataEntryPanel.cpp b/src/MainEditor/UI/EntryPanel/DataEntryPanel.cpp index 95a03181c..b68a27289 100644 --- a/src/MainEditor/UI/EntryPanel/DataEntryPanel.cpp +++ b/src/MainEditor/UI/EntryPanel/DataEntryPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -36,6 +36,7 @@ #include "General/UI.h" #include "MainEditor/BinaryControlLump.h" #include "MainEditor/MainEditor.h" +#include "UI/WxUtils.h" using namespace slade; @@ -85,7 +86,7 @@ wxString DataEntryTable::GetValue(int row, int col) data_.read(&val, 1); return wxString::Format("%hhd", val); } - else if (columns_[col].size == 2) + if (columns_[col].size == 2) { int16_t val; data_.read(&val, 2); @@ -93,7 +94,7 @@ wxString DataEntryTable::GetValue(int row, int col) val = wxINT16_SWAP_ON_LE(val); return wxString::Format("%hd", val); } - else if (columns_[col].size == 4) + if (columns_[col].size == 4) { int32_t val; data_.read(&val, 4); @@ -101,7 +102,7 @@ wxString DataEntryTable::GetValue(int row, int col) val = wxINT32_SWAP_ON_LE(val); return wxString::Format("%d", val); } - else if (columns_[col].size == 8) + if (columns_[col].size == 8) { int64_t val; data_.read(&val, 8); @@ -109,11 +110,12 @@ wxString DataEntryTable::GetValue(int row, int col) val = wxINT64_SWAP_ON_LE(val); return wxString::Format("%lld", val); } + return "INVALID SIZE"; } // Unsigned integer column - else if (columns_[col].type == ColType::IntUnsigned || columns_[col].type == ColType::IntBEUnsigned) + if (columns_[col].type == ColType::IntUnsigned || columns_[col].type == ColType::IntBEUnsigned) { bool be = columns_[col].type == ColType::IntBEUnsigned; @@ -123,7 +125,7 @@ wxString DataEntryTable::GetValue(int row, int col) data_.read(&val, 1); return wxString::Format("%hhd", val); } - else if (columns_[col].size == 2) + if (columns_[col].size == 2) { uint16_t val; data_.read(&val, 2); @@ -131,7 +133,7 @@ wxString DataEntryTable::GetValue(int row, int col) val = wxINT16_SWAP_ON_LE(val); return wxString::Format("%hd", val); } - else if (columns_[col].size == 4) + if (columns_[col].size == 4) { uint32_t val; data_.read(&val, 4); @@ -139,37 +141,37 @@ wxString DataEntryTable::GetValue(int row, int col) val = wxINT32_SWAP_ON_LE(val); return wxString::Format("%d", val); } - else if (columns_[col].size == 8) + if (columns_[col].size == 8) { uint64_t val; data_.read(&val, 8); if (be) val = wxINT64_SWAP_ON_LE(val); - return wxString::Format("%lld", (long long)val); + return wxString::Format("%lld", static_cast(val)); } return "INVALID SIZE"; } // Fixed-point float column - else if (columns_[col].type == ColType::Fixed) + if (columns_[col].type == ColType::Fixed) { if (columns_[col].size == 4) { int32_t val; data_.read(&val, 4); - return wxString::Format("%1.3f", (double)val / 65536.0); + return wxString::Format("%1.3f", static_cast(val) / 65536.0); } return "INVALID SIZE"; } // String column - else if (columns_[col].type == ColType::String) + if (columns_[col].type == ColType::String) { return wxString::FromAscii(data_.data() + data_.currentPos(), columns_[col].size); } // Custom value column - else if (columns_[col].type == ColType::CustomValue) + if (columns_[col].type == ColType::CustomValue) { int value = 0; if (columns_[col].size == 1) @@ -301,7 +303,7 @@ void DataEntryTable::SetValue(int row, int col, const wxString& value) // ----------------------------------------------------------------------------- wxString DataEntryTable::GetColLabelValue(int col) { - if ((unsigned)col < columns_.size()) + if (static_cast(col) < columns_.size()) return columns_[col].name; return wxString::Format("Column%d", col); @@ -335,9 +337,9 @@ bool DataEntryTable::DeleteRows(size_t pos, size_t num) vector new_rows_new; for (int a : rows_new_) { - if ((unsigned)a >= pos + num) + if (static_cast(a) >= pos + num) new_rows_new.push_back(a - num); - else if ((unsigned)a < pos) + else if (static_cast(a) < pos) new_rows_new.push_back(a); } rows_new_ = new_rows_new; @@ -346,9 +348,9 @@ bool DataEntryTable::DeleteRows(size_t pos, size_t num) vector new_cells_modified; for (auto& cell : cells_modified_) { - if ((unsigned)cell.x >= pos + num) - new_cells_modified.emplace_back(cell.x - (int)num, cell.y); - else if ((unsigned)cell.x < pos) + if (static_cast(cell.x) >= pos + num) + new_cells_modified.emplace_back(cell.x - static_cast(num), cell.y); + else if (static_cast(cell.x) < pos) new_cells_modified.emplace_back(cell.x, cell.y); } cells_modified_ = new_cells_modified; @@ -383,14 +385,14 @@ bool DataEntryTable::InsertRows(size_t pos, size_t num) // Update new rows for (int& row : rows_new_) - if ((unsigned)row >= pos) + if (static_cast(row) >= pos) row += num; for (unsigned a = 0; a < num; a++) rows_new_.push_back(pos + a); // Update modified cells for (auto& cell : cells_modified_) - if (cell.x >= (int)pos) + if (cell.x >= static_cast(pos)) cell.x += num; // Send message to grid @@ -914,11 +916,11 @@ DataEntryPanel::DataEntryPanel(wxWindow* parent) : EntryPanel(parent, "data"), t auto vbox = new wxBoxSizer(wxVERTICAL); sizer_main_->Add(vbox, 1, wxEXPAND); combo_cell_value_ = new wxComboBox(this, -1, "", wxDefaultPosition, wxDefaultSize, 0, nullptr, wxTE_PROCESS_ENTER); - vbox->Add(combo_cell_value_, 0, wxEXPAND | wxBOTTOM, ui::pad()); + vbox->Add(combo_cell_value_, wxutil::sfWithBorder(0, wxBOTTOM).Expand()); // Create grid grid_data_ = new wxGrid(this, -1); - vbox->Add(grid_data_, 1, wxEXPAND | wxBOTTOM, ui::pad()); + vbox->Add(grid_data_, wxutil::sfWithBorder(1, wxBOTTOM).Expand()); // Add actions to toolbar wxArrayString actions; @@ -1130,8 +1132,8 @@ void DataEntryPanel::changeValue() const auto vbox = new wxBoxSizer(wxVERTICAL); dlg.SetSizer(vbox); - vbox->Add(combo, 0, wxEXPAND | wxALL, 10); - vbox->Add(dlg.CreateButtonSizer(wxOK | wxCANCEL), 0, wxEXPAND | wxALL, 10); + vbox->Add(combo, wxutil::sfWithLargeBorder(0).Expand()); + vbox->Add(dlg.CreateButtonSizer(wxOK | wxCANCEL), wxutil::sfWithLargeBorder(0).Expand()); // Show dialog dlg.Fit(); @@ -1150,8 +1152,8 @@ void DataEntryPanel::changeValue() const } // Apply value to selected cells - for (unsigned a = 0; a < selection.size(); a++) - grid_data_->SetCellValue(selection[a].x, selection[a].y, wxString::Format("%ld", lval)); + for (auto& a : selection) + grid_data_->SetCellValue(a.x, a.y, wxString::Format("%ld", lval)); grid_data_->ForceRefresh(); } } diff --git a/src/MainEditor/UI/EntryPanel/DataEntryPanel.h b/src/MainEditor/UI/EntryPanel/DataEntryPanel.h index e1011bf5c..be88f33b7 100644 --- a/src/MainEditor/UI/EntryPanel/DataEntryPanel.h +++ b/src/MainEditor/UI/EntryPanel/DataEntryPanel.h @@ -40,7 +40,7 @@ class DataEntryTable : public wxGridTableBase { } - void addCustomValue(int key, wxString value) { custom_values.emplace_back(key, value); } + void addCustomValue(int key, const wxString& value) { custom_values.emplace_back(key, value); } wxString customValue(int key) { @@ -54,7 +54,7 @@ class DataEntryTable : public wxGridTableBase }; DataEntryTable(DataEntryPanel* parent) : parent_{ parent } {} - virtual ~DataEntryTable() = default; + ~DataEntryTable() override = default; // wxGridTableBase overrides int GetNumberRows() override; @@ -91,7 +91,7 @@ class DataEntryPanel : public EntryPanel { public: DataEntryPanel(wxWindow* parent); - ~DataEntryPanel() = default; + ~DataEntryPanel() override = default; void setDataModified(bool modified) { EntryPanel::setModified(modified); } diff --git a/src/MainEditor/UI/EntryPanel/DefaultEntryPanel.cpp b/src/MainEditor/UI/EntryPanel/DefaultEntryPanel.cpp index 02c3e614f..d64b3cb72 100644 --- a/src/MainEditor/UI/EntryPanel/DefaultEntryPanel.cpp +++ b/src/MainEditor/UI/EntryPanel/DefaultEntryPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -40,6 +40,7 @@ #include "MainEditor/MainEditor.h" #include "MainEditor/UI/ArchivePanel.h" #include "UI/Dialogs/ModifyOffsetsDialog.h" +#include "UI/WxUtils.h" using namespace slade; @@ -56,37 +57,39 @@ using namespace slade; // ----------------------------------------------------------------------------- DefaultEntryPanel::DefaultEntryPanel(wxWindow* parent) : EntryPanel(parent, "default") { + namespace wx = wxutil; + sizer_main_->AddStretchSpacer(1); // Add index label label_index_ = new wxStaticText(this, -1, "Index"); - sizer_main_->Add(label_index_, 0, wxALL | wxALIGN_CENTER, ui::pad()); + sizer_main_->Add(label_index_, wx::sfWithBorder().Center()); // Add type label label_type_ = new wxStaticText(this, -1, "Type"); - sizer_main_->Add(label_type_, 0, wxALL | wxALIGN_CENTER, ui::pad()); + sizer_main_->Add(label_type_, wx::sfWithBorder().Center()); // Add size label label_size_ = new wxStaticText(this, -1, "Size"); - sizer_main_->Add(label_size_, 0, wxALL | wxALIGN_CENTER, ui::pad()); + sizer_main_->Add(label_size_, wx::sfWithBorder().Center()); // Add actions frame frame_actions_ = new wxStaticBox(this, -1, "Actions"); auto framesizer = new wxStaticBoxSizer(frame_actions_, wxVERTICAL); - sizer_main_->Add(framesizer, 0, wxALL | wxALIGN_CENTER, ui::pad()); + sizer_main_->Add(framesizer, wx::sfWithBorder().Center()); // Add 'Convert Gfx' button btn_gfx_convert_ = new wxButton(this, -1, "Convert Gfx To..."); framesizer->AddSpacer(4); - framesizer->Add(btn_gfx_convert_, 0, wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, ui::pad()); + framesizer->Add(btn_gfx_convert_, wx::sfWithBorder(0, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); // Add 'Modify Gfx Offsets' button btn_gfx_modify_offsets_ = new wxButton(this, -1, "Modify Gfx Offsets"); - framesizer->Add(btn_gfx_modify_offsets_, 0, wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, ui::pad()); + framesizer->Add(btn_gfx_modify_offsets_, wx::sfWithBorder(0, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); // Add 'Edit Textures' button btn_texture_edit_ = new wxButton(this, -1, "Edit Textures"); - framesizer->Add(btn_texture_edit_, 0, wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, ui::pad()); + framesizer->Add(btn_texture_edit_, wx::sfWithBorder(0, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); sizer_main_->AddStretchSpacer(1); @@ -155,7 +158,7 @@ bool DefaultEntryPanel::loadEntry(ArchiveEntry* entry) // ----------------------------------------------------------------------------- // Loads [entries] into the panel, for multiple selection handling // ----------------------------------------------------------------------------- -bool DefaultEntryPanel::loadEntries(vector& entries) +bool DefaultEntryPanel::loadEntries(const vector& entries) { // Update labels label_type_->SetLabel(wxString::Format("%lu selected entries", static_cast(entries.size()))); diff --git a/src/MainEditor/UI/EntryPanel/DefaultEntryPanel.h b/src/MainEditor/UI/EntryPanel/DefaultEntryPanel.h index 972916841..361d2825d 100644 --- a/src/MainEditor/UI/EntryPanel/DefaultEntryPanel.h +++ b/src/MainEditor/UI/EntryPanel/DefaultEntryPanel.h @@ -10,7 +10,7 @@ class DefaultEntryPanel : public EntryPanel DefaultEntryPanel(wxWindow* parent); ~DefaultEntryPanel() override = default; - bool loadEntries(vector& entries); + bool loadEntries(const vector& entries); protected: bool loadEntry(ArchiveEntry* entry) override; diff --git a/src/MainEditor/UI/EntryPanel/EntryPanel.cpp b/src/MainEditor/UI/EntryPanel/EntryPanel.cpp index a9ca8d989..ff1f4c477 100644 --- a/src/MainEditor/UI/EntryPanel/EntryPanel.cpp +++ b/src/MainEditor/UI/EntryPanel/EntryPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -41,6 +41,7 @@ #include "MainEditor/UI/MainWindow.h" #include "UI/SToolBar/SToolBar.h" #include "UI/SToolBar/SToolBarButton.h" +#include "UI/WxUtils.h" using namespace slade; @@ -69,16 +70,17 @@ CVAR(Bool, confirm_entry_revert, true, CVar::Flag::Save) // ----------------------------------------------------------------------------- EntryPanel::EntryPanel(wxWindow* parent, const wxString& id, bool left_toolbar) : wxPanel(parent, -1), id_{ id } { + namespace wx = wxutil; + auto sizer = new wxBoxSizer(wxVERTICAL); SetSizer(sizer); wxWindow::Show(false); // Add toolbar - toolbar_ = new SToolBar(this); - auto pad_min = ui::px(ui::Size::PadMinimum); - sizer->Add(toolbar_, 0, wxEXPAND | wxLEFT, pad_min); - sizer->AddSpacer(pad_min); + toolbar_ = new SToolBar(this); + sizer->Add(toolbar_, wx::sfWithMinBorder(0, wxLEFT).Expand()); + sizer->AddSpacer(ui::padMin()); // Default entry toolbar group auto tb_group = new SToolBarGroup(toolbar_, "Entry"); @@ -97,13 +99,13 @@ EntryPanel::EntryPanel(wxWindow* parent, const wxString& id, bool left_toolbar) if (left_toolbar) { auto* hbox = new wxBoxSizer(wxHORIZONTAL); - hbox->Add(toolbar_left_, 0, wxEXPAND | wxRIGHT, pad_min); - hbox->Add(sizer_main_, 1, wxEXPAND); - sizer->Add(hbox, 1, wxEXPAND | wxLEFT, pad_min); + hbox->Add(toolbar_left_, wx::sfWithMinBorder(0, wxRIGHT).Expand()); + hbox->Add(sizer_main_, wxSizerFlags(1).Expand()); + sizer->Add(hbox, wx::sfWithMinBorder(1, wxLEFT).Expand()); } else - sizer->Add(sizer_main_, 1, wxEXPAND | wxLEFT, pad_min); - sizer->Add(sizer_bottom_, 0, wxEXPAND | wxTOP | wxLEFT, ui::pad()); + sizer->Add(sizer_main_, wx::sfWithMinBorder(1, wxLEFT).Expand()); + sizer->Add(sizer_bottom_, wx::sfWithBorder(0, wxTOP | wxLEFT).Expand()); // Bind button events Bind(wxEVT_STOOLBAR_BUTTON_CLICKED, &EntryPanel::onToolbarButton, this, toolbar_->GetId()); @@ -147,8 +149,8 @@ void EntryPanel::addBorderPadding() Freeze(); auto* sizer = GetSizer(); SetSizer(new wxBoxSizer(wxHORIZONTAL), false); - GetSizer()->AddSpacer(ui::px(ui::Size::PadMinimum)); - GetSizer()->Add(sizer, 1, wxEXPAND | wxTOP | wxRIGHT | wxBOTTOM, ui::pad()); + GetSizer()->AddSpacer(ui::padMin()); + GetSizer()->Add(sizer, wxutil::sfWithBorder(1, wxTOP | wxRIGHT | wxBOTTOM).Expand()); Layout(); Thaw(); } @@ -156,7 +158,7 @@ void EntryPanel::addBorderPadding() // ----------------------------------------------------------------------------- // 'Opens' the given entry (sets the frame label then loads it) // ----------------------------------------------------------------------------- -bool EntryPanel::openEntry(ArchiveEntry* entry) +bool EntryPanel::openEntry(const ArchiveEntry* entry) { return openEntry(entry ? entry->getShared() : nullptr); } @@ -367,7 +369,7 @@ void EntryPanel::removeCustomMenu() const // return true if the panel is shown on any tab, even if it is not on the one // that is selected... // ----------------------------------------------------------------------------- -bool EntryPanel::isActivePanel() +bool EntryPanel::isActivePanel() const { return (IsShown() && maineditor::currentEntryPanel() == this); } @@ -385,7 +387,7 @@ void EntryPanel::updateToolbar() // Handles an action from the 'standalone' Entry menu (when this EntryPanel is // in its own tab) // ----------------------------------------------------------------------------- -bool EntryPanel::handleStandaloneAction(string_view id) +bool EntryPanel::handleStandaloneAction(const string_view id) { // Save if (id == "arch_entry_save") diff --git a/src/MainEditor/UI/EntryPanel/EntryPanel.h b/src/MainEditor/UI/EntryPanel/EntryPanel.h index 8943c949c..1a24fe827 100644 --- a/src/MainEditor/UI/EntryPanel/EntryPanel.h +++ b/src/MainEditor/UI/EntryPanel/EntryPanel.h @@ -18,12 +18,12 @@ class EntryPanel : public wxPanel, protected SActionHandler wxString name() const { return id_; } ArchiveEntry* entry() const { return entry_.lock().get(); } bool isModified() const { return modified_; } - bool isActivePanel(); + bool isActivePanel() const; void setUndoManager(UndoManager* manager) { undo_manager_ = manager; } MemChunk* entryData() { return &entry_data_; } void addBorderPadding(); - bool openEntry(ArchiveEntry* entry); + bool openEntry(const ArchiveEntry* entry); bool openEntry(shared_ptr entry); bool saveEntry(); virtual bool revertEntry(bool confirm = true); diff --git a/src/MainEditor/UI/EntryPanel/GfxEntryPanel.cpp b/src/MainEditor/UI/EntryPanel/GfxEntryPanel.cpp index 18709873c..eb89541bc 100644 --- a/src/MainEditor/UI/EntryPanel/GfxEntryPanel.cpp +++ b/src/MainEditor/UI/EntryPanel/GfxEntryPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -38,6 +38,7 @@ #include "MainEditor/EntryOperations.h" #include "MainEditor/MainEditor.h" #include "MainEditor/UI/MainWindow.h" +#include "UI/Controls/ColourBox.h" #include "UI/Controls/PaletteChooser.h" #include "UI/Controls/SIconButton.h" #include "UI/Controls/ZoomControl.h" @@ -48,6 +49,7 @@ #include "UI/Dialogs/ModifyOffsetsDialog.h" #include "UI/Dialogs/TranslationEditorDialog.h" #include "UI/SBrush.h" +#include "UI/WxUtils.h" #include "Utility/StringUtils.h" @@ -77,6 +79,8 @@ EXTERN_CVAR(Int, last_tint_amount) // ----------------------------------------------------------------------------- GfxEntryPanel::GfxEntryPanel(wxWindow* parent) : EntryPanel(parent, "gfx", true) { + namespace wx = wxutil; + // Init variables prev_translation_.addRange(TransRange::Type::Palette, 0); edit_translation_.addRange(TransRange::Type::Palette, 0); @@ -114,19 +118,19 @@ GfxEntryPanel::GfxEntryPanel(wxWindow* parent) : EntryPanel(parent, "gfx", true) 0); spin_xoffset_->SetMinSize(spinsize); spin_yoffset_->SetMinSize(spinsize); - sizer_bottom_->Add(new wxStaticText(this, -1, "Offsets:"), 0, wxALIGN_CENTER_VERTICAL, 0); - sizer_bottom_->Add(spin_xoffset_, 0, wxALIGN_CENTER_VERTICAL | wxLEFT | wxRIGHT, ui::pad()); - sizer_bottom_->Add(spin_yoffset_, 0, wxALIGN_CENTER_VERTICAL | wxRIGHT, ui::pad()); + sizer_bottom_->Add(new wxStaticText(this, -1, "Offsets:"), wxSizerFlags().CenterVertical()); + sizer_bottom_->Add(spin_xoffset_, wx::sfWithBorder(0, wxLEFT | wxRIGHT).CenterVertical()); + sizer_bottom_->Add(spin_yoffset_, wx::sfWithBorder(0, wxRIGHT).CenterVertical()); // Gfx (offset) type wxString offset_types[] = { "Auto", "Graphic", "Sprite", "HUD" }; choice_offset_type_ = new wxChoice(this, -1, wxDefaultPosition, wxDefaultSize, 4, offset_types); choice_offset_type_->SetSelection(0); - sizer_bottom_->Add(choice_offset_type_, 0, wxALIGN_CENTER_VERTICAL | wxRIGHT, ui::pad()); + sizer_bottom_->Add(choice_offset_type_, wx::sfWithBorder(0, wxRIGHT).CenterVertical()); // Auto offset btn_auto_offset_ = new SIconButton(this, "offset", "Modify Offsets..."); - sizer_bottom_->Add(btn_auto_offset_, 0, wxALIGN_CENTER_VERTICAL); + sizer_bottom_->Add(btn_auto_offset_, wxSizerFlags().CenterVertical()); sizer_bottom_->AddStretchSpacer(); @@ -144,9 +148,9 @@ GfxEntryPanel::GfxEntryPanel(wxWindow* parent) : EntryPanel(parent, "gfx", true) 1, 0); spin_curimg_->SetMinSize(spinsize); - sizer_bottom_->Add(text_imgnum_, 0, wxALIGN_CENTER, 0); - sizer_bottom_->Add(spin_curimg_, 0, wxSHRINK | wxALIGN_CENTER, ui::pad()); - sizer_bottom_->Add(text_imgoutof_, 0, wxALIGN_CENTER | wxRIGHT, ui::padLarge()); + sizer_bottom_->Add(text_imgnum_, wxSizerFlags().Center()); + sizer_bottom_->Add(spin_curimg_, wxSizerFlags().Center()); // 0, wxSHRINK | wxALIGN_CENTER, ui::pad()); + sizer_bottom_->Add(text_imgoutof_, wx::sfWithLargeBorder(0, wxRIGHT).Center()); text_imgnum_->Show(false); spin_curimg_->Show(false); text_imgoutof_->Show(false); @@ -708,10 +712,10 @@ void GfxEntryPanel::applyViewType(ArchiveEntry* entry) const const int sel = choice_offset_type_->GetSelection(); switch (sel) { - case 0: gfx_canvas_->setViewType(detectOffsetType(entry)); break; - case 1: gfx_canvas_->setViewType(GfxCanvas::View::Default); break; - case 2: gfx_canvas_->setViewType(GfxCanvas::View::Sprite); break; - case 3: gfx_canvas_->setViewType(GfxCanvas::View::HUD); break; + case 0: gfx_canvas_->setViewType(detectOffsetType(entry)); break; + case 1: gfx_canvas_->setViewType(GfxCanvas::View::Default); break; + case 2: gfx_canvas_->setViewType(GfxCanvas::View::Sprite); break; + case 3: gfx_canvas_->setViewType(GfxCanvas::View::HUD); break; default: break; } } @@ -806,9 +810,9 @@ bool GfxEntryPanel::handleEntryPanelAction(string_view id) // Rotate image switch (choice) { - case 0: image()->rotate(90); break; - case 1: image()->rotate(180); break; - case 2: image()->rotate(270); break; + case 0: image()->rotate(90); break; + case 1: image()->rotate(180); break; + case 2: image()->rotate(270); break; default: break; } @@ -1086,6 +1090,8 @@ void GfxEntryPanel::toolbarButtonClick(const wxString& action_id) // // ----------------------------------------------------------------------------- +// ReSharper disable CppMemberFunctionMayBeConst +// ReSharper disable CppParameterMayBeConstPtrOrRef // ----------------------------------------------------------------------------- // Called when the colour box's value is changed @@ -1306,7 +1312,7 @@ CONSOLE_COMMAND(rotate, 1, true) return; } } - const int angle = (int)val; + const int angle = static_cast(val); if (angle % 90) { log::error(wxString::Format("Invalid parameter: %i is not a multiple of 90.", angle)); diff --git a/src/MainEditor/UI/EntryPanel/HexEntryPanel.cpp b/src/MainEditor/UI/EntryPanel/HexEntryPanel.cpp index b70329b46..11f62c253 100644 --- a/src/MainEditor/UI/EntryPanel/HexEntryPanel.cpp +++ b/src/MainEditor/UI/EntryPanel/HexEntryPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -51,7 +51,7 @@ HexEntryPanel::HexEntryPanel(wxWindow* parent) : EntryPanel(parent, "hex") { // Create hex editor hex_editor_ = new HexEditorPanel(this); - sizer_main_->Add(hex_editor_, 1, wxEXPAND); + sizer_main_->Add(hex_editor_, wxSizerFlags(1).Expand()); // Hide toolbar toolbar_->Show(false); diff --git a/src/MainEditor/UI/EntryPanel/MapEntryPanel.cpp b/src/MainEditor/UI/EntryPanel/MapEntryPanel.cpp index 6295d00ba..af93040c9 100644 --- a/src/MainEditor/UI/EntryPanel/MapEntryPanel.cpp +++ b/src/MainEditor/UI/EntryPanel/MapEntryPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -33,6 +33,7 @@ #include "Main.h" #include "MapEntryPanel.h" #include "Archive/Archive.h" +#include "OpenGL/OpenGL.h" #include "UI/Canvas/MapPreviewCanvas.h" #include "UI/WxUtils.h" @@ -71,7 +72,7 @@ MapEntryPanel::MapEntryPanel(wxWindow* parent) : EntryPanel(parent, "map") { // Setup map canvas map_canvas_ = new MapPreviewCanvas(this); - sizer_main_->Add(map_canvas_, 1, wxEXPAND, 0); + sizer_main_->Add(map_canvas_, wxSizerFlags(1).Expand()); // Setup map toolbar buttons auto group = new SToolBarGroup(toolbar_, "Map"); @@ -85,9 +86,9 @@ MapEntryPanel::MapEntryPanel(wxWindow* parent) : EntryPanel(parent, "map") stb_revert_ = nullptr; // Setup bottom panel - sizer_bottom_->Add(label_stats_ = new wxStaticText(this, -1, ""), 0, wxALIGN_CENTER_VERTICAL); + sizer_bottom_->Add(label_stats_ = new wxStaticText(this, -1, ""), wxSizerFlags().CenterVertical()); sizer_bottom_->AddStretchSpacer(); - sizer_bottom_->Add(cb_show_things_ = new wxCheckBox(this, -1, "Show Things"), 0, wxALIGN_CENTER_VERTICAL); + sizer_bottom_->Add(cb_show_things_ = new wxCheckBox(this, -1, "Show Things"), wxSizerFlags().CenterVertical()); cb_show_things_->SetValue(map_view_things); // Bind events @@ -107,9 +108,9 @@ bool MapEntryPanel::loadEntry(ArchiveEntry* entry) map_canvas_->clearMap(); // Find map definition for entry - auto maps = entry->parent()->detectMaps(); - Archive::MapDesc thismap; - bool found = false; + auto maps = entry->parent()->detectMaps(); + MapDesc thismap; + bool found = false; for (auto& map : maps) { if (map.head.lock().get() == entry) diff --git a/src/MainEditor/UI/EntryPanel/PaletteEntryPanel.cpp b/src/MainEditor/UI/EntryPanel/PaletteEntryPanel.cpp index 6143878f1..629ec0d2e 100644 --- a/src/MainEditor/UI/EntryPanel/PaletteEntryPanel.cpp +++ b/src/MainEditor/UI/EntryPanel/PaletteEntryPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -87,29 +87,31 @@ class PaletteColouriseDialog : public wxDialog wxDialog(parent, -1, "Colourise", wxDefaultPosition, wxDefaultSize, wxDEFAULT_DIALOG_STYLE | wxRESIZE_BORDER), palette_{ pal } { + namespace wx = wxutil; + // Set dialog icon - wxutil::setWindowIcon(this, "palette_colourise"); + wx::setWindowIcon(this, "palette_colourise"); // Setup main sizer auto msizer = new wxBoxSizer(wxVERTICAL); SetSizer(msizer); auto sizer = new wxBoxSizer(wxVERTICAL); - msizer->Add(sizer, 1, wxEXPAND | wxALL, ui::padLarge()); + msizer->Add(sizer, wx::sfWithLargeBorder(1).Expand()); // Add colour chooser auto hbox = new wxBoxSizer(wxHORIZONTAL); - sizer->Add(hbox, 0, wxEXPAND | wxBOTTOM, ui::pad()); + sizer->Add(hbox, wx::sfWithBorder(0, wxBOTTOM).Expand()); cp_colour_ = new wxColourPickerCtrl(this, -1, wxColour(255, 0, 0)); - hbox->Add(new wxStaticText(this, -1, "Colour:"), 1, wxALIGN_CENTER_VERTICAL | wxRIGHT, ui::pad()); - hbox->Add(cp_colour_, 0, wxEXPAND); + hbox->Add(new wxStaticText(this, -1, "Colour:"), wx::sfWithBorder(1, wxRIGHT).CenterVertical()); + hbox->Add(cp_colour_, wxSizerFlags().Expand()); // Add preview pal_preview_ = new PaletteCanvas(this, -1); - sizer->Add(pal_preview_, 1, wxEXPAND | wxBOTTOM, ui::pad()); + sizer->Add(pal_preview_, wx::sfWithBorder(1, wxBOTTOM).Expand()); // Add buttons - sizer->Add(CreateButtonSizer(wxOK | wxCANCEL), 0, wxEXPAND); + sizer->Add(CreateButtonSizer(wxOK | wxCANCEL), wxSizerFlags().Expand()); // Setup preview pal_preview_->setSelectionType(PaletteCanvas::SelectionType::Range); @@ -161,39 +163,41 @@ class PaletteTintDialog : public wxDialog wxDialog(parent, -1, "Tint", wxDefaultPosition, wxDefaultSize, wxDEFAULT_DIALOG_STYLE | wxRESIZE_BORDER), palette_{ pal } { + namespace wx = wxutil; + // Set dialog icon - wxutil::setWindowIcon(this, "palette_tint"); + wx::setWindowIcon(this, "palette_tint"); // Setup main sizer auto msizer = new wxBoxSizer(wxVERTICAL); SetSizer(msizer); auto sizer = new wxBoxSizer(wxVERTICAL); - msizer->Add(sizer, 1, wxEXPAND | wxALL, ui::padLarge()); + msizer->Add(sizer, wx::sfWithLargeBorder(1).Expand()); // Add colour chooser auto hbox = new wxBoxSizer(wxHORIZONTAL); - sizer->Add(hbox, 0, wxEXPAND | wxBOTTOM, ui::pad()); + sizer->Add(hbox, wx::sfWithBorder(0, wxBOTTOM).Expand()); cp_colour_ = new wxColourPickerCtrl(this, -1, wxColour(255, 0, 0)); - hbox->Add(new wxStaticText(this, -1, "Colour:"), 1, wxALIGN_CENTER_VERTICAL | wxRIGHT, ui::pad()); - hbox->Add(cp_colour_, 0, wxALIGN_CENTER_VERTICAL); + hbox->Add(new wxStaticText(this, -1, "Colour:"), wx::sfWithBorder(1, wxRIGHT).CenterVertical()); + hbox->Add(cp_colour_, wxSizerFlags().CenterVertical()); // Add 'amount' slider hbox = new wxBoxSizer(wxHORIZONTAL); - sizer->Add(hbox, 0, wxEXPAND | wxBOTTOM, ui::pad()); + sizer->Add(hbox, wx::sfWithBorder(0, wxBOTTOM).Expand()); slider_amount_ = new wxSlider(this, -1, 50, 0, 100); label_amount_ = new wxStaticText(this, -1, "100%"); - hbox->Add(new wxStaticText(this, -1, "Amount:"), 0, wxALIGN_CENTER_VERTICAL | wxRIGHT, ui::pad()); - hbox->Add(slider_amount_, 1, wxEXPAND | wxRIGHT, ui::pad()); - hbox->Add(label_amount_, 0, wxALIGN_CENTER_VERTICAL); + hbox->Add(new wxStaticText(this, -1, "Amount:"), wx::sfWithBorder(0, wxRIGHT).CenterVertical()); + hbox->Add(slider_amount_, wx::sfWithBorder(1, wxRIGHT).Expand()); + hbox->Add(label_amount_, wxSizerFlags().CenterVertical()); // Add preview pal_preview_ = new PaletteCanvas(this, -1); - sizer->Add(pal_preview_, 1, wxEXPAND | wxBOTTOM, ui::pad()); + sizer->Add(pal_preview_, wx::sfWithBorder(1, wxBOTTOM).Expand()); // Add buttons - sizer->Add(CreateButtonSizer(wxOK | wxCANCEL), 0, wxEXPAND); + sizer->Add(CreateButtonSizer(wxOK | wxCANCEL), wxSizerFlags().Expand()); // Setup preview pal_preview_->setSelectionType(PaletteCanvas::SelectionType::Range); @@ -227,7 +231,7 @@ class PaletteTintDialog : public wxDialog ColRGBA colour() const { return ColRGBA{ cp_colour_->GetColour() }; } - float amount() const { return (float)slider_amount_->GetValue() * 0.01f; } + float amount() const { return static_cast(slider_amount_->GetValue()) * 0.01f; } // Re-apply the changes in selection, colour and amount on a fresh palette void redraw() const @@ -270,51 +274,53 @@ class PaletteColourTweakDialog : public wxDialog wxDEFAULT_DIALOG_STYLE | wxRESIZE_BORDER), palette_{ pal } { + namespace wx = wxutil; + // Set dialog icon - wxutil::setWindowIcon(this, "palette_tweak"); + wx::setWindowIcon(this, "palette_tweak"); // Setup main sizer auto msizer = new wxBoxSizer(wxVERTICAL); SetSizer(msizer); auto sizer = new wxBoxSizer(wxVERTICAL); - msizer->Add(sizer, 1, wxEXPAND | wxALL, ui::padLarge()); + msizer->Add(sizer, wx::sfWithLargeBorder(1).Expand()); // Add 'hue shift' slider auto hbox = new wxBoxSizer(wxHORIZONTAL); - sizer->Add(hbox, 0, wxEXPAND | wxBOTTOM, ui::pad()); + sizer->Add(hbox, wx::sfWithBorder(0, wxBOTTOM).Expand()); slider_hue_ = new wxSlider(this, -1, 0, 0, 500); label_hue_ = new wxStaticText(this, -1, "0.000"); - hbox->Add(new wxStaticText(this, -1, "Hue Shift:"), 0, wxALIGN_CENTER_VERTICAL | wxRIGHT, ui::pad()); - hbox->Add(slider_hue_, 1, wxEXPAND | wxRIGHT, ui::pad()); - hbox->Add(label_hue_, 0, wxALIGN_CENTER_VERTICAL); + hbox->Add(new wxStaticText(this, -1, "Hue Shift:"), wx::sfWithBorder(0, wxRIGHT).CenterVertical()); + hbox->Add(slider_hue_, wx::sfWithBorder(1, wxRIGHT).Expand()); + hbox->Add(label_hue_, wxSizerFlags().CenterVertical()); // Add 'Saturation' slider hbox = new wxBoxSizer(wxHORIZONTAL); - sizer->Add(hbox, 0, wxEXPAND | wxBOTTOM, ui::pad()); + sizer->Add(hbox, wx::sfWithBorder(0, wxBOTTOM).Expand()); slider_sat_ = new wxSlider(this, -1, 100, 0, 200); label_sat_ = new wxStaticText(this, -1, "100%"); - hbox->Add(new wxStaticText(this, -1, "Saturation:"), 0, wxALIGN_CENTER_VERTICAL | wxRIGHT, ui::pad()); - hbox->Add(slider_sat_, 1, wxEXPAND | wxRIGHT, ui::pad()); - hbox->Add(label_sat_, 0, wxALIGN_CENTER_VERTICAL); + hbox->Add(new wxStaticText(this, -1, "Saturation:"), wx::sfWithBorder(0, wxRIGHT).CenterVertical()); + hbox->Add(slider_sat_, wx::sfWithBorder(1, wxRIGHT).Expand()); + hbox->Add(label_sat_, wxSizerFlags().CenterVertical()); // Add 'Luminosity' slider hbox = new wxBoxSizer(wxHORIZONTAL); - sizer->Add(hbox, 0, wxEXPAND | wxBOTTOM, ui::pad()); + sizer->Add(hbox, wx::sfWithBorder(0, wxBOTTOM).Expand()); slider_lum_ = new wxSlider(this, -1, 100, 0, 200); label_lum_ = new wxStaticText(this, -1, "100%"); - hbox->Add(new wxStaticText(this, -1, "Luminosity:"), 0, wxALIGN_CENTER_VERTICAL | wxRIGHT, ui::pad()); - hbox->Add(slider_lum_, 1, wxEXPAND | wxRIGHT, ui::pad()); - hbox->Add(label_lum_, 0, wxALIGN_CENTER_VERTICAL); + hbox->Add(new wxStaticText(this, -1, "Luminosity:"), wx::sfWithBorder(0, wxRIGHT).CenterVertical()); + hbox->Add(slider_lum_, wx::sfWithBorder(1, wxRIGHT).Expand()); + hbox->Add(label_lum_, wxSizerFlags().CenterVertical()); // Add preview pal_preview_ = new PaletteCanvas(this, -1); - sizer->Add(pal_preview_, 1, wxEXPAND | wxBOTTOM, ui::pad()); + sizer->Add(pal_preview_, wx::sfWithBorder(1, wxBOTTOM).Expand()); // Add buttons - sizer->Add(CreateButtonSizer(wxOK | wxCANCEL), 0, wxEXPAND); + sizer->Add(CreateButtonSizer(wxOK | wxCANCEL), wxSizerFlags().Expand()); // Setup preview pal_preview_->setSelectionType(PaletteCanvas::SelectionType::Range); @@ -361,9 +367,9 @@ class PaletteColourTweakDialog : public wxDialog Palette* finalPalette() const { return &(pal_preview_->palette()); } - float hue() const { return (float)slider_hue_->GetValue() * 0.002f; } - float sat() const { return (float)slider_sat_->GetValue() * 0.01f; } - float lum() const { return (float)slider_lum_->GetValue() * 0.01f; } + float hue() const { return static_cast(slider_hue_->GetValue()) * 0.002f; } + float sat() const { return static_cast(slider_sat_->GetValue()) * 0.01f; } + float lum() const { return static_cast(slider_lum_->GetValue()) * 0.01f; } // Re-apply the changes in selection, hue, saturation and luminosity on a fresh palette void redraw() const @@ -400,6 +406,8 @@ class PaletteInvertDialog : public wxDialog wxDialog(parent, -1, "Invert", wxDefaultPosition, wxDefaultSize, wxDEFAULT_DIALOG_STYLE | wxRESIZE_BORDER), palette_{ pal } { + namespace wx = wxutil; + // Set dialog icon wxutil::setWindowIcon(this, "palette_invert"); @@ -407,14 +415,14 @@ class PaletteInvertDialog : public wxDialog auto msizer = new wxBoxSizer(wxVERTICAL); SetSizer(msizer); auto sizer = new wxBoxSizer(wxVERTICAL); - msizer->Add(sizer, 1, wxEXPAND | wxALL, ui::padLarge()); + msizer->Add(sizer, wx::sfWithLargeBorder(1).Expand()); // Add preview pal_preview_ = new PaletteCanvas(this, -1); - sizer->Add(pal_preview_, 1, wxEXPAND | wxBOTTOM, ui::pad()); + sizer->Add(pal_preview_, wx::sfWithBorder(1, wxBOTTOM).Expand()); // Add buttons - sizer->Add(CreateButtonSizer(wxOK | wxCANCEL), 0, wxEXPAND); + sizer->Add(CreateButtonSizer(wxOK | wxCANCEL), wxSizerFlags().Expand()); // Setup preview pal_preview_->setSelectionType(PaletteCanvas::SelectionType::Range); @@ -468,6 +476,8 @@ class GeneratePalettesDialog : public wxDialog wxDefaultSize, wxDEFAULT_DIALOG_STYLE | wxRESIZE_BORDER) { + namespace wx = wxutil; + // Set dialog icon wxutil::setWindowIcon(this, "palette"); @@ -475,15 +485,15 @@ class GeneratePalettesDialog : public wxDialog auto msizer = new wxBoxSizer(wxVERTICAL); SetSizer(msizer); auto sizer = new wxBoxSizer(wxVERTICAL); - msizer->Add(sizer, 1, wxEXPAND | wxALL, ui::padLarge()); + msizer->Add(sizer, wx::sfWithLargeBorder(1).Expand()); // Add buttons rb_doom_ = new wxRadioButton(this, -1, "Doom (14 Palettes)", wxDefaultPosition, wxDefaultSize, wxRB_GROUP); - sizer->Add(rb_doom_, 0, wxEXPAND | wxBOTTOM, ui::pad()); + sizer->Add(rb_doom_, wx::sfWithBorder(0, wxBOTTOM).Expand()); rb_hexen_ = new wxRadioButton(this, -1, "Hexen (28 Palettes)"); - sizer->Add(rb_hexen_, 0, wxEXPAND); + sizer->Add(rb_hexen_, wxSizerFlags().Expand()); - sizer->Add(CreateButtonSizer(wxOK | wxCANCEL), 0, wxEXPAND); + sizer->Add(CreateButtonSizer(wxOK | wxCANCEL), wxSizerFlags().Expand()); // Init layout wxDialog::Layout(); @@ -523,6 +533,8 @@ class PaletteGradientDialog : public wxDialog wxDialog(parent, -1, "Gradient", wxDefaultPosition, wxDefaultSize, wxDEFAULT_DIALOG_STYLE | wxRESIZE_BORDER), palette_{ pal } { + namespace wx = wxutil; + // Set dialog icon wxutil::setWindowIcon(this, "palette_gradient"); @@ -530,26 +542,26 @@ class PaletteGradientDialog : public wxDialog auto msizer = new wxBoxSizer(wxVERTICAL); SetSizer(msizer); auto sizer = new wxBoxSizer(wxVERTICAL); - msizer->Add(sizer, 1, wxEXPAND | wxALL, ui::padLarge()); + msizer->Add(sizer, wx::sfWithLargeBorder(1).Expand()); // Add colour choosers auto hbox = new wxBoxSizer(wxHORIZONTAL); - sizer->Add(hbox, 0, wxEXPAND | wxBOTTOM, ui::pad()); + sizer->Add(hbox, wx::sfWithBorder(0, wxBOTTOM).Expand()); cp_startcolour_ = new wxColourPickerCtrl(this, -1, wxColour(0, 0, 0)); - hbox->Add(new wxStaticText(this, -1, "Start Colour:"), 1, wxALIGN_CENTER_VERTICAL | wxRIGHT, ui::pad()); - hbox->Add(cp_startcolour_, 0, wxEXPAND); + hbox->Add(new wxStaticText(this, -1, "Start Colour:"), wx::sfWithBorder(1, wxRIGHT).CenterVertical()); + hbox->Add(cp_startcolour_, wxSizerFlags().Expand()); cp_endcolour_ = new wxColourPickerCtrl(this, -1, wxColour(255, 255, 255)); - hbox->Add(new wxStaticText(this, -1, "End Colour:"), 1, wxALIGN_CENTER_VERTICAL | wxRIGHT, ui::pad()); - hbox->Add(cp_endcolour_, 0, wxEXPAND); + hbox->Add(new wxStaticText(this, -1, "End Colour:"), wx::sfWithBorder(1, wxRIGHT).CenterVertical()); + hbox->Add(cp_endcolour_, wxSizerFlags().Expand()); // Add preview pal_preview_ = new PaletteCanvas(this, -1); - sizer->Add(pal_preview_, 1, wxEXPAND | wxBOTTOM, ui::pad()); + sizer->Add(pal_preview_, wx::sfWithBorder(1, wxBOTTOM).Expand()); // Add buttons - sizer->Add(CreateButtonSizer(wxOK | wxCANCEL), 0, wxEXPAND); + sizer->Add(CreateButtonSizer(wxOK | wxCANCEL), wxSizerFlags().Expand()); // Setup preview pal_preview_->setSelectionType(PaletteCanvas::SelectionType::Range); @@ -638,7 +650,7 @@ PaletteEntryPanel::PaletteEntryPanel(wxWindow* parent) : EntryPanel(parent, "pal // --- Palette canvas --- pal_canvas_ = new PaletteCanvas(this, -1); pal_canvas_->setSelectionType(PaletteCanvas::SelectionType::One); - sizer_main_->Add(pal_canvas_, 1, wxEXPAND, 0); + sizer_main_->Add(pal_canvas_, wxSizerFlags(1).Expand()); // Bind events pal_canvas_->Bind(wxEVT_LEFT_DOWN, &PaletteEntryPanel::onPalCanvasMouseEvent, this); @@ -1083,8 +1095,9 @@ bool PaletteEntryPanel::generateColormaps() const else if (l == GRAYMAP) { // Generate inverse map - grey = ((float)rgb.r / 256.0 * col_greyscale_r) + ((float)rgb.g / 256.0 * col_greyscale_g) - + ((float)rgb.b / 256.0 * col_greyscale_b); + grey = (static_cast(rgb.r) / 256.0 * col_greyscale_r) + + (static_cast(rgb.g) / 256.0 * col_greyscale_g) + + (static_cast(rgb.b) / 256.0 * col_greyscale_b); grey = 1.0 - grey; // Clamp value: with Id Software's values, the sum is greater than 1.0 (0.299+0.587+0.144=1.030) // This means the negation above can give a negative value (for example, with RGB values of 247 or diff --git a/src/MainEditor/UI/EntryPanel/PaletteEntryPanel.h b/src/MainEditor/UI/EntryPanel/PaletteEntryPanel.h index 33c6089ec..3d25cd638 100644 --- a/src/MainEditor/UI/EntryPanel/PaletteEntryPanel.h +++ b/src/MainEditor/UI/EntryPanel/PaletteEntryPanel.h @@ -1,7 +1,6 @@ #pragma once #include "EntryPanel.h" -#include "Graphics/Palette/Palette.h" /* TODO: * - Improve and enrich palette edition functions @@ -18,6 +17,7 @@ namespace slade { +class Palette; class PaletteCanvas; class ArchiveEntry; diff --git a/src/MainEditor/UI/EntryPanel/TextEntryPanel.cpp b/src/MainEditor/UI/EntryPanel/TextEntryPanel.cpp index 9aac6b9e1..ffecb8df1 100644 --- a/src/MainEditor/UI/EntryPanel/TextEntryPanel.cpp +++ b/src/MainEditor/UI/EntryPanel/TextEntryPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -32,14 +32,17 @@ #include "Main.h" #include "TextEntryPanel.h" #include "Game/Configuration.h" +#include "Game/Game.h" #include "General/UI.h" #include "MainEditor/EntryOperations.h" +#include "MainEditor/MainEditor.h" +#include "TextEditor/TextLanguage.h" +#include "TextEditor/TextStyle.h" #include "TextEditor/UI/FindReplacePanel.h" #include "TextEditor/UI/TextEditorCtrl.h" #include "UI/Dialogs/Preferences/EditingPrefsPanel.h" #include "UI/Dialogs/Preferences/PreferencesDialog.h" #include "Utility/StringUtils.h" -#include "MainEditor/MainEditor.h" using namespace slade; @@ -66,14 +69,13 @@ TextEntryPanel::TextEntryPanel(wxWindow* parent) : EntryPanel(parent, "text") { // Create the text area text_area_ = new TextEditorCtrl(this, -1); - sizer_main_->Add(text_area_, 1, wxEXPAND, 0); + sizer_main_->Add(text_area_, wxSizerFlags(1).Expand()); // Create the find+replace panel panel_fr_ = new FindReplacePanel(this, *text_area_); text_area_->setFindReplacePanel(panel_fr_); panel_fr_->Hide(); - sizer_main_->Add(panel_fr_, 0, wxEXPAND | wxTOP, ui::padLarge()); - // sizer_main_->AddSpacer(UI::pad()); + sizer_main_->Add(panel_fr_, wxutil::sfWithLargeBorder(0, wxTOP).Expand()); // Add 'Text Language' choice to toolbar auto group_language = new SToolBarGroup(toolbar_, "Text Language", true); @@ -128,10 +130,8 @@ TextEntryPanel::TextEntryPanel(wxWindow* parent) : EntryPanel(parent, "text") menu_custom_->AppendSeparator(); SAction::fromId("ptxt_wrap")->addToMenu(menu_custom_); - custom_menu_name_ = "Text"; - wxWindowBase::Layout(); } diff --git a/src/MainEditor/UI/MainWindow.cpp b/src/MainEditor/UI/MainWindow.cpp index cee9c9d1d..4741beeab 100644 --- a/src/MainEditor/UI/MainWindow.cpp +++ b/src/MainEditor/UI/MainWindow.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net diff --git a/src/MainEditor/UI/StartPanel.cpp b/src/MainEditor/UI/StartPanel.cpp index 8733f6492..a20e2bc40 100644 --- a/src/MainEditor/UI/StartPanel.cpp +++ b/src/MainEditor/UI/StartPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -36,7 +36,6 @@ #include "App.h" #include "Archive/ArchiveManager.h" #include "General/SAction.h" -#include "General/UI.h" #include "UI/SToolBar/SToolBarButton.h" #include "UI/WxUtils.h" #include @@ -99,10 +98,10 @@ wxSizer* createLogoSizer(wxWindow* parent) // Logo auto logo_bitmap = new wxStaticBitmap(parent, -1, getIconBitmapBundle("general/logo.svg", 112)); - sizer->Add(logo_bitmap, wxSizerFlags(1).CenterVertical().Border(wxRIGHT, ui::padLarge())); + sizer->Add(logo_bitmap, wxutil::sfWithLargeBorder(1, wxRIGHT).CenterVertical()); auto vbox = new wxBoxSizer(wxVERTICAL); - sizer->Add(vbox, 1, wxEXPAND); + sizer->Add(vbox, wxSizerFlags(1).Expand()); vbox->AddStretchSpacer(); @@ -116,7 +115,7 @@ wxSizer* createLogoSizer(wxWindow* parent) auto tagline_label = new wxStaticText(parent, -1, "It's a Doom Editor"); tagline_label->SetFont(tagline_label->GetFont().Bold().Italic().Scale(1.2f)); tagline_label->SetForegroundColour(wxColour(blue_dark_colour)); - vbox->Add(tagline_label, wxSizerFlags().CenterHorizontal().Border(wxBOTTOM, ui::pad())); + vbox->Add(tagline_label, wxutil::sfWithBorder(0, wxBOTTOM).CenterHorizontal()); // Version auto version_label = new wxStaticText(parent, -1, "v" + app::version().toString()); @@ -134,27 +133,13 @@ wxSizer* createLogoSizer(wxWindow* parent) // ----------------------------------------------------------------------------- wxSizer* createActionsSizer(wxWindow* parent) { - auto sizer = new wxBoxSizer(wxVERTICAL); + auto sizer = new wxBoxSizer(wxVERTICAL); + auto sflags = wxutil::sfWithBorder(0, wxBOTTOM).Expand(); - // Open Archive - sizer->Add( - createActionButton(parent, "aman_open", "Open Archive", "open"), - wxSizerFlags().Expand().Border(wxBOTTOM, ui::pad())); - - // Open Directory - sizer->Add( - createActionButton(parent, "aman_opendir", "Open Directory", "opendir"), - wxSizerFlags().Expand().Border(wxBOTTOM, ui::pad())); - - // New Archive - sizer->Add( - createActionButton(parent, "aman_newarchive", "Create New Archive", "newarchive"), - wxSizerFlags().Expand().Border(wxBOTTOM, ui::pad())); - - // New Map - sizer->Add( - createActionButton(parent, "aman_newmap", "Create New Map", "mapeditor"), - wxSizerFlags().Expand().Border(wxBOTTOM, ui::pad())); + sizer->Add(createActionButton(parent, "aman_open", "Open Archive", "open"), sflags); + sizer->Add(createActionButton(parent, "aman_opendir", "Open Directory", "opendir"), sflags); + sizer->Add(createActionButton(parent, "aman_newarchive", "Create New Archive", "newarchive"), sflags); + sizer->Add(createActionButton(parent, "aman_newmap", "Create New Map", "mapeditor"), sflags); return sizer; } @@ -193,25 +178,27 @@ StartPanel::StartPanel(wxWindow* parent) : wxPanel(parent, -1) // ----------------------------------------------------------------------------- void StartPanel::setupLayout() { + namespace wx = wxutil; + auto main_sizer = new wxBoxSizer(wxVERTICAL); SetSizer(main_sizer); // Blue strip at the top auto top_panel = new wxPanel(this, -1, wxDefaultPosition, { -1, 4 }); top_panel->SetBackgroundColour(wxColour(116, 135, 175)); - main_sizer->Add(top_panel, wxSizerFlags(0).Expand()); + main_sizer->Add(top_panel, wxSizerFlags().Expand()); // Left side (logo + actions) auto left_sizer = new wxBoxSizer(wxVERTICAL); left_sizer->Add(createActionsSizer(this), wxSizerFlags(1).Right()); auto content_sizer = new wxBoxSizer(wxHORIZONTAL); - content_sizer->Add(left_sizer, wxSizerFlags(1).CenterVertical().Border(wxRIGHT, ui::padLarge())); - content_sizer->Add(recent_files_panel_, wxSizerFlags(1).CenterVertical().Border(wxLEFT, ui::padLarge())); + content_sizer->Add(left_sizer, wx::sfWithLargeBorder(1, wxRIGHT).CenterVertical()); + content_sizer->Add(recent_files_panel_, wx::sfWithLargeBorder(1, wxLEFT).CenterVertical()); main_sizer->AddStretchSpacer(); - main_sizer->Add(createLogoSizer(this), wxSizerFlags(0).Center().Border(wxBOTTOM, ui::padLarge())); - main_sizer->Add(content_sizer, wxSizerFlags(1).Center().Border(wxLEFT | wxRIGHT, ui::pad())); + main_sizer->Add(createLogoSizer(this), wx::sfWithLargeBorder(0, wxBOTTOM).Center()); + main_sizer->Add(content_sizer, wx::sfWithBorder(1, wxLEFT | wxRIGHT).Center()); main_sizer->AddStretchSpacer(); } @@ -231,7 +218,7 @@ void StartPanel::updateRecentFilesPanel() auto title_label = new wxStaticText(recent_files_panel_, -1, "Recent Files"); title_label->SetFont(title_label->GetFont().Bold().Scale(1.25f)); - sizer->Add(title_label, wxSizerFlags().Expand().Border(wxBOTTOM, ui::pad())); + sizer->Add(title_label, wxutil::sfWithBorder(0, wxBOTTOM).Expand()); auto recent_files = app::archiveManager().recentFiles(); if (recent_files.empty()) @@ -245,7 +232,7 @@ void StartPanel::updateRecentFilesPanel() auto index = 0; for (const auto& path : recent_files) { - sizer->Add(createRecentFileSizer(path, index), wxSizerFlags().Border(wxBOTTOM, ui::padMin())); + sizer->Add(createRecentFileSizer(path, index), wxutil::sfWithMinBorder(0, wxBOTTOM)); if (index++ > 10) break; @@ -289,8 +276,7 @@ wxSizer* StartPanel::createRecentFileSizer(string_view full_path, int index) con } sizer->Add( - new wxStaticBitmap(recent_files_panel_, -1, getIconBitmapBundle(icon, 16)), - wxSizerFlags().Border(wxRIGHT, ui::pad())); + new wxStaticBitmap(recent_files_panel_, -1, getIconBitmapBundle(icon, 16)), wxutil::sfWithBorder(0, wxRIGHT)); // Text -------------------------------------------------------------------- @@ -306,7 +292,7 @@ wxSizer* StartPanel::createRecentFileSizer(string_view full_path, int index) con filename_label->SetDoubleBuffered(true); if (path.fileName().length() > 24) filename_label->SetToolTip(wxutil::strFromView(path.fileName())); - sizer->Add(filename_label, wxSizerFlags().Bottom().Border(wxRIGHT, ui::padLarge())); + sizer->Add(filename_label, wxutil::sfWithLargeBorder(0, wxRIGHT).Bottom()); auto path_label = new wxStaticText(recent_files_panel_, -1, wxutil::strFromView(path.path(false))); sizer->Add(path_label, wxSizerFlags().Bottom()); diff --git a/src/MainEditor/UI/TextureXEditor/PatchBrowser.cpp b/src/MainEditor/UI/TextureXEditor/PatchBrowser.cpp index 79ea38f14..93e5d93cd 100644 --- a/src/MainEditor/UI/TextureXEditor/PatchBrowser.cpp +++ b/src/MainEditor/UI/TextureXEditor/PatchBrowser.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -40,6 +40,7 @@ #include "General/Misc.h" #include "General/ResourceManager.h" #include "Graphics/CTexture/CTexture.h" +#include "Graphics/CTexture/PatchTable.h" #include "Graphics/CTexture/TextureXList.h" #include "Graphics/SImage/SImage.h" #include "MainEditor/MainEditor.h" @@ -74,7 +75,7 @@ bool PatchBrowserItem::loadImage() SImage img; // Load patch image - if (type_ == Type::Patch) + if (patch_type_ == Type::Patch) { // Find patch entry auto entry = app::resources().getPatchEntry(name_.ToStdString(), nspace_.ToStdString(), archive_); @@ -87,7 +88,7 @@ bool PatchBrowserItem::loadImage() } // Or, load texture image - if (type_ == Type::CTexture) + if (patch_type_ == Type::CTexture) { // Find texture auto tex = app::resources().getTexture(name_.ToStdString(), "", archive_); @@ -122,7 +123,7 @@ wxString PatchBrowserItem::itemInfo() info += "Unknown size"; // Add patch type - if (type_ == Type::Patch) + if (patch_type_ == Type::Patch) info += ", Patch"; else info += ", Texture"; @@ -166,14 +167,16 @@ PatchBrowser::PatchBrowser(wxWindow* parent) : BrowserWindow(parent) items_root_->addChild("Unknown"); // Update when main palette changed - sc_palette_changed_ = theMainWindow->paletteChooser()->signals().palette_changed.connect([this]() { - // Update palette - palette_.copyPalette(theMainWindow->paletteChooser()->selectedPalette()); + sc_palette_changed_ = theMainWindow->paletteChooser()->signals().palette_changed.connect( + [this] + { + // Update palette + palette_->copyPalette(theMainWindow->paletteChooser()->selectedPalette()); - // Reload all items - reloadItems(); - Refresh(); - }); + // Reload all items + reloadItems(); + Refresh(); + }); // Set dialog title wxTopLevelWindow::SetTitle("Browse Patches"); @@ -443,15 +446,12 @@ bool PatchBrowser::openTextureXList(TextureXList* texturex, Archive* parent) // ----------------------------------------------------------------------------- // Returns the index of the currently selected patch, or -1 if none are selected // ----------------------------------------------------------------------------- -int PatchBrowser::selectedPatch() +int PatchBrowser::selectedPatch() const { // Get selected item auto item = dynamic_cast(selectedItem()); - if (item) - return item->index(); - else - return -1; + return item ? item->index() : -1; } // ----------------------------------------------------------------------------- @@ -464,7 +464,7 @@ void PatchBrowser::selectPatch(int pt_index) return; // Check index - if (pt_index < 0 || pt_index >= (int)patch_table_->nPatches()) + if (pt_index < 0 || pt_index >= static_cast(patch_table_->nPatches())) return; // Select by patch name diff --git a/src/MainEditor/UI/TextureXEditor/PatchBrowser.h b/src/MainEditor/UI/TextureXEditor/PatchBrowser.h index bcf7bfc74..ef0ca3f12 100644 --- a/src/MainEditor/UI/TextureXEditor/PatchBrowser.h +++ b/src/MainEditor/UI/TextureXEditor/PatchBrowser.h @@ -1,5 +1,6 @@ #pragma once +#include "UI/Browser/BrowserItem.h" #include "UI/Browser/BrowserWindow.h" namespace slade @@ -18,27 +19,27 @@ class PatchBrowserItem : public BrowserItem }; PatchBrowserItem( - wxString name, - Archive* archive = nullptr, - Type type = Type::Patch, - wxString nspace = "", - unsigned index = 0) : + const wxString& name, + Archive* archive = nullptr, + Type type = Type::Patch, + const wxString& nspace = "", + unsigned index = 0) : BrowserItem{ name, index, "patch" }, archive_{ archive }, - type_{ type }, + patch_type_{ type }, nspace_{ nspace } { } - ~PatchBrowserItem(); + ~PatchBrowserItem() override; bool loadImage() override; wxString itemInfo() override; void clearImage() override; private: - Archive* archive_ = nullptr; - Type type_ = Type::Patch; + Archive* archive_ = nullptr; + Type patch_type_ = Type::Patch; wxString nspace_; }; @@ -46,12 +47,12 @@ class PatchBrowser : public BrowserWindow { public: PatchBrowser(wxWindow* parent); - ~PatchBrowser() = default; + ~PatchBrowser() override = default; bool openPatchTable(PatchTable* table); bool openArchive(Archive* archive); bool openTextureXList(TextureXList* texturex, Archive* parent); - int selectedPatch(); + int selectedPatch() const; void selectPatch(int pt_index); void selectPatch(const wxString& name); void setFullPath(bool enabled) { full_path_ = enabled; } diff --git a/src/MainEditor/UI/TextureXEditor/PatchTablePanel.cpp b/src/MainEditor/UI/TextureXEditor/PatchTablePanel.cpp index 1b1a6ccb8..4cc05b7e1 100644 --- a/src/MainEditor/UI/TextureXEditor/PatchTablePanel.cpp +++ b/src/MainEditor/UI/TextureXEditor/PatchTablePanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -36,6 +36,7 @@ #include "Archive/ArchiveEntry.h" #include "Archive/ArchiveManager.h" #include "General/Misc.h" +#include "General/UI.h" #include "Graphics/SImage/SImage.h" #include "MainEditor/MainEditor.h" #include "MainEditor/UI/MainWindow.h" @@ -68,7 +69,8 @@ EXTERN_CVAR(String, dir_last) // PatchTableListView class constructor // ----------------------------------------------------------------------------- PatchTableListView::PatchTableListView(wxWindow* parent, PatchTable* patch_table) : - VirtualListView(parent), patch_table_{ patch_table } + VirtualListView(parent), + patch_table_{ patch_table } { // Add columns InsertColumn(0, "#"); @@ -97,7 +99,7 @@ wxString PatchTableListView::itemText(long item, long column, long index) const return "INVALID INDEX"; // Check index is ok - if (index < 0 || (unsigned)index > patch_table_->nPatches()) + if (index < 0 || static_cast(index) > patch_table_->nPatches()) return "INVALID INDEX"; // Get associated patch @@ -171,7 +173,7 @@ bool PatchTableListView::usageSort(long left, long right) return left < right; else return lv_current_->sortDescend() ? p2.used_in.size() < p1.used_in.size() : - p1.used_in.size() < p2.used_in.size(); + p1.used_in.size() < p2.used_in.size(); } // ----------------------------------------------------------------------------- @@ -198,7 +200,9 @@ void PatchTableListView::sortItems() // PatchTablePanel class constructor // ----------------------------------------------------------------------------- PatchTablePanel::PatchTablePanel(wxWindow* parent, PatchTable* patch_table, TextureXEditor* tx_editor) : - wxPanel(parent, -1), patch_table_{ patch_table }, parent_{ tx_editor } + wxPanel(parent, -1), + patch_table_{ patch_table }, + parent_{ tx_editor } { // Create controls list_patches_ = new PatchTableListView(this, patch_table); @@ -221,7 +225,7 @@ PatchTablePanel::PatchTablePanel(wxWindow* parent, PatchTable* patch_table, Text list_patches_->Bind(wxEVT_LIST_ITEM_SELECTED, &PatchTablePanel::onDisplayChanged, this); // Update when main palette changed - sc_palette_changed_ = theMainWindow->paletteChooser()->signals().palette_changed.connect([this]() + sc_palette_changed_ = theMainWindow->paletteChooser()->signals().palette_changed.connect([this] { updateDisplay(); }); } @@ -230,25 +234,27 @@ PatchTablePanel::PatchTablePanel(wxWindow* parent, PatchTable* patch_table, Text // ----------------------------------------------------------------------------- void PatchTablePanel::setupLayout() { + namespace wx = wxutil; + auto sizer = new wxBoxSizer(wxHORIZONTAL); SetSizer(sizer); // Patches List + actions auto frame = new wxStaticBox(this, -1, "Patch List (PNAMES)"); auto framesizer = new wxStaticBoxSizer(frame, wxHORIZONTAL); - sizer->Add(framesizer, 0, wxEXPAND | wxALL, ui::pad()); - framesizer->Add(toolbar_, 0, wxEXPAND | wxTOP | wxBOTTOM, ui::px(ui::Size::PadMinimum)); - framesizer->AddSpacer(ui::px(ui::Size::PadMinimum)); - framesizer->Add(list_patches_, 1, wxEXPAND | wxTOP | wxRIGHT | wxBOTTOM, ui::pad()); + sizer->Add(framesizer, wx::sfWithBorder().Expand()); + framesizer->Add(toolbar_, wx::sfWithMinBorder(0, wxTOP | wxBOTTOM).Expand()); + framesizer->AddSpacer(ui::padMin()); + framesizer->Add(list_patches_, wx::sfWithBorder(1, wxTOP | wxRIGHT | wxBOTTOM).Expand()); // Patch preview & info frame = new wxStaticBox(this, -1, "Patch Preview && Info"); framesizer = new wxStaticBoxSizer(frame, wxVERTICAL); - sizer->Add(framesizer, 1, wxEXPAND | wxTOP | wxRIGHT | wxBOTTOM, ui::pad()); - framesizer->Add(zc_zoom_, 0, wxALL, ui::pad()); - framesizer->Add(patch_canvas_, 1, wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, ui::pad()); - framesizer->Add(label_dimensions_, 0, wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, ui::pad()); - framesizer->Add(label_textures_, 0, wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, ui::pad()); + sizer->Add(framesizer, wx::sfWithBorder(1, wxTOP | wxRIGHT | wxBOTTOM).Expand()); + framesizer->Add(zc_zoom_, wx::sfWithBorder()); + framesizer->Add(patch_canvas_, wx::sfWithBorder(1, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); + framesizer->Add(label_dimensions_, wx::sfWithBorder(0, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); + framesizer->Add(label_textures_, wx::sfWithBorder(0, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); } // ----------------------------------------------------------------------------- diff --git a/src/MainEditor/UI/TextureXEditor/PatchTablePanel.h b/src/MainEditor/UI/TextureXEditor/PatchTablePanel.h index 3409458b7..537393854 100644 --- a/src/MainEditor/UI/TextureXEditor/PatchTablePanel.h +++ b/src/MainEditor/UI/TextureXEditor/PatchTablePanel.h @@ -2,11 +2,11 @@ #include "General/SAction.h" #include "General/Sigslot.h" -#include "Graphics/CTexture/PatchTable.h" #include "UI/Lists/VirtualListView.h" namespace slade { +class PatchTable; class GfxCanvas; class TextureXEditor; class SToolBar; @@ -24,7 +24,7 @@ class PatchTableListView : public VirtualListView public: PatchTableListView(wxWindow* parent, PatchTable* patch_table); - ~PatchTableListView() = default; + ~PatchTableListView() override = default; PatchTable* patchTable() const { return patch_table_; } @@ -43,7 +43,7 @@ class PatchTablePanel : public wxPanel, SActionHandler { public: PatchTablePanel(wxWindow* parent, PatchTable* patch_table, TextureXEditor* tx_editor = nullptr); - ~PatchTablePanel() = default; + ~PatchTablePanel() override = default; private: PatchTable* patch_table_ = nullptr; diff --git a/src/MainEditor/UI/TextureXEditor/TextureEditorPanel.cpp b/src/MainEditor/UI/TextureXEditor/TextureEditorPanel.cpp index 4ca616de3..139b86459 100644 --- a/src/MainEditor/UI/TextureXEditor/TextureEditorPanel.cpp +++ b/src/MainEditor/UI/TextureXEditor/TextureEditorPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -32,10 +32,13 @@ #include "Main.h" #include "TextureEditorPanel.h" #include "General/KeyBind.h" +#include "General/SAction.h" +#include "General/UI.h" #include "Graphics/CTexture/TextureXList.h" #include "TextureXEditor.h" #include "UI/Canvas/CTextureCanvas.h" #include "UI/Controls/ZoomControl.h" +#include "UI/Lists/ListView.h" #include "UI/SToolBar/SToolBar.h" #include "UI/SToolBar/SToolBarButton.h" #include "UI/WxUtils.h" @@ -77,7 +80,8 @@ EXTERN_CVAR(Bool, tx_arc) // TextureEditorPanel class constructor // ----------------------------------------------------------------------------- TextureEditorPanel::TextureEditorPanel(wxWindow* parent, TextureXEditor* tx_editor) : - wxPanel(parent, -1), tx_editor_{ tx_editor } + wxPanel(parent, -1), + tx_editor_{ tx_editor } { // Create controls tex_canvas_ = new CTextureCanvas(this, -1); @@ -96,6 +100,8 @@ TextureEditorPanel::TextureEditorPanel(wxWindow* parent, TextureXEditor* tx_edit // ----------------------------------------------------------------------------- void TextureEditorPanel::setupLayout() { + namespace wx = wxutil; + // Init controls cb_tex_scale_->SetValue(tx_apply_scale); cb_tex_arc_->SetValue(tx_arc); @@ -116,37 +122,37 @@ void TextureEditorPanel::setupLayout() // Setup left section (view controls + texture canvas + texture controls) auto vbox = new wxBoxSizer(wxVERTICAL); - sizer->Add(vbox, 1, wxEXPAND | wxRIGHT, ui::pad()); + sizer->Add(vbox, wx::sfWithBorder(1, wxRIGHT).Expand()); // Add view controls auto hbox = new wxBoxSizer(wxHORIZONTAL); - vbox->Add(hbox, 0, wxEXPAND | wxBOTTOM | wxTOP, ui::px(ui::Size::PadMinimum)); - hbox->Add(zc_zoom_, 0, wxEXPAND | wxRIGHT, ui::pad()); + vbox->Add(hbox, wx::sfWithMinBorder(0, wxBOTTOM | wxTOP).Expand()); + hbox->Add(zc_zoom_, wx::sfWithBorder(0, wxRIGHT).Expand()); hbox->AddStretchSpacer(); - hbox->Add(cb_tex_scale_, 0, wxEXPAND | wxRIGHT, ui::pad()); - hbox->Add(cb_tex_arc_, 0, wxEXPAND | wxRIGHT, ui::pad()); - hbox->Add(cb_draw_outside_, 0, wxEXPAND); + hbox->Add(cb_tex_scale_, wx::sfWithBorder(0, wxRIGHT).Expand()); + hbox->Add(cb_tex_arc_, wx::sfWithBorder(0, wxRIGHT).Expand()); + hbox->Add(cb_draw_outside_, wxSizerFlags().Expand()); // Add texture canvas - vbox->Add(tex_canvas_, 1, wxEXPAND); + vbox->Add(tex_canvas_, wxSizerFlags(1).Expand()); // Add extra view controls hbox = new wxBoxSizer(wxHORIZONTAL); - vbox->Add(hbox, 0, wxEXPAND | wxBOTTOM | wxTOP, ui::pad()); - hbox->Add(label_viewtype_, 0, wxALIGN_CENTER_VERTICAL | wxRIGHT, ui::pad()); - hbox->Add(choice_viewtype_, 0, wxEXPAND); + vbox->Add(hbox, wx::sfWithBorder(0, wxBOTTOM | wxTOP).Expand()); + hbox->Add(label_viewtype_, wx::sfWithBorder(0, wxRIGHT).CenterVertical()); + hbox->Add(choice_viewtype_, wxSizerFlags().Expand()); hbox->AddStretchSpacer(); - hbox->Add(cb_blend_rgba_, 0, wxEXPAND); + hbox->Add(cb_blend_rgba_, wxSizerFlags().Expand()); // Add texture controls - vbox->Add(createTextureControls(this), 0, wxEXPAND); + vbox->Add(createTextureControls(this), wxSizerFlags().Expand()); // Setup right section (patch controls) vbox = new wxBoxSizer(wxVERTICAL); - sizer->Add(vbox, 0, wxEXPAND); + sizer->Add(vbox, wxSizerFlags().Expand()); // Add patch controls - vbox->Add(createPatchControls(this), 1, wxEXPAND); + vbox->Add(createPatchControls(this), wxSizerFlags(1).Expand()); // Bind events @@ -201,10 +207,10 @@ wxPanel* TextureEditorPanel::createTextureControls(wxWindow* parent) // "Texture Properties" frame auto frame = new wxStaticBox(panel, -1, "Texture Properties"); auto framesizer = new wxStaticBoxSizer(frame, wxVERTICAL); - sizer->Add(framesizer, 1, wxEXPAND); + sizer->Add(framesizer, wxSizerFlags(1).Expand()); auto gb_sizer = new wxGridBagSizer(ui::pad(), ui::pad()); - framesizer->Add(gb_sizer, 1, wxALL, ui::pad()); + framesizer->Add(gb_sizer, wxutil::sfWithBorder(1)); // Layout gb_sizer->Add(new wxStaticText(panel, -1, "Name:"), { 0, 0 }, { 1, 1 }, wxALIGN_CENTER_VERTICAL); @@ -276,6 +282,8 @@ void TextureEditorPanel::updateTextureScaleLabel() // ----------------------------------------------------------------------------- wxPanel* TextureEditorPanel::createPatchControls(wxWindow* parent) { + namespace wx = wxutil; + auto panel = new wxPanel(parent, -1); // Setup panel sizer @@ -285,7 +293,7 @@ wxPanel* TextureEditorPanel::createPatchControls(wxWindow* parent) // -- Texture Patches frame -- auto frame = new wxStaticBox(panel, -1, "Patches"); auto framesizer = new wxStaticBoxSizer(frame, wxHORIZONTAL); - sizer->Add(framesizer, 0, wxEXPAND | wxBOTTOM, ui::pad()); + sizer->Add(framesizer, wx::sfWithBorder(0, wxBOTTOM).Expand()); // Create patches list list_patches_ = new ListView(panel, -1); @@ -306,14 +314,14 @@ wxPanel* TextureEditorPanel::createPatchControls(wxWindow* parent) // Layout list_patches_->SetInitialSize(wxutil::scaledSize(100, tb_patches_->group("_Patch")->GetBestSize().y)); - framesizer->Add(list_patches_, 1, wxEXPAND | wxLEFT | wxTOP | wxBOTTOM, ui::pad()); - framesizer->Add(tb_patches_, 0, wxEXPAND | wxLEFT | wxTOP | wxBOTTOM, ui::px(ui::Size::PadMinimum)); + framesizer->Add(list_patches_, wx::sfWithBorder(1, wxLEFT | wxTOP | wxBOTTOM).Expand()); + framesizer->Add(tb_patches_, wx::sfWithMinBorder(0, wxLEFT | wxTOP | wxBOTTOM).Expand()); // -- Patch Properties frame -- frame = new wxStaticBox(panel, -1, "Patch Properties"); framesizer = new wxStaticBoxSizer(frame, wxVERTICAL); - sizer->Add(framesizer, 1, wxEXPAND); + sizer->Add(framesizer, wxSizerFlags(1).Expand()); // X Position const auto spinsize = wxSize{ ui::px(ui::Size::SpinCtrlWidth), -1 }; @@ -321,14 +329,14 @@ wxPanel* TextureEditorPanel::createPatchControls(wxWindow* parent) auto hbox = new wxBoxSizer(wxHORIZONTAL); framesizer->Add(hbox, 0, wxEXPAND | wxALL, ui::pad()); spin_patch_left_ = new wxSpinCtrl(panel, -1, "", wxDefaultPosition, spinsize, spinflags, SHRT_MIN, SHRT_MAX); - hbox->Add(new wxStaticText(panel, -1, "X Position:"), 0, wxALIGN_CENTER_VERTICAL | wxRIGHT, ui::pad()); + hbox->Add(new wxStaticText(panel, -1, "X Position:"), wx::sfWithBorder(0, wxRIGHT).CenterVertical()); hbox->Add(spin_patch_left_, 1); // Y Position hbox = new wxBoxSizer(wxHORIZONTAL); framesizer->Add(hbox, 0, wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, ui::pad()); spin_patch_top_ = new wxSpinCtrl(panel, -1, "", wxDefaultPosition, spinsize, spinflags, SHRT_MIN, SHRT_MAX); - hbox->Add(new wxStaticText(panel, -1, "Y Position:"), 0, wxALIGN_CENTER_VERTICAL | wxRIGHT, ui::pad()); + hbox->Add(new wxStaticText(panel, -1, "Y Position:"), wx::sfWithBorder(0, wxRIGHT).CenterVertical()); hbox->Add(spin_patch_top_, 1); return panel; @@ -462,7 +470,7 @@ void TextureEditorPanel::clearTexture() // ----------------------------------------------------------------------------- // Sets the texture canvas' palette and refreshes it // ----------------------------------------------------------------------------- -void TextureEditorPanel::setPalette(Palette* pal) const +void TextureEditorPanel::setPalette(const Palette* pal) const { tex_canvas_->setPalette(pal); tex_canvas_->updatePatchTextures(); @@ -739,6 +747,8 @@ bool TextureEditorPanel::handleSAction(string_view id) // // ----------------------------------------------------------------------------- +// ReSharper disable CppMemberFunctionMayBeConst +// ReSharper disable CppParameterMayBeConstPtrOrRef // ----------------------------------------------------------------------------- // Called when the 'show outside' checkbox is changed @@ -1077,7 +1087,7 @@ void TextureEditorPanel::onTexScaleXChanged(wxCommandEvent& e) { // Set texture's x scale if (tex_current_) - tex_current_->setScaleX((double)spin_tex_scalex_->GetValue() / 8.0); + tex_current_->setScaleX(static_cast(spin_tex_scalex_->GetValue()) / 8.0); // Update UI updateTextureScaleLabel(); @@ -1092,7 +1102,7 @@ void TextureEditorPanel::onTexScaleYChanged(wxCommandEvent& e) { // Set texture's y scale if (tex_current_) - tex_current_->setScaleY((double)spin_tex_scaley_->GetValue() / 8.0); + tex_current_->setScaleY(static_cast(spin_tex_scaley_->GetValue()) / 8.0); // Update UI updateTextureScaleLabel(); diff --git a/src/MainEditor/UI/TextureXEditor/TextureEditorPanel.h b/src/MainEditor/UI/TextureXEditor/TextureEditorPanel.h index b47da55d7..cf5a85687 100644 --- a/src/MainEditor/UI/TextureXEditor/TextureEditorPanel.h +++ b/src/MainEditor/UI/TextureXEditor/TextureEditorPanel.h @@ -1,9 +1,8 @@ #pragma once -#include "UI/Lists/ListView.h" - namespace slade { +class ListView; class TextureXEditor; class TextureXList; class CTextureCanvas; @@ -36,7 +35,7 @@ class TextureEditorPanel : public wxPanel bool openTexture(const CTexture* tex, TextureXList* list); void clearTexture(); - void setPalette(Palette* pal) const; + void setPalette(const Palette* pal) const; Palette* palette() const; bool blendRGBA() const; diff --git a/src/MainEditor/UI/TextureXEditor/TextureXEditor.cpp b/src/MainEditor/UI/TextureXEditor/TextureXEditor.cpp index 30502ba17..0fe0b44f2 100644 --- a/src/MainEditor/UI/TextureXEditor/TextureXEditor.cpp +++ b/src/MainEditor/UI/TextureXEditor/TextureXEditor.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -36,8 +36,12 @@ #include "Archive/ArchiveManager.h" #include "General/ResourceManager.h" #include "General/UndoRedo.h" +#include "Graphics/CTexture/TextureXList.h" #include "MainEditor/MainEditor.h" #include "MainEditor/UI/MainWindow.h" +#include "PatchBrowser.h" +#include "PatchTablePanel.h" +#include "TextureXPanel.h" #include "UI/Controls/PaletteChooser.h" #include "UI/Controls/UndoManagerHistoryPanel.h" #include "UI/Dialogs/ExtMessageDialog.h" @@ -58,6 +62,8 @@ class CreateTextureXDialog : public wxDialog public: CreateTextureXDialog(wxWindow* parent) : wxDialog(parent, -1, "Create Texture Definitions") { + namespace wx = wxutil; + // Setup layout auto m_vbox = new wxBoxSizer(wxVERTICAL); SetSizer(m_vbox); @@ -65,44 +71,42 @@ class CreateTextureXDialog : public wxDialog // --- Format options --- auto frame = new wxStaticBox(this, -1, "Format"); auto framesizer = new wxStaticBoxSizer(frame, wxVERTICAL); - m_vbox->Add(framesizer, 0, wxEXPAND | wxALL, ui::pad()); + m_vbox->Add(framesizer, wx::sfWithBorder().Expand()); // Doom format rb_format_doom_ = new wxRadioButton( this, -1, "Doom (TEXTURE1 + PNAMES)", wxDefaultPosition, wxDefaultSize, wxRB_GROUP); rb_format_strife_ = new wxRadioButton(this, -1, "Strife (TEXTURE1 + PNAMES)"); rb_format_textures_ = new wxRadioButton(this, -1, "ZDoom (TEXTURES)"); - wxutil::layoutVertically( - framesizer, - { rb_format_doom_, rb_format_strife_, rb_format_textures_ }, - wxSizerFlags(1).Expand().Border(wxALL, ui::pad())); + wx::layoutVertically( + framesizer, { rb_format_doom_, rb_format_strife_, rb_format_textures_ }, wx::sfWithBorder(1).Expand()); // --- Source options --- frame = new wxStaticBox(this, -1, "Source"); framesizer = new wxStaticBoxSizer(frame, wxVERTICAL); - m_vbox->Add(framesizer, 0, wxEXPAND | wxALL, ui::pad()); + m_vbox->Add(framesizer, wx::sfWithBorder().Expand()); // New list rb_new_ = new wxRadioButton(this, -1, "Create New (Empty)", wxDefaultPosition, wxDefaultSize, wxRB_GROUP); - framesizer->Add(rb_new_, 0, wxEXPAND | wxALL, ui::pad()); + framesizer->Add(rb_new_, wx::sfWithBorder().Expand()); // Import from Base Resource Archive rb_import_bra_ = new wxRadioButton(this, -1, "Import from Base Resource Archive:"); - framesizer->Add(rb_import_bra_, 0, wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, ui::pad()); + framesizer->Add(rb_import_bra_, wx::sfWithBorder(0, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); // Add buttons - m_vbox->Add(CreateButtonSizer(wxOK | wxCANCEL), 0, wxEXPAND | wxALL, ui::pad()); + m_vbox->Add(CreateButtonSizer(wxOK | wxCANCEL), wx::sfWithBorder().Expand()); // Bind events rb_new_->Bind(wxEVT_RADIOBUTTON, &CreateTextureXDialog::onRadioNewSelected, this); rb_import_bra_->Bind(wxEVT_RADIOBUTTON, &CreateTextureXDialog::onRadioNewSelected, this); SetInitialSize(wxSize(-1, -1)); - wxWindowBase::Layout(); + wxTopLevelWindowBase::Layout(); } - ~CreateTextureXDialog() = default; + ~CreateTextureXDialog() override = default; TextureXList::Format getSelectedFormat() const { @@ -202,24 +206,28 @@ TextureXEditor::TextureXEditor(wxWindow* parent) : wxPanel(parent, -1) // Add tabs tabs_ = STabCtrl::createControl(this); - sizer->Add(tabs_, 1, wxEXPAND | wxALL, ui::pad()); + sizer->Add(tabs_, wxutil::sfWithBorder(1).Expand()); // Bind events Bind(wxEVT_SHOW, &TextureXEditor::onShow, this); // Update patch browser & palette when resources are updated or the patch table is modified - sc_resources_updated_ = app::resources().signals().resources_updated.connect([this]() { - pb_update_ = true; - updateTexturePalette(); - }); - sc_ptable_modified_ = patch_table_.signals().modified.connect([this]() { - pb_update_ = true; - updateTexturePalette(); - }); + sc_resources_updated_ = app::resources().signals().resources_updated.connect( + [this] + { + pb_update_ = true; + updateTexturePalette(); + }); + sc_ptable_modified_ = patch_table_.signals().modified.connect( + [this] + { + pb_update_ = true; + updateTexturePalette(); + }); // Update the editor palette if the main palette is changed sc_palette_changed_ = theMainWindow->paletteChooser()->signals().palette_changed.connect( - [this]() { updateTexturePalette(); }); + [this] { updateTexturePalette(); }); // Update + layout updateTexturePalette(); @@ -377,7 +385,7 @@ bool TextureXEditor::openArchive(Archive* archive) // ----------------------------------------------------------------------------- // Sets the texture panels' palettes to what is selected in the palette chooser // ----------------------------------------------------------------------------- -void TextureXEditor::updateTexturePalette() +void TextureXEditor::updateTexturePalette() const { // Get palette auto pal = theMainWindow->paletteChooser()->selectedPalette(); @@ -629,7 +637,7 @@ void TextureXEditor::setSelection(size_t index) const if (index < tabs_->GetPageCount() && index != tabs_->GetSelection()) tabs_->SetSelection(index); } -void TextureXEditor::setSelection(ArchiveEntry* entry) const +void TextureXEditor::setSelection(const ArchiveEntry* entry) const { for (size_t a = 0; a < tabs_->GetPageCount(); a++) { @@ -678,7 +686,7 @@ void TextureXEditor::updateMenuStatus() const // ----------------------------------------------------------------------------- // Performs an undo operation // ----------------------------------------------------------------------------- -void TextureXEditor::undo() +void TextureXEditor::undo() const { wxString action = undo_manager_->undo(); if (!action.empty()) @@ -691,7 +699,7 @@ void TextureXEditor::undo() // ----------------------------------------------------------------------------- // Performs an redo operation // ----------------------------------------------------------------------------- -void TextureXEditor::redo() +void TextureXEditor::redo() const { wxString action = undo_manager_->redo(); if (!action.empty()) @@ -701,6 +709,14 @@ void TextureXEditor::redo() } } +// ----------------------------------------------------------------------------- +// Set if full path is enabled in the patch browser +// ----------------------------------------------------------------------------- +void TextureXEditor::setFullPath(bool enabled) const +{ + patch_browser_->setFullPath(enabled); +} + // ----------------------------------------------------------------------------- // diff --git a/src/MainEditor/UI/TextureXEditor/TextureXEditor.h b/src/MainEditor/UI/TextureXEditor/TextureXEditor.h index d081e4e2a..e18f12179 100644 --- a/src/MainEditor/UI/TextureXEditor/TextureXEditor.h +++ b/src/MainEditor/UI/TextureXEditor/TextureXEditor.h @@ -1,21 +1,22 @@ #pragma once -#include "Archive/Archive.h" -#include "General/UndoRedo.h" #include "Graphics/CTexture/PatchTable.h" -#include "PatchBrowser.h" -#include "PatchTablePanel.h" -#include "TextureEditorPanel.h" -#include "TextureXPanel.h" #include "UI/Controls/STabCtrl.h" namespace slade { +class PatchBrowser; +class TextureXPanel; +class ArchiveEntry; +class UndoManager; +class PatchTable; +class Archive; + class TextureXEditor : public wxPanel { public: TextureXEditor(wxWindow* parent); - ~TextureXEditor(); + ~TextureXEditor() override; Archive* archive() const { return archive_; } PatchTable& patchTable() { return patch_table_; } @@ -23,18 +24,18 @@ class TextureXEditor : public wxPanel UndoManager* undoManager() const { return undo_manager_.get(); } bool openArchive(Archive* archive); - void updateTexturePalette(); + void updateTexturePalette() const; void saveChanges(); bool close(); void showTextureMenu(bool show = true) const; void setSelection(size_t index) const; - void setSelection(ArchiveEntry* entry) const; + void setSelection(const ArchiveEntry* entry) const; void updateMenuStatus() const; - void undo(); - void redo(); + void undo() const; + void redo() const; // Editing - void setFullPath(bool enabled = false) const { patch_browser_->setFullPath(enabled); } + void setFullPath(bool enabled = false) const; bool removePatch(unsigned index, bool delete_entry = false); int browsePatchTable(const wxString& first = "") const; wxString browsePatchEntry(const wxString& first = ""); diff --git a/src/MainEditor/UI/TextureXEditor/TextureXPanel.cpp b/src/MainEditor/UI/TextureXEditor/TextureXPanel.cpp index bd39bcdf9..c1d3a7504 100644 --- a/src/MainEditor/UI/TextureXEditor/TextureXPanel.cpp +++ b/src/MainEditor/UI/TextureXEditor/TextureXPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -38,9 +38,9 @@ #include "General/ColourConfiguration.h" #include "General/KeyBind.h" #include "General/Misc.h" -#include "General/ResourceManager.h" #include "General/UI.h" #include "General/UndoRedo.h" +#include "Graphics/CTexture/TextureXList.h" #include "MainEditor/MainEditor.h" #include "TextureXEditor.h" #include "UI/Controls/SIconButton.h" @@ -72,7 +72,7 @@ EXTERN_CVAR(Bool, wad_force_uppercase) // ----------------------------------------------------------------------------- namespace { -bool TxListIsTextures(const TextureXList& tx) +bool txListIsTextures(const TextureXList& tx) { return tx.format() == TextureXList::Format::Textures; } @@ -88,7 +88,8 @@ class TextureClipboardItem : public ClipboardItem { public: TextureClipboardItem(const CTexture& texture, Archive* parent) : - ClipboardItem(Type::CompositeTexture), texture_{ new CTexture() } + ClipboardItem(Type::CompositeTexture), + texture_{ new CTexture() } { // Create/copy texture texture_->copyTexture(texture); @@ -157,13 +158,17 @@ class NewTextureDialog : public wxDialog { public: NewTextureDialog(wxWindow* parent, TextureXEditor* editor, TextureXList* texturex) : - wxDialog(parent, -1, "New Texture"), editor_{ editor }, texturex_{ texturex } + wxDialog(parent, -1, "New Texture"), + editor_{ editor }, + texturex_{ texturex } { - wxutil::setWindowIcon(this, "tex_new"); + namespace wx = wxutil; + + wx::setWindowIcon(this, "tex_new"); SetSizer(new wxBoxSizer(wxVERTICAL)); auto* sizer = new wxGridBagSizer(ui::pad(), ui::pad()); - GetSizer()->Add(sizer, 1, wxEXPAND | wxLEFT | wxRIGHT | wxTOP, ui::padLarge()); + GetSizer()->Add(sizer, wx::sfWithLargeBorder(1, wxLEFT | wxRIGHT | wxTOP).Expand()); // Name text_name_ = new wxTextCtrl(this, -1); @@ -173,8 +178,8 @@ class NewTextureDialog : public wxDialog // Blank rb_blank_ = new wxRadioButton(this, -1, "Blank"); rb_blank_->SetValue(true); - spin_width_ = wxutil::createSpinCtrl(this, 64, 0, 4096); - spin_height_ = wxutil::createSpinCtrl(this, 128, 0, 4096); + spin_width_ = wx::createSpinCtrl(this, 64, 0, 4096); + spin_height_ = wx::createSpinCtrl(this, 128, 0, 4096); sizer->Add(rb_blank_, { 1, 0 }, { 1, 1 }, wxALIGN_CENTER_VERTICAL); sizer->Add(new wxStaticText(this, -1, "Size:"), { 1, 1 }, { 1, 1 }, wxALIGN_CENTER_VERTICAL | wxALIGN_RIGHT); sizer->Add(spin_width_, { 1, 2 }, { 1, 1 }, wxEXPAND); @@ -195,9 +200,7 @@ class NewTextureDialog : public wxDialog // Separator GetSizer()->Add( new wxStaticLine(this, -1, wxDefaultPosition, wxDefaultSize, wxHORIZONTAL), - 0, - wxEXPAND | wxLEFT | wxRIGHT | wxTOP, - ui::padLarge()); + wx::sfWithLargeBorder(0, wxLEFT | wxRIGHT | wxTOP).Expand()); // Dialog buttons auto* btn_create = new wxButton(this, -1, "Create"); @@ -205,9 +208,9 @@ class NewTextureDialog : public wxDialog btn_create->SetDefault(); auto* hbox = new wxBoxSizer(wxHORIZONTAL); hbox->AddStretchSpacer(1); - hbox->Add(btn_create, 0, wxEXPAND | wxRIGHT, ui::pad()); - hbox->Add(btn_cancel, 0, wxEXPAND); - GetSizer()->Add(hbox, 0, wxEXPAND | wxALL, ui::padLarge()); + hbox->Add(btn_create, wx::sfWithBorder(0, wxRIGHT).Expand()); + hbox->Add(btn_cancel, wxSizerFlags().Expand()); + GetSizer()->Add(hbox, wx::sfWithLargeBorder().Expand()); // Bind events rb_blank_->Bind( @@ -238,7 +241,7 @@ class NewTextureDialog : public wxDialog // Setup dialog size SetInitialSize({ ui::scalePx(400), -1 }); - wxWindowBase::Layout(); + wxTopLevelWindowBase::Layout(); wxWindowBase::Fit(); wxTopLevelWindowBase::SetMinSize(GetBestSize()); CenterOnParent(); @@ -285,7 +288,7 @@ class NewTextureDialog : public wxDialog { // Browse for patch wxString patch; - if (TxListIsTextures(*texturex_)) + if (txListIsTextures(*texturex_)) patch = editor_->browsePatchEntry(); else patch = editor_->patchTable().patchName(editor_->browsePatchTable()); @@ -307,7 +310,8 @@ class NewTextureDialog : public wxDialog // TextureXListView class constructor // ----------------------------------------------------------------------------- TextureXListView::TextureXListView(wxWindow* parent, TextureXList* texturex) : - VirtualListView{ parent }, texturex_{ texturex } + VirtualListView{ parent }, + texturex_{ texturex } { // Add columns InsertColumn(0, "Name"); @@ -327,7 +331,7 @@ wxString TextureXListView::itemText(long item, long column, long index) const return "INVALID INDEX"; // Check index is ok - if (index < 0 || (unsigned)index > texturex_->size()) + if (index < 0 || static_cast(index) > texturex_->size()) return "INVALID INDEX"; // Get associated texture @@ -354,7 +358,7 @@ void TextureXListView::updateItemAttr(long item, long column, long index) const return; // Check index is ok - if (index < 0 || (unsigned)index > texturex_->size()) + if (index < 0 || static_cast(index) > texturex_->size()) return; // Get associated texture @@ -370,10 +374,10 @@ void TextureXListView::updateItemAttr(long item, long column, long index) const // Set colour depending on entry state switch (tex->state()) { - case 1: item_attr_->SetTextColour(colourconfig::colour("modified").toWx()); break; - case 2: item_attr_->SetTextColour(colourconfig::colour("new").toWx()); break; + case 1: item_attr_->SetTextColour(colourconfig::colour("modified").toWx()); break; + case 2: item_attr_->SetTextColour(colourconfig::colour("new").toWx()); break; default: item_attr_->SetTextColour(wxSystemSettings::GetColour(wxSYS_COLOUR_LISTBOXTEXT)); break; - }; + } } // ----------------------------------------------------------------------------- @@ -488,7 +492,9 @@ class TextureSwapUS : public UndoStep { public: TextureSwapUS(TextureXList& texturex, int index1, int index2) : - texturex_(texturex), index1_(index1), index2_(index2) + texturex_(&texturex), + index1_(index1), + index2_(index2) { } ~TextureSwapUS() override = default; @@ -496,7 +502,7 @@ class TextureSwapUS : public UndoStep bool doSwap() const { // Get parent dir - texturex_.swapTextures(index1_, index2_); + texturex_->swapTextures(index1_, index2_); return true; } @@ -504,9 +510,9 @@ class TextureSwapUS : public UndoStep bool doRedo() override { return doSwap(); } private: - TextureXList& texturex_; - int index1_ = -1; - int index2_ = -1; + TextureXList* texturex_ = nullptr; + int index1_ = -1; + int index2_ = -1; }; class TextureCreateDeleteUS : public UndoStep @@ -519,7 +525,10 @@ class TextureCreateDeleteUS : public UndoStep // Texture Deleted TextureCreateDeleteUS(TextureXPanel* tx_panel, unique_ptr tex_removed, int removed_index) : - tx_panel_{ tx_panel }, tex_removed_{ std::move(tex_removed) }, index_{ removed_index }, created_{ false } + tx_panel_{ tx_panel }, + tex_removed_{ std::move(tex_removed) }, + index_{ removed_index }, + created_{ false } { } @@ -612,8 +621,13 @@ class TextureModificationUS : public UndoStep // TextureXPanel class constructor // ----------------------------------------------------------------------------- TextureXPanel::TextureXPanel(wxWindow* parent, TextureXEditor& tx_editor) : - wxPanel{ parent, -1 }, tx_editor_{ &tx_editor }, undo_manager_{ tx_editor.undoManager() } + wxPanel{ parent, -1 }, + texturex_{ new TextureXList() }, + tx_editor_{ &tx_editor }, + undo_manager_{ tx_editor.undoManager() } { + namespace wx = wxutil; + // Setup sizer auto sizer = new wxBoxSizer(wxHORIZONTAL); SetSizer(sizer); @@ -621,7 +635,7 @@ TextureXPanel::TextureXPanel(wxWindow* parent, TextureXEditor& tx_editor) : // Frame frame_textures_ = new wxStaticBox(this, -1, "Textures"); auto framesizer = new wxStaticBoxSizer(frame_textures_, wxHORIZONTAL); - sizer->Add(framesizer, 0, wxEXPAND | wxLEFT | wxTOP | wxBOTTOM, ui::pad()); + sizer->Add(framesizer, wx::sfWithBorder(0, wxLEFT | wxTOP | wxBOTTOM).Expand()); // Toolbar toolbar_ = new SToolBar(this, false, wxVERTICAL); @@ -632,20 +646,19 @@ TextureXPanel::TextureXPanel(wxWindow* parent, TextureXEditor& tx_editor) : toolbar_->group("_Texture")->setAllButtonsEnabled(false); toolbar_->group("_Sorting")->setAllButtonsEnabled(false); toolbar_->findActionButton("txed_sort")->Enable(); - framesizer->Add(toolbar_, 0, wxEXPAND | wxTOP | wxBOTTOM, ui::px(ui::Size::PadMinimum)); + framesizer->Add(toolbar_, wx::sfWithMinBorder(0, wxTOP | wxBOTTOM).Expand()); // Textures list + filter - list_textures_ = new TextureXListView(this, &texturex_); + list_textures_ = new TextureXListView(this, texturex_.get()); text_filter_ = new wxTextCtrl(this, -1); btn_clear_filter_ = new SIconButton(this, "close", "Clear Filter"); auto* vbox = new wxBoxSizer(wxVERTICAL); - framesizer->AddSpacer(ui::px(ui::Size::PadMinimum)); - framesizer->Add(vbox, 1, wxEXPAND | wxTOP | wxRIGHT | wxBOTTOM, ui::pad()); - vbox->Add(list_textures_, 1, wxEXPAND | wxBOTTOM, ui::pad()); + framesizer->AddSpacer(ui::padMin()); + framesizer->Add(vbox, wx::sfWithBorder(1, wxTOP | wxRIGHT | wxBOTTOM).Expand()); + vbox->Add(list_textures_, wx::sfWithBorder(1, wxBOTTOM).Expand()); vbox->Add( - wxutil::layoutHorizontally({ wxutil::createLabelHBox(this, "Filter:", text_filter_), btn_clear_filter_ }, 0), - 0, - wxEXPAND); + wx::layoutHorizontally({ wx::createLabelHBox(this, "Filter:", text_filter_), btn_clear_filter_ }, 0), + wxSizerFlags().Expand()); // Bind events list_textures_->Bind(wxEVT_LIST_ITEM_SELECTED, &TextureXPanel::onTextureListSelect, this); @@ -674,16 +687,16 @@ bool TextureXPanel::openTEXTUREX(ArchiveEntry* entry) if (entry->type()->formatId() == "texturex") { // TEXTURE1/2 format - if (!texturex_.readTEXTUREXData(entry, tx_editor_->patchTable())) + if (!texturex_->readTEXTUREXData(entry, tx_editor_->patchTable())) return false; // Create default texture editor texture_editor_ = new TextureEditorPanel(this, tx_editor_); // Update patch table usage info - for (size_t a = 0; a < texturex_.size(); a++) + for (size_t a = 0; a < texturex_->size(); a++) { - auto tex = texturex_.texture(a); + auto tex = texturex_->texture(a); // Go through texture's patches for (size_t p = 0; p < tex->nPatches(); p++) @@ -693,7 +706,7 @@ bool TextureXPanel::openTEXTUREX(ArchiveEntry* entry) else { // TEXTURES format - if (!texturex_.readTEXTURESData(entry)) + if (!texturex_->readTEXTURESData(entry)) return false; // Create extended texture editor @@ -706,11 +719,11 @@ bool TextureXPanel::openTEXTUREX(ArchiveEntry* entry) tx_entry_ = entry; // Add texture editor area - GetSizer()->Add(texture_editor_, 1, wxEXPAND | wxALL, ui::pad()); + GetSizer()->Add(texture_editor_, wxutil::sfWithBorder(1).Expand()); texture_editor_->setupLayout(); // Update format label - frame_textures_->SetLabel("Textures (" + texturex_.textureXFormatString() + " format)"); + frame_textures_->SetLabel("Textures (" + texturex_->textureXFormatString() + " format)"); // Update texture list list_textures_->updateList(); @@ -731,18 +744,18 @@ bool TextureXPanel::saveTEXTUREX() // Write list to entry, in the correct format tx_entry_->unlock(); // Have to unlock the entry first bool ok = false; - if (TxListIsTextures(texturex_)) - ok = texturex_.writeTEXTURESData(tx_entry_); + if (txListIsTextures(*texturex_)) + ok = texturex_->writeTEXTURESData(tx_entry_); else - ok = texturex_.writeTEXTUREXData(tx_entry_, tx_editor_->patchTable()); + ok = texturex_->writeTEXTUREXData(tx_entry_, tx_editor_->patchTable()); // Redetect type and lock it up EntryType::detectEntryType(*tx_entry_); tx_entry_->lock(); // Set all textures to unmodified - for (unsigned a = 0; a < texturex_.size(); a++) - texturex_.texture(a)->setState(0); + for (unsigned a = 0; a < texturex_->size(); a++) + texturex_->texture(a)->setState(0); list_textures_->updateList(); // Update variables @@ -754,7 +767,7 @@ bool TextureXPanel::saveTEXTUREX() // ----------------------------------------------------------------------------- // Sets the texture editor's palette // ----------------------------------------------------------------------------- -void TextureXPanel::setPalette(Palette* pal) const +void TextureXPanel::setPalette(const Palette* pal) const { texture_editor_->setPalette(pal); } @@ -782,7 +795,7 @@ void TextureXPanel::applyChanges() tx_editor_->patchTable().updatePatchUsage(tex_current_); list_textures_->updateList(); modified_ = true; - texture_editor_->openTexture(tex_current_, &texturex_); + texture_editor_->openTexture(tex_current_, texturex_.get()); } } @@ -798,7 +811,7 @@ unique_ptr TextureXPanel::newTextureFromPatch(const wxString& name, co tex->setState(2); // Setup texture scale - if (TxListIsTextures(texturex_)) + if (txListIsTextures(*texturex_)) { tex->setScale({ 1., 1. }); tex->setExtended(true); @@ -830,13 +843,13 @@ unique_ptr TextureXPanel::newTextureFromPatch(const wxString& name, co // ----------------------------------------------------------------------------- void TextureXPanel::newTexture() { - auto* dialog = new NewTextureDialog(maineditor::windowWx(), tx_editor_, &texturex_); + auto* dialog = new NewTextureDialog(maineditor::windowWx(), tx_editor_, texturex_.get()); if (dialog->ShowModal() != wxID_OK) return; // Process name auto name = dialog->texName(); - if (!TxListIsTextures(texturex_)) + if (!txListIsTextures(*texturex_)) name = name.Upper().Truncate(8); // Create new texture @@ -853,7 +866,7 @@ void TextureXPanel::newTexture() tex->setHeight(dialog->texHeight()); // Setup texture scale - if (TxListIsTextures(texturex_)) + if (txListIsTextures(*texturex_)) { tex->setScale({ 1., 1. }); tex->setExtended(true); @@ -868,8 +881,8 @@ void TextureXPanel::newTexture() auto* tex_ptr = tex.get(); int selected = list_textures_->itemIndex(list_textures_->lastSelected()); if (selected == -1) - selected = texturex_.size() - 1; // Add to end of the list if nothing selected - texturex_.addTexture(std::move(tex), selected + 1); + selected = texturex_->size() - 1; // Add to end of the list if nothing selected + texturex_->addTexture(std::move(tex), selected + 1); // Record undo level undo_manager_->beginRecord("New Texture"); @@ -899,7 +912,7 @@ void TextureXPanel::newTextureFromPatch() { // Browse for patch wxString patch; - if (TxListIsTextures(texturex_)) + if (txListIsTextures(*texturex_)) patch = tx_editor_->browsePatchEntry(); else patch = tx_editor_->patchTable().patchName(tx_editor_->browsePatchTable()); @@ -923,8 +936,8 @@ void TextureXPanel::newTextureFromPatch() // Add texture after the last selected item int selected = list_textures_->itemIndex(list_textures_->lastSelected()); if (selected == -1) - selected = texturex_.size() - 1; // Add to end of the list if nothing selected - texturex_.addTexture(std::move(tex), selected + 1); + selected = texturex_->size() - 1; // Add to end of the list if nothing selected + texturex_->addTexture(std::move(tex), selected + 1); // Record undo level undo_manager_->beginRecord("New Texture from Patch"); @@ -1015,7 +1028,7 @@ void TextureXPanel::newTextureFromFile() tx_entry_->parent()->addEntry(entry, "patches"); // Add patch to patch table if needed - if (!TxListIsTextures(texturex_)) + if (!txListIsTextures(*texturex_)) tx_editor_->patchTable().addPatch(wxutil::strToView(name)); @@ -1026,8 +1039,8 @@ void TextureXPanel::newTextureFromFile() // Add texture after the last selected item int selected = list_textures_->itemIndex(list_textures_->lastSelected()); if (selected == -1) - selected = texturex_.size() - 1; // Add to end of the list if nothing selected - texturex_.addTexture(std::move(tex), selected + 1); + selected = texturex_->size() - 1; // Add to end of the list if nothing selected + texturex_->addTexture(std::move(tex), selected + 1); // Record undo level undo_manager_->beginRecord("New Texture from File"); @@ -1063,12 +1076,12 @@ void TextureXPanel::removeTexture() for (int a = selection.size() - 1; a >= 0; a--) { // Remove texture from patch table entries - auto tex = texturex_.texture(selection[a]); + auto tex = texturex_->texture(selection[a]); for (unsigned p = 0; p < tex->nPatches(); p++) tx_editor_->patchTable().patch(tex->patch(p)->name()).removeTextureUsage(tex->name()); // Remove texture from list - auto removed = texturex_.removeTexture(selection[a]); + auto removed = texturex_->removeTexture(selection[a]); // Record undo step undo_manager_->recordUndoStep(std::make_unique(this, std::move(removed), selection[a])); @@ -1105,10 +1118,10 @@ void TextureXPanel::moveUp() for (long index : selection) { // Swap selected texture with the one above it - texturex_.swapTextures(index, index - 1); + texturex_->swapTextures(index, index - 1); // Record undo step - undo_manager_->recordUndoStep(std::make_unique(texturex_, index, index - 1)); + undo_manager_->recordUndoStep(std::make_unique(*texturex_, index, index - 1)); } // End recording undo level @@ -1145,10 +1158,10 @@ void TextureXPanel::moveDown() for (int a = selection.size() - 1; a >= 0; a--) { // Swap selected texture with the one below it - texturex_.swapTextures(selection[a], selection[a] + 1); + texturex_->swapTextures(selection[a], selection[a] + 1); // Record undo step - undo_manager_->recordUndoStep(std::make_unique(texturex_, selection[a], selection[a] + 1)); + undo_manager_->recordUndoStep(std::make_unique(*texturex_, selection[a], selection[a] + 1)); } // End recording undo level @@ -1178,8 +1191,8 @@ void TextureXPanel::sort() if (selection.size() < 2) { selection.clear(); - selection.resize(texturex_.size()); - for (size_t i = 0; i < texturex_.size(); ++i) + selection.resize(texturex_->size()); + for (size_t i = 0; i < texturex_->size(); ++i) selection[i] = i; } @@ -1188,13 +1201,13 @@ void TextureXPanel::sort() return; // Fill a map with pairs - vector origindex(texturex_.size()); + vector origindex(texturex_->size()); std::map tmap; tmap.clear(); for (long index : selection) { // We want to be sure that each key is unique, so we add the position to the name string - wxString name = wxString::Format("%-8s%8d", texturex_.texture(index)->name(), index); + wxString name = wxString::Format("%-8s%8d", texturex_->texture(index)->name(), index); // x keeps the current position, while y keeps the original position tmap[name] = index; origindex[index] = index; @@ -1214,10 +1227,10 @@ void TextureXPanel::sort() size_t tmp = origindex[index]; origindex[index] = origindex[itr->second]; origindex[itr->second] = tmp; - texturex_.swapTextures(index, itr->second); - undo_manager_->recordUndoStep(std::make_unique(texturex_, index, itr->second)); + texturex_->swapTextures(index, itr->second); + undo_manager_->recordUndoStep(std::make_unique(*texturex_, index, itr->second)); // Update the position of the displaced texture in the tmap - wxString name = wxString::Format("%-8s%8d", texturex_.texture(itr->second)->name(), tmp); + wxString name = wxString::Format("%-8s%8d", texturex_->texture(itr->second)->name(), tmp); tmap[name] = itr->second; } ++itr; @@ -1236,7 +1249,7 @@ void TextureXPanel::sort() // ----------------------------------------------------------------------------- // Copies any selected textures to the clipboard // ----------------------------------------------------------------------------- -void TextureXPanel::copy() +void TextureXPanel::copy() const { // Get selected textures auto selection = list_textures_->selection(true); @@ -1247,8 +1260,9 @@ void TextureXPanel::copy() // Create list of textures to copy vector> copy_items; + copy_items.reserve(selection.size()); for (long index : selection) - copy_items.emplace_back(new TextureClipboardItem(*texturex_.texture(index), tx_editor_->archive())); + copy_items.emplace_back(new TextureClipboardItem(*texturex_->texture(index), tx_editor_->archive())); // Add list to clipboard app::clipboard().clear(); @@ -1267,7 +1281,7 @@ void TextureXPanel::paste() // Get last selected index int selected = list_textures_->itemIndex(list_textures_->lastSelected()); if (selected == -1) - selected = texturex_.size() - 1; // Add to end of the list if nothing selected + selected = texturex_->size() - 1; // Add to end of the list if nothing selected // Begin recording undo level undo_manager_->beginRecord("Paste Texture(s)"); @@ -1283,11 +1297,11 @@ void TextureXPanel::paste() auto item = dynamic_cast(app::clipboard().item(a)); // Add new texture after last selected item - auto ntex = std::make_unique(TxListIsTextures(texturex_)); + auto ntex = std::make_unique(txListIsTextures(*texturex_)); auto ntex_ptr = ntex.get(); ntex->copyTexture(item->texture(), true); ntex->setState(2); - texturex_.addTexture(std::move(ntex), ++selected); + texturex_->addTexture(std::move(ntex), ++selected); // Record undo step undo_manager_->recordUndoStep(std::make_unique(this, selected)); @@ -1298,7 +1312,7 @@ void TextureXPanel::paste() auto patch = ntex_ptr->patch(p); // Update patch table if necessary - if (!TxListIsTextures(texturex_)) + if (!txListIsTextures(*texturex_)) tx_editor_->patchTable().addPatch(patch->name()); // Get the entry for this patch @@ -1350,8 +1364,9 @@ void TextureXPanel::renameTexture(bool each) return; // Go through selection + selection.reserve(selec_num.size()); for (long index : selec_num) - selection.push_back(texturex_.texture(index)); + selection.push_back(texturex_->texture(index)); // Define alphabet static const string alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"; @@ -1384,6 +1399,7 @@ void TextureXPanel::renameTexture(bool each) { // Get a list of entry names vector names; + names.reserve(selection.size()); for (auto& texture : selection) names.push_back(texture->name()); @@ -1451,8 +1467,9 @@ void TextureXPanel::exportTexture() bool force_rgba = texture_editor_->blendRGBA(); // Go through selection + selection.reserve(selec_num.size()); for (long index : selec_num) - selection.push_back(texturex_.texture(index)); + selection.push_back(texturex_->texture(index)); // Create gfx conversion dialog GfxConvDialog gcd(this); @@ -1539,12 +1556,12 @@ void TextureXPanel::extractTexture() if (!tx_entry_) return; - auto archive = tx_entry_->parent(); bool force_rgba = texture_editor_->blendRGBA(); // Go through selection + selection.reserve(selec_num.size()); for (long index : selec_num) - selection.push_back(texturex_.texture(index)); + selection.push_back(texturex_->texture(index)); // If we're just exporting one texture @@ -1630,7 +1647,7 @@ bool TextureXPanel::modifyOffsets() { // Get texture bool current = false; - auto ctex = texturex_.texture(index); + auto ctex = texturex_->texture(index); if (ctex == tex_current_) { // Texture is currently open in the editor @@ -1767,19 +1784,19 @@ void TextureXPanel::onTextureListSelect(wxListEvent& e) { tex_current_ = nullptr; undo_manager_->setResetPoint(); - texture_editor_->openTexture(tex_current_, &texturex_); + texture_editor_->openTexture(tex_current_, texturex_.get()); return; } // Get selected texture - auto tex = texturex_.texture(list_textures_->itemIndex(e.GetIndex())); + auto tex = texturex_->texture(list_textures_->itemIndex(e.GetIndex())); // Save any changes to previous texture applyChanges(); // Open texture in editor undo_manager_->setResetPoint(); - texture_editor_->openTexture(tex, &texturex_); + texture_editor_->openTexture(tex, texturex_.get()); // Set current texture tex_current_ = tex; @@ -1798,7 +1815,7 @@ void TextureXPanel::onTextureListRightClick(wxListEvent& e) SAction::fromId("txed_rename")->addToMenu(&context, true); if (list_textures_->GetSelectedItemCount() > 1) SAction::fromId("txed_rename_each")->addToMenu(&context, true); - if (TxListIsTextures(texturex_)) + if (txListIsTextures(*texturex_)) SAction::fromId("txed_offsets")->addToMenu(&context, true); SAction::fromId("txed_export")->addToMenu(texport, true, "Archive (as image)"); SAction::fromId("txed_extract")->addToMenu(texport, true, "File"); diff --git a/src/MainEditor/UI/TextureXEditor/TextureXPanel.h b/src/MainEditor/UI/TextureXEditor/TextureXPanel.h index 4b3b3c8be..dab467190 100644 --- a/src/MainEditor/UI/TextureXEditor/TextureXPanel.h +++ b/src/MainEditor/UI/TextureXEditor/TextureXPanel.h @@ -1,11 +1,14 @@ #pragma once #include "General/SAction.h" -#include "Graphics/CTexture/TextureXList.h" #include "UI/Lists/VirtualListView.h" namespace slade { +class Palette; +class CTexture; +class ArchiveEntry; +class TextureXList; class TextureXEditor; class TextureEditorPanel; class UndoManager; @@ -15,7 +18,7 @@ class TextureXListView : public VirtualListView { public: TextureXListView(wxWindow* parent, TextureXList* texturex); - ~TextureXListView() = default; + ~TextureXListView() override = default; TextureXList* txList() const { return texturex_; } @@ -41,9 +44,9 @@ class TextureXPanel : public wxPanel, SActionHandler { public: TextureXPanel(wxWindow* parent, TextureXEditor& tx_editor); - ~TextureXPanel(); + ~TextureXPanel() override; - TextureXList& txList() { return texturex_; } + TextureXList& txList() const { return *texturex_; } ArchiveEntry* txEntry() const { return tx_entry_; } bool isModified() const { return modified_; } CTexture* currentTexture() const { return tex_current_; } @@ -51,7 +54,7 @@ class TextureXPanel : public wxPanel, SActionHandler bool openTEXTUREX(ArchiveEntry* entry); bool saveTEXTUREX(); - void setPalette(Palette* pal) const; + void setPalette(const Palette* pal) const; void applyChanges(); void updateTextureList() const { list_textures_->updateList(); } @@ -69,7 +72,7 @@ class TextureXPanel : public wxPanel, SActionHandler void moveUp(); void moveDown(); void sort(); - void copy(); + void copy() const; void paste(); // Undo/Redo @@ -80,12 +83,12 @@ class TextureXPanel : public wxPanel, SActionHandler bool handleAction(string_view id) override; private: - TextureXList texturex_; - TextureXEditor* tx_editor_ = nullptr; - ArchiveEntry* tx_entry_ = nullptr; - CTexture* tex_current_ = nullptr; - bool modified_ = false; - UndoManager* undo_manager_ = nullptr; + unique_ptr texturex_; + TextureXEditor* tx_editor_ = nullptr; + ArchiveEntry* tx_entry_ = nullptr; + CTexture* tex_current_ = nullptr; + bool modified_ = false; + UndoManager* undo_manager_ = nullptr; // Controls TextureXListView* list_textures_ = nullptr; diff --git a/src/MainEditor/UI/TextureXEditor/ZTextureEditorPanel.cpp b/src/MainEditor/UI/TextureXEditor/ZTextureEditorPanel.cpp index 5be714877..353f57577 100644 --- a/src/MainEditor/UI/TextureXEditor/ZTextureEditorPanel.cpp +++ b/src/MainEditor/UI/TextureXEditor/ZTextureEditorPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -32,11 +32,15 @@ // ----------------------------------------------------------------------------- #include "Main.h" #include "ZTextureEditorPanel.h" +#include "General/UI.h" +#include "Graphics/CTexture/CTexture.h" #include "Graphics/SImage/SImage.h" #include "MainEditor/MainEditor.h" #include "TextureXEditor.h" #include "UI/Canvas/CTextureCanvas.h" +#include "UI/Controls/ColourBox.h" #include "UI/Dialogs/TranslationEditorDialog.h" +#include "UI/Lists/ListView.h" #include "UI/SToolBar/SToolBar.h" #include "UI/SToolBar/SToolBarButton.h" #include "UI/WxUtils.h" @@ -83,10 +87,10 @@ wxPanel* ZTextureEditorPanel::createTextureControls(wxWindow* parent) // "Texture Properties" frame auto frame = new wxStaticBox(panel, -1, "Texture Properties"); auto framesizer = new wxStaticBoxSizer(frame, wxVERTICAL); - sizer->Add(framesizer, 0, wxEXPAND); + sizer->Add(framesizer, wxSizerFlags().Expand()); auto gb_sizer = new wxGridBagSizer(ui::pad(), ui::pad()); - framesizer->Add(gb_sizer, 1, wxEXPAND | wxALL, ui::pad()); + framesizer->Add(gb_sizer, wxutil::sfWithBorder(1).Expand()); // Name text_tex_name_ = new wxTextCtrl(panel, -1); @@ -212,6 +216,8 @@ void ZTextureEditorPanel::updateTextureControls() // ----------------------------------------------------------------------------- wxPanel* ZTextureEditorPanel::createPatchControls(wxWindow* parent) { + namespace wx = wxutil; + auto panel = new wxScrolledWindow(parent, -1); panel->SetScrollRate(0, 4); @@ -222,7 +228,7 @@ wxPanel* ZTextureEditorPanel::createPatchControls(wxWindow* parent) // -- Texture Patches frame -- auto frame = new wxStaticBox(panel, -1, "Patches"); auto framesizer = new wxStaticBoxSizer(frame, wxHORIZONTAL); - sizer->Add(framesizer, 0, wxEXPAND); + sizer->Add(framesizer, wxSizerFlags().Expand()); // Create patches list list_patches_ = new ListView(panel, -1); @@ -243,17 +249,17 @@ wxPanel* ZTextureEditorPanel::createPatchControls(wxWindow* parent) // Layout list_patches_->SetInitialSize(wxutil::scaledSize(100, tb_patches_->group("_Patch")->GetBestSize().y)); - framesizer->Add(list_patches_, 1, wxEXPAND | wxLEFT | wxTOP | wxBOTTOM, ui::pad()); - framesizer->Add(tb_patches_, 0, wxEXPAND | wxLEFT | wxTOP | wxBOTTOM, ui::px(ui::Size::PadMinimum)); + framesizer->Add(list_patches_, wx::sfWithBorder(1, wxLEFT | wxTOP | wxBOTTOM).Expand()); + framesizer->Add(tb_patches_, wx::sfWithMinBorder(0, wxLEFT | wxTOP | wxBOTTOM).Expand()); // -- Patch Properties frame -- frame = new wxStaticBox(panel, -1, "Patch Properties"); framesizer = new wxStaticBoxSizer(frame, wxVERTICAL); - sizer->Add(framesizer, 0, wxEXPAND | wxTOP, ui::pad()); + sizer->Add(framesizer, wx::sfWithBorder(0, wxTOP).Expand()); auto* gb_sizer = new wxGridBagSizer(ui::pad(), ui::pad()); - framesizer->Add(gb_sizer, 1, wxEXPAND | wxALL, ui::pad()); + framesizer->Add(gb_sizer, wx::sfWithBorder(1).Expand()); // X Position const auto spinsize = wxSize{ ui::px(ui::Size::SpinCtrlWidth), -1 }; @@ -301,10 +307,10 @@ wxPanel* ZTextureEditorPanel::createPatchControls(wxWindow* parent) frame = new wxStaticBox(panel, -1, "Patch Colour"); framesizer = new wxStaticBoxSizer(frame, wxVERTICAL); - sizer->Add(framesizer, 0, wxEXPAND | wxTOP, ui::pad()); + sizer->Add(framesizer, wx::sfWithBorder(0, wxTOP).Expand()); gb_sizer = new wxGridBagSizer(ui::pad(), ui::pad()); - framesizer->Add(gb_sizer, 1, wxEXPAND | wxALL, ui::pad()); + framesizer->Add(gb_sizer, wx::sfWithBorder(1).Expand()); // 'Normal' colour rb_pc_normal_ = new wxRadioButton(panel, -1, "Normal", wxDefaultPosition, wxDefaultSize, wxRB_GROUP); @@ -340,7 +346,7 @@ wxPanel* ZTextureEditorPanel::createPatchControls(wxWindow* parent) // Translation text entry text_translation_ = new wxTextCtrl(panel, -1, "", wxDefaultPosition, wxDefaultSize, wxTE_PROCESS_ENTER); - hbox->Add(text_translation_, 1, wxEXPAND | wxRIGHT, ui::pad()); + hbox->Add(text_translation_, wx::sfWithBorder(1, wxRIGHT).Expand()); // Translation edit button btn_edit_translation_ = new wxButton(panel, -1, "Edit", wxDefaultPosition, wxDefaultSize, wxBU_EXACTFIT); @@ -435,16 +441,16 @@ void ZTextureEditorPanel::updatePatchControls() spin_alpha_->SetValue(patch->alpha()); choice_style_->SetStringSelection(patch->style()); cb_blend_col_->setColour(patch->colour()); - spin_tint_amount_->SetValue((double)patch->colour().a / 255.0); + spin_tint_amount_->SetValue(static_cast(patch->colour().a) / 255.0); text_translation_->SetValue(patch->translation().asText()); switch (patch->rotation()) { - case 0: choice_rotation_->SetSelection(0); break; - case 90: choice_rotation_->SetSelection(1); break; + case 0: choice_rotation_->SetSelection(0); break; + case 90: choice_rotation_->SetSelection(1); break; case 180: choice_rotation_->SetSelection(2); break; case -90: choice_rotation_->SetSelection(3); break; - default: choice_rotation_->SetSelection(-1); break; + default: choice_rotation_->SetSelection(-1); break; } // Update patch colour controls @@ -568,6 +574,8 @@ void ZTextureEditorPanel::enableBlendControls(bool enable, bool tint) const // // ----------------------------------------------------------------------------- +// ReSharper disable CppMemberFunctionMayBeConst +// ReSharper disable CppParameterMayBeConstPtrOrRef // ----------------------------------------------------------------------------- // Called when the 'Truecolour Preview' checkbox is (un)checked @@ -795,9 +803,9 @@ void ZTextureEditorPanel::onPatchRotationChanged(wxCommandEvent& e) int rot = 0; switch (choice_rotation_->GetSelection()) { - case 1: rot = 90; break; - case 2: rot = 180; break; - case 3: rot = -90; break; + case 1: rot = 90; break; + case 2: rot = 180; break; + case 3: rot = -90; break; default: rot = 0; break; } diff --git a/src/MainEditor/UI/TextureXEditor/ZTextureEditorPanel.h b/src/MainEditor/UI/TextureXEditor/ZTextureEditorPanel.h index 421a82bd9..a5f7a1688 100644 --- a/src/MainEditor/UI/TextureXEditor/ZTextureEditorPanel.h +++ b/src/MainEditor/UI/TextureXEditor/ZTextureEditorPanel.h @@ -1,12 +1,13 @@ #pragma once #include "TextureEditorPanel.h" -#include "UI/Controls/ColourBox.h" class wxSpinCtrlDouble; namespace slade { +class ColourBox; + class ZTextureEditorPanel : public TextureEditorPanel { public: diff --git a/src/MapEditor/Edit/Edit2D.cpp b/src/MapEditor/Edit/Edit2D.cpp index 816d4f3ae..014425918 100644 --- a/src/MapEditor/Edit/Edit2D.cpp +++ b/src/MapEditor/Edit/Edit2D.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -34,12 +34,24 @@ #include "App.h" #include "Game/Configuration.h" #include "General/Clipboard.h" +#include "MapEditor/MapClipboardItems.h" #include "MapEditor/MapEditContext.h" +#include "MapEditor/MapEditor.h" +#include "MapEditor/Renderer/MapRenderer2D.h" +#include "MapEditor/Renderer/Renderer.h" #include "MapEditor/SectorBuilder.h" #include "MapEditor/UndoSteps.h" +#include "SLADEMap/MapObject/MapLine.h" +#include "SLADEMap/MapObject/MapSector.h" +#include "SLADEMap/MapObject/MapSide.h" +#include "SLADEMap/MapObject/MapThing.h" +#include "SLADEMap/MapObject/MapVertex.h" +#include "SLADEMap/MapObjectList/LineList.h" +#include "SLADEMap/SLADEMap.h" #include "Utility/MathStuff.h" using namespace slade; +using namespace mapeditor; // ----------------------------------------------------------------------------- @@ -61,10 +73,13 @@ CVAR(Bool, map_remove_invalid_lines, false, CVar::Flag::Save) // ----------------------------------------------------------------------------- // Edit2D class constructor // ----------------------------------------------------------------------------- -Edit2D::Edit2D(MapEditContext& context) : - context_{ context }, - copy_line_{ nullptr, nullptr, ©_side_front_, ©_side_back_ } +Edit2D::Edit2D(MapEditContext& context) : context_{ &context } { + copy_side_front_ = std::make_unique(); + copy_side_back_ = std::make_unique(); + copy_line_ = std::make_unique(nullptr, nullptr, copy_side_front_.get(), copy_side_back_.get()); + copy_sector_ = std::make_unique(); + copy_thing_ = std::make_unique(); } // ----------------------------------------------------------------------------- @@ -72,16 +87,14 @@ Edit2D::Edit2D(MapEditContext& context) : // ----------------------------------------------------------------------------- void Edit2D::mirror(bool x_axis) const { - using mapeditor::Mode; - // Mirror things - if (context_.editMode() == Mode::Things) + if (context_->editMode() == Mode::Things) { // Begin undo level - context_.beginUndoRecord("Mirror Things", true, false, false); + context_->beginUndoRecord("Mirror Things", true, false, false); // Get things to mirror - auto things = context_.selection().selectedThings(); + auto things = context_->selection().selectedThings(); // Get midpoint BBox bbox; @@ -111,23 +124,23 @@ void Edit2D::mirror(bool x_axis) const angle += 360; thing->setAngle(angle); } - context_.endUndoRecord(true); + context_->endUndoRecord(true); } // Mirror map architecture - else if (context_.editMode() != Mode::Visual) + else if (context_->editMode() != Mode::Visual) { // Begin undo level - context_.beginUndoRecord("Mirror Map Architecture", true, false, false); + context_->beginUndoRecord("Mirror Map Architecture", true, false, false); // Get vertices to mirror vector vertices; vector lines; - if (context_.editMode() == Mode::Vertices) - vertices = context_.selection().selectedVertices(); - else if (context_.editMode() == Mode::Lines) + if (context_->editMode() == Mode::Vertices) + vertices = context_->selection().selectedVertices(); + else if (context_->editMode() == Mode::Lines) { - auto sel = context_.selection().selectedLines(); + auto sel = context_->selection().selectedLines(); for (auto line : sel) { VECTOR_ADD_UNIQUE(vertices, line->v1()); @@ -135,9 +148,9 @@ void Edit2D::mirror(bool x_axis) const lines.push_back(line); } } - else if (context_.editMode() == Mode::Sectors) + else if (context_->editMode() == Mode::Sectors) { - auto sectors = context_.selection().selectedSectors(); + auto sectors = context_->selection().selectedSectors(); for (auto sector : sectors) { sector->putVertices(vertices); @@ -164,7 +177,7 @@ void Edit2D::mirror(bool x_axis) const for (auto& line : lines) line->flip(false); - context_.endUndoRecord(true); + context_->endUndoRecord(true); } } @@ -174,30 +187,30 @@ void Edit2D::mirror(bool x_axis) const // ----------------------------------------------------------------------------- void Edit2D::editObjectProperties() { - auto selection = context_.selection().selectedObjects(); + auto selection = context_->selection().selectedObjects(); if (selection.empty()) return; // Begin recording undo level - context_.beginUndoRecord(fmt::format("Property Edit ({})", context_.modeString(false))); + context_->beginUndoRecord(fmt::format("Property Edit ({})", context_->modeString(false))); for (auto item : selection) - context_.recordPropertyChangeUndoStep(item); + context_->recordPropertyChangeUndoStep(item); bool done = mapeditor::editObjectProperties(selection); if (done) { - context_.renderer().forceUpdate(); - context_.updateDisplay(); + context_->renderer().forceUpdate(); + context_->updateDisplay(); - if (context_.editMode() == mapeditor::Mode::Things && selection[0]->objType() == MapObject::Type::Thing) + if (context_->editMode() == Mode::Things && selection[0]->objType() == MapObject::Type::Thing) { - copy_thing_.copy(selection[0]); + copy_thing_->copy(selection[0]); thing_copied_ = true; } } // End undo level - context_.endUndoRecord(done); + context_->endUndoRecord(done); } // ----------------------------------------------------------------------------- @@ -208,26 +221,26 @@ void Edit2D::splitLine(double x, double y, double min_dist) const Vec2d point(x, y); // Get the closest line - auto line = context_.map().lines().nearest(point, min_dist); + auto line = context_->map().lines().nearest(point, min_dist); // Do nothing if no line is close enough if (!line) return; // Begin recording undo level - context_.beginUndoRecord("Split Line", true, true, false); + context_->beginUndoRecord("Split Line", true, true, false); // Get closest point on the line auto closest = math::closestPointOnLine(point, line->seg()); // Create vertex there - auto vertex = context_.map().createVertex(closest); + auto vertex = context_->map().createVertex(closest); // Do line split - context_.map().splitLine(line, vertex); + context_->map().splitLine(line, vertex); // Finish recording undo level - context_.endUndoRecord(); + context_->endUndoRecord(); } // ----------------------------------------------------------------------------- @@ -236,21 +249,21 @@ void Edit2D::splitLine(double x, double y, double min_dist) const void Edit2D::flipLines(bool sides) const { // Get selected/hilighted line(s) - auto lines = context_.selection().selectedLines(); + auto lines = context_->selection().selectedLines(); if (lines.empty()) return; // Go through list - context_.undoManager()->beginRecord("Flip Line"); + context_->undoManager()->beginRecord("Flip Line"); for (auto& line : lines) { - context_.undoManager()->recordUndoStep(std::make_unique(line)); + context_->undoManager()->recordUndoStep(std::make_unique(line)); line->flip(sides); } - context_.undoManager()->endRecord(true); + context_->undoManager()->endRecord(true); // Update display - context_.updateDisplay(); + context_->updateDisplay(); } // ----------------------------------------------------------------------------- @@ -259,26 +272,26 @@ void Edit2D::flipLines(bool sides) const void Edit2D::correctLineSectors() const { // Get selected/hilighted line(s) - auto lines = context_.selection().selectedLines(); + auto lines = context_->selection().selectedLines(); if (lines.empty()) return; - context_.beginUndoRecord("Correct Line Sectors"); + context_->beginUndoRecord("Correct Line Sectors"); bool changed = false; for (auto& line : lines) { - if (context_.map().correctLineSectors(line)) + if (context_->map().correctLineSectors(line)) changed = true; } - context_.endUndoRecord(changed); + context_->endUndoRecord(changed); // Update display if (changed) { - context_.addEditorMessage("Corrected Sector references"); - context_.updateDisplay(); + context_->addEditorMessage("Corrected Sector references"); + context_->updateDisplay(); } } @@ -288,25 +301,25 @@ void Edit2D::correctLineSectors() const void Edit2D::changeSectorHeight(int amount, bool floor, bool ceiling) const { // Do nothing if not in sectors mode - if (context_.editMode() != mapeditor::Mode::Sectors) + if (context_->editMode() != Mode::Sectors) return; // Get selected sectors (if any) - auto selection = context_.selection().selectedSectors(); + auto selection = context_->selection().selectedSectors(); if (selection.empty()) return; // If we're modifying both heights, take sector_mode into account if (floor && ceiling) { - if (context_.sectorEditMode() == mapeditor::SectorMode::Floor) + if (context_->sectorEditMode() == SectorMode::Floor) ceiling = false; - if (context_.sectorEditMode() == mapeditor::SectorMode::Ceiling) + if (context_->sectorEditMode() == SectorMode::Ceiling) floor = false; } // Begin record undo level - context_.beginUndoRecordLocked("Change Sector Height", true, false, false); + context_->beginUndoRecordLocked("Change Sector Height", true, false, false); // Go through selection for (auto& sector : selection) @@ -321,7 +334,7 @@ void Edit2D::changeSectorHeight(int amount, bool floor, bool ceiling) const } // End record undo level - context_.endUndoRecord(); + context_->endUndoRecord(); // Add editor message string what; @@ -337,10 +350,10 @@ void Edit2D::changeSectorHeight(int amount, bool floor, bool ceiling) const inc = "decreased"; amount = -amount; } - context_.addEditorMessage(fmt::format("{} height {} by {}", what, inc, amount)); + context_->addEditorMessage(fmt::format("{} height {} by {}", what, inc, amount)); // Update display - context_.updateDisplay(); + context_->updateDisplay(); } // ----------------------------------------------------------------------------- @@ -350,16 +363,16 @@ void Edit2D::changeSectorHeight(int amount, bool floor, bool ceiling) const void Edit2D::changeSectorLight(bool up, bool fine) const { // Do nothing if not in sectors mode - if (context_.editMode() != mapeditor::Mode::Sectors) + if (context_->editMode() != Mode::Sectors) return; // Get selected sectors (if any) - auto selection = context_.selection().selectedSectors(); + auto selection = context_->selection().selectedSectors(); if (selection.empty()) return; // Begin record undo level - context_.beginUndoRecordLocked("Change Sector Light", true, false, false); + context_->beginUndoRecordLocked("Change Sector Light", true, false, false); // Go through selection for (auto& sector : selection) @@ -378,14 +391,14 @@ void Edit2D::changeSectorLight(bool up, bool fine) const } // End record undo level - context_.endUndoRecord(); + context_->endUndoRecord(); // Add editor message int amount = fine ? 1 : game::configuration().lightLevelInterval(); - context_.addEditorMessage(fmt::format("Light level {} by {}", up ? "increased" : "decreased", amount)); + context_->addEditorMessage(fmt::format("Light level {} by {}", up ? "increased" : "decreased", amount)); // Update display - context_.updateDisplay(); + context_->updateDisplay(); } // ----------------------------------------------------------------------------- @@ -395,16 +408,14 @@ void Edit2D::changeSectorLight(bool up, bool fine) const // ----------------------------------------------------------------------------- void Edit2D::changeSectorTexture() const { - using mapeditor::SectorMode; - // Get selected sectors - auto selection = context_.selection().selectedSectors(); + auto selection = context_->selection().selectedSectors(); if (selection.empty()) return; // Determine the initial texture string texture, browser_title, undo_name; - auto mode = context_.sectorEditMode(); + auto mode = context_->sectorEditMode(); if (mode == SectorMode::Floor) { texture = selection[0]->floor().texture; @@ -419,20 +430,20 @@ void Edit2D::changeSectorTexture() const } else { - context_.openSectorTextureOverlay(selection); + context_->openSectorTextureOverlay(selection); return; } // Lock hilight - bool hl_lock = context_.selection().hilightLocked(); - context_.selection().lockHilight(); + bool hl_lock = context_->selection().hilightLocked(); + context_->selection().lockHilight(); // Open texture browser - auto selected_tex = mapeditor::browseTexture(texture, mapeditor::TextureType::Flat, context_.map(), browser_title); + auto selected_tex = mapeditor::browseTexture(texture, TextureType::Flat, context_->map(), browser_title); if (!selected_tex.empty()) { // Set texture depending on edit mode - context_.beginUndoRecord(undo_name, true, false, false); + context_->beginUndoRecord(undo_name, true, false, false); for (auto& sector : selection) { if (mode == SectorMode::Floor) @@ -440,12 +451,12 @@ void Edit2D::changeSectorTexture() const else if (mode == SectorMode::Ceiling) sector->setCeilingTexture(selected_tex); } - context_.endUndoRecord(); + context_->endUndoRecord(); } // Unlock hilight if needed - context_.selection().lockHilight(hl_lock); - context_.renderer().renderer2D().clearTextureCache(); + context_->selection().lockHilight(hl_lock); + context_->renderer().renderer2D().clearTextureCache(); } // ----------------------------------------------------------------------------- @@ -455,11 +466,11 @@ void Edit2D::changeSectorTexture() const void Edit2D::joinSectors(bool remove_lines) const { // Check edit mode - if (context_.editMode() != mapeditor::Mode::Sectors) + if (context_->editMode() != Mode::Sectors) return; // Get sectors to merge - auto sectors = context_.selection().selectedSectors(false); + auto sectors = context_->selection().selectedSectors(false); if (sectors.size() < 2) // Need at least 2 sectors to join return; @@ -467,13 +478,13 @@ void Edit2D::joinSectors(bool remove_lines) const auto target = sectors[0]; // Clear selection - context_.selection().clear(); + context_->selection().clear(); // Init list of lines vector lines; // Begin recording undo level - context_.beginUndoRecord("Join/Merge Sectors", true, false, true); + context_->beginUndoRecord("Join/Merge Sectors", true, false, true); // Go through merge sectors for (unsigned a = 1; a < sectors.size(); a++) @@ -501,7 +512,7 @@ void Edit2D::joinSectors(bool remove_lines) const } // Delete sector - context_.map().removeSector(sector); + context_->map().removeSector(sector); } // Remove any changed lines that now have the target sector on both sides (if needed) @@ -515,7 +526,7 @@ void Edit2D::joinSectors(bool remove_lines) const { VECTOR_ADD_UNIQUE(verts, line->v1()); VECTOR_ADD_UNIQUE(verts, line->v2()); - context_.map().removeLine(line); + context_->map().removeLine(line); nlines++; } } @@ -525,66 +536,66 @@ void Edit2D::joinSectors(bool remove_lines) const for (auto& vert : verts) { if (vert->nConnectedLines() == 0) - context_.map().removeVertex(vert); + context_->map().removeVertex(vert); } // Finish recording undo level - context_.endUndoRecord(); + context_->endUndoRecord(); // Editor message if (nlines == 0) - context_.addEditorMessage(fmt::format("Joined {} Sectors", sectors.size())); + context_->addEditorMessage(fmt::format("Joined {} Sectors", sectors.size())); else - context_.addEditorMessage(fmt::format("Joined {} Sectors (removed {} Lines)", sectors.size(), nlines)); + context_->addEditorMessage(fmt::format("Joined {} Sectors (removed {} Lines)", sectors.size(), nlines)); } // ----------------------------------------------------------------------------- // Opens the thing type browser for the currently selected thing(s) // ----------------------------------------------------------------------------- -void Edit2D::changeThingType() +void Edit2D::changeThingType() const { // Get selected things (if any) - auto selection = context_.selection().selectedThings(); + auto selection = context_->selection().selectedThings(); // Do nothing if no selection or hilight if (selection.empty()) return; // Browse thing type - int newtype = mapeditor::browseThingType(selection[0]->type(), context_.map()); + int newtype = mapeditor::browseThingType(selection[0]->type(), context_->map()); if (newtype >= 0) { // Go through selection - context_.beginUndoRecord("Thing Type Change", true, false, false); + context_->beginUndoRecord("Thing Type Change", true, false, false); for (auto& thing : selection) thing->setType(newtype); - context_.endUndoRecord(true); + context_->endUndoRecord(true); // Add editor message auto type_name = game::configuration().thingType(newtype).name(); if (selection.size() == 1) - context_.addEditorMessage(fmt::format("Changed type to \"{}\"", type_name)); + context_->addEditorMessage(fmt::format("Changed type to \"{}\"", type_name)); else - context_.addEditorMessage(fmt::format("Changed {} things to type \"{}\"", selection.size(), type_name)); + context_->addEditorMessage(fmt::format("Changed {} things to type \"{}\"", selection.size(), type_name)); // Update 'copy' thing with new type - copy_thing_.setIntProperty("type", newtype); + copy_thing_->setIntProperty("type", newtype); // Update display - context_.updateDisplay(); + context_->updateDisplay(); } } // ----------------------------------------------------------------------------- // Sets the angle of all selected things to face toward [mouse_pos] // ----------------------------------------------------------------------------- -void Edit2D::thingQuickAngle(Vec2d mouse_pos) const +void Edit2D::thingQuickAngle(const Vec2d& mouse_pos) const { // Do nothing if not in things mode - if (context_.editMode() != mapeditor::Mode::Things) + if (context_->editMode() != Mode::Things) return; - for (auto thing : context_.selection().selectedThings()) + for (auto thing : context_->selection().selectedThings()) thing->setAnglePoint(mouse_pos); } @@ -593,8 +604,7 @@ void Edit2D::thingQuickAngle(Vec2d mouse_pos) const // ----------------------------------------------------------------------------- void Edit2D::copy() const { - using mapeditor::Mode; - auto mode = context_.editMode(); + auto mode = context_->editMode(); // Can't copy/paste vertices (no point) if (mode == Mode::Vertices) @@ -612,10 +622,10 @@ void Edit2D::copy() const // Get selected lines vector lines; if (mode == Mode::Lines) - lines = context_.selection().selectedLines(); + lines = context_->selection().selectedLines(); else if (mode == Mode::Sectors) { - for (auto sector : context_.selection().selectedSectors()) + for (auto sector : context_->selection().selectedSectors()) sector->putLines(lines); } @@ -626,14 +636,14 @@ void Edit2D::copy() const app::clipboard().add(std::move(c)); // Editor message - context_.addEditorMessage(fmt::format("Copied {}", info)); + context_->addEditorMessage(fmt::format("Copied {}", info)); } // Copy things else if (mode == Mode::Things) { // Get selected things - auto things = context_.selection().selectedThings(); + auto things = context_->selection().selectedThings(); // Add to clipboard auto c = std::make_unique(); @@ -642,14 +652,14 @@ void Edit2D::copy() const app::clipboard().add(std::move(c)); // Editor message - context_.addEditorMessage(fmt::format("Copied {}", info)); + context_->addEditorMessage(fmt::format("Copied {}", info)); } } // ----------------------------------------------------------------------------- // Pastes previously copied objects at [mouse_pos] // ----------------------------------------------------------------------------- -void Edit2D::paste(Vec2d mouse_pos) const +void Edit2D::paste(const Vec2d& mouse_pos) const { // Go through clipboard items for (unsigned a = 0; a < app::clipboard().size(); a++) @@ -657,26 +667,26 @@ void Edit2D::paste(Vec2d mouse_pos) const // Map architecture if (app::clipboard().item(a)->type() == ClipboardItem::Type::MapArchitecture) { - context_.beginUndoRecord("Paste Map Architecture"); + context_->beginUndoRecord("Paste Map Architecture"); auto clip = dynamic_cast(app::clipboard().item(a)); // Snap the geometry in such a way that it stays in the same position relative to the grid - auto pos = context_.relativeSnapToGrid(clip->midpoint(), mouse_pos); - auto new_verts = clip->pasteToMap(&context_.map(), pos); - context_.map().mergeArch(new_verts); - context_.addEditorMessage(fmt::format("Pasted {}", clip->info())); - context_.endUndoRecord(true); + auto pos = context_->relativeSnapToGrid(clip->midpoint(), mouse_pos); + auto new_verts = clip->pasteToMap(&context_->map(), pos); + context_->map().mergeArch(new_verts); + context_->addEditorMessage(fmt::format("Pasted {}", clip->info())); + context_->endUndoRecord(true); } // Things else if (app::clipboard().item(a)->type() == ClipboardItem::Type::MapThings) { - context_.beginUndoRecord("Paste Things", false, true, false); + context_->beginUndoRecord("Paste Things", false, true, false); auto clip = dynamic_cast(app::clipboard().item(a)); // Snap the geometry in such a way that it stays in the same position relative to the grid - auto pos = context_.relativeSnapToGrid(clip->midpoint(), mouse_pos); - clip->pasteToMap(&context_.map(), pos); - context_.addEditorMessage(fmt::format("Pasted {}", clip->info())); - context_.endUndoRecord(true); + auto pos = context_->relativeSnapToGrid(clip->midpoint(), mouse_pos); + clip->pasteToMap(&context_->map(), pos); + context_->addEditorMessage(fmt::format("Pasted {}", clip->info())); + context_->endUndoRecord(true); } } } @@ -687,144 +697,142 @@ void Edit2D::paste(Vec2d mouse_pos) const void Edit2D::copyProperties() { // Get MapObject to copy from - auto copy_object = context_.selection().firstSelectedOrHilight().asObject(context_.map()); + auto copy_object = context_->selection().firstSelectedOrHilight().asObject(context_->map()); if (!copy_object) return; // Sectors mode - if (context_.editMode() == mapeditor::Mode::Sectors) + if (context_->editMode() == Mode::Sectors) { - copy_sector_.copy(copy_object); + copy_sector_->copy(copy_object); sector_copied_ = true; - context_.addEditorMessage(fmt::format("Copied sector #{} properties", copy_object->index())); + context_->addEditorMessage(fmt::format("Copied sector #{} properties", copy_object->index())); } // Things mode - else if (context_.editMode() == mapeditor::Mode::Things) + else if (context_->editMode() == Mode::Things) { - copy_thing_.copy(copy_object); + copy_thing_->copy(copy_object); thing_copied_ = true; - context_.addEditorMessage(fmt::format("Copied thing #{} properties", copy_object->index())); + context_->addEditorMessage(fmt::format("Copied thing #{} properties", copy_object->index())); } // Lines mode - else if (context_.editMode() == mapeditor::Mode::Lines) + else if (context_->editMode() == Mode::Lines) { - copy_line_.copy(copy_object); + copy_line_->copy(copy_object); line_copied_ = true; - context_.addEditorMessage(fmt::format("Copied line #{} properties", copy_object->index())); + context_->addEditorMessage(fmt::format("Copied line #{} properties", copy_object->index())); } } // ----------------------------------------------------------------------------- // Pastes previously copied properties to all selected objects // ----------------------------------------------------------------------------- -void Edit2D::pasteProperties() +void Edit2D::pasteProperties() const { // Do nothing if no selection or hilight - if (!context_.selection().hasHilightOrSelection()) + if (!context_->selection().hasHilightOrSelection()) return; // Sectors mode - if (context_.editMode() == mapeditor::Mode::Sectors) + if (context_->editMode() == Mode::Sectors) { // Do nothing if no properties have been copied if (!sector_copied_) return; // Paste properties to selection/hilight - context_.beginUndoRecord("Paste Sector Properties", true, false, false); - for (auto sector : context_.selection().selectedSectors()) - sector->copy(©_sector_); - context_.endUndoRecord(); + context_->beginUndoRecord("Paste Sector Properties", true, false, false); + for (auto sector : context_->selection().selectedSectors()) + sector->copy(copy_sector_.get()); + context_->endUndoRecord(); // Editor message - context_.addEditorMessage("Pasted sector properties"); + context_->addEditorMessage("Pasted sector properties"); } // Things mode - if (context_.editMode() == mapeditor::Mode::Things) + if (context_->editMode() == Mode::Things) { // Do nothing if no properties have been copied if (!thing_copied_) return; // Paste properties to selection/hilight - context_.beginUndoRecord("Paste Thing Properties", true, false, false); - for (auto thing : context_.selection().selectedThings()) + context_->beginUndoRecord("Paste Thing Properties", true, false, false); + for (auto thing : context_->selection().selectedThings()) { // Paste properties (but keep position) double x = thing->xPos(); double y = thing->yPos(); - thing->copy(©_thing_); + thing->copy(copy_thing_.get()); thing->setFloatProperty("x", x); thing->setFloatProperty("y", y); } - context_.endUndoRecord(); + context_->endUndoRecord(); // Editor message - context_.addEditorMessage("Pasted thing properties"); + context_->addEditorMessage("Pasted thing properties"); } // Lines mode - else if (context_.editMode() == mapeditor::Mode::Lines) + else if (context_->editMode() == Mode::Lines) { // Do nothing if no properties have been copied if (!line_copied_) return; // Paste properties to selection/hilight - context_.beginUndoRecord("Paste Line Properties", true, false, false); - for (auto line : context_.selection().selectedLines()) - line->copy(©_line_); - context_.endUndoRecord(); + context_->beginUndoRecord("Paste Line Properties", true, false, false); + for (auto line : context_->selection().selectedLines()) + line->copy(copy_line_.get()); + context_->endUndoRecord(); // Editor message - context_.addEditorMessage("Pasted line properties"); + context_->addEditorMessage("Pasted line properties"); } // Update display - context_.updateDisplay(); + context_->updateDisplay(); } // ----------------------------------------------------------------------------- // Creates an object (depending on edit mode) at [x,y] // ----------------------------------------------------------------------------- -void Edit2D::createObject(Vec2d pos) const +void Edit2D::createObject(const Vec2d& pos) const { - using mapeditor::Mode; - // Vertices mode - if (context_.editMode() == Mode::Vertices) + if (context_->editMode() == Mode::Vertices) { // If there are less than 2 vertices currently selected, just create a vertex at x,y - if (context_.selection().size() < 2) + if (context_->selection().size() < 2) createVertex(pos); else { // Otherwise, create lines between selected vertices - context_.beginUndoRecord("Create Lines", false, true, false); - auto vertices = context_.selection().selectedVertices(false); + context_->beginUndoRecord("Create Lines", false, true, false); + auto vertices = context_->selection().selectedVertices(false); for (unsigned a = 0; a < vertices.size() - 1; a++) - context_.map().createLine(vertices[a], vertices[a + 1]); - context_.endUndoRecord(true); + context_->map().createLine(vertices[a], vertices[a + 1]); + context_->endUndoRecord(true); // Editor message - context_.addEditorMessage(fmt::format("Created {} line(s)", context_.selection().size() - 1)); + context_->addEditorMessage(fmt::format("Created {} line(s)", context_->selection().size() - 1)); // Clear selection - context_.selection().clear(); + context_->selection().clear(); } } // Sectors mode - else if (context_.editMode() == Mode::Sectors) + else if (context_->editMode() == Mode::Sectors) { // Sector - if (context_.map().nLines() > 0) + if (context_->map().nLines() > 0) { createSector(pos); } @@ -832,12 +840,12 @@ void Edit2D::createObject(Vec2d pos) const { // Just create a vertex createVertex(pos); - context_.setEditMode(Mode::Lines); + context_->setEditMode(Mode::Lines); } } // Things mode - else if (context_.editMode() == Mode::Things) + else if (context_->editMode() == Mode::Things) createThing(pos); } @@ -847,17 +855,18 @@ void Edit2D::createObject(Vec2d pos) const void Edit2D::createVertex(Vec2d pos) const { // Snap coordinates to grid if necessary - pos.x = context_.snapToGrid(pos.x, false); - pos.y = context_.snapToGrid(pos.y, false); + pos.x = context_->snapToGrid(pos.x, false); + pos.y = context_->snapToGrid(pos.y, false); // Create vertex - context_.beginUndoRecord("Create Vertex", true, true, false); - auto vertex = context_.map().createVertex(pos, 2); - context_.endUndoRecord(true); + context_->beginUndoRecord("Create Vertex", true, true, false); + auto vertex = context_->map().createVertex(pos, 2); + context_->endUndoRecord(true); // Editor message if (vertex) - context_.addEditorMessage(fmt::format("Created vertex at ({}, {})", (int)vertex->xPos(), (int)vertex->yPos())); + context_->addEditorMessage(fmt::format( + "Created vertex at ({}, {})", static_cast(vertex->xPos()), static_cast(vertex->yPos()))); } // ----------------------------------------------------------------------------- @@ -866,38 +875,39 @@ void Edit2D::createVertex(Vec2d pos) const void Edit2D::createThing(Vec2d pos) const { // Snap coordinates to grid if necessary - pos.x = context_.snapToGrid(pos.x, false); - pos.y = context_.snapToGrid(pos.y, false); + pos.x = context_->snapToGrid(pos.x, false); + pos.y = context_->snapToGrid(pos.y, false); // Begin undo step - context_.beginUndoRecord("Create Thing", false, true, false); + context_->beginUndoRecord("Create Thing", false, true, false); // Create thing - auto thing = context_.map().createThing(pos); + auto thing = context_->map().createThing(pos); // Setup properties - game::configuration().applyDefaults(thing, context_.map().currentFormat() == MapFormat::UDMF); + game::configuration().applyDefaults(thing, context_->map().currentFormat() == MapFormat::UDMF); if (thing_copied_ && thing) { // Copy type and angle from the last copied thing - thing->setType(copy_thing_.type()); - thing->setAngle(copy_thing_.angle()); + thing->setType(copy_thing_->type()); + thing->setAngle(copy_thing_->angle()); } // End undo step - context_.endUndoRecord(true); + context_->endUndoRecord(true); // Editor message if (thing) - context_.addEditorMessage(fmt::format("Created thing at ({}, {})", (int)thing->xPos(), (int)thing->yPos())); + context_->addEditorMessage( + fmt::format("Created thing at ({}, {})", static_cast(thing->xPos()), static_cast(thing->yPos()))); } // ----------------------------------------------------------------------------- // Creates a new sector at [x,y] // ----------------------------------------------------------------------------- -void Edit2D::createSector(Vec2d pos) const +void Edit2D::createSector(const Vec2d& pos) const { - auto& map = context_.map(); + auto& map = context_->map(); // Find nearest line auto line = map.lines().nearest(pos, 99999999); @@ -909,8 +919,8 @@ void Edit2D::createSector(Vec2d pos) const // Get sector to copy if we're in sectors mode MapSector* sector_copy = nullptr; - if (context_.editMode() == mapeditor::Mode::Sectors && !context_.selection().empty()) - sector_copy = context_.selection()[0].asSector(map); + if (context_->editMode() == Mode::Sectors && !context_->selection().empty()) + sector_copy = context_->selection()[0].asSector(map); // Run sector builder SectorBuilder builder; @@ -927,11 +937,11 @@ void Edit2D::createSector(Vec2d pos) const // Create sector from builder result if needed if (ok) { - context_.beginUndoRecord("Create Sector", true, true, false); + context_->beginUndoRecord("Create Sector", true, true, false); builder.createSector(nullptr, sector_copy); // Flash - context_.renderer().animateSelectionChange({ (int)map.nSectors() - 1, mapeditor::ItemType::Sector }); + context_->renderer().animateSelectionChange({ static_cast(map.nSectors()) - 1, ItemType::Sector }); } // Set some sector defaults from game configuration if needed @@ -945,11 +955,11 @@ void Edit2D::createSector(Vec2d pos) const // Editor message if (ok) { - context_.addEditorMessage(fmt::format("Created sector #{}", map.nSectors() - 1)); - context_.endUndoRecord(true); + context_->addEditorMessage(fmt::format("Created sector #{}", map.nSectors() - 1)); + context_->endUndoRecord(true); } else - context_.addEditorMessage("Sector creation failed: " + builder.error()); + context_->addEditorMessage("Sector creation failed: " + builder.error()); } // ----------------------------------------------------------------------------- @@ -957,19 +967,17 @@ void Edit2D::createSector(Vec2d pos) const // ----------------------------------------------------------------------------- void Edit2D::deleteObject() const { - using mapeditor::Mode; - - switch (context_.editMode()) + switch (context_->editMode()) { case Mode::Vertices: deleteVertex(); break; - case Mode::Lines: deleteLine(); break; - case Mode::Sectors: deleteSector(); break; - case Mode::Things: deleteThing(); break; - default: return; + case Mode::Lines: deleteLine(); break; + case Mode::Sectors: deleteSector(); break; + case Mode::Things: deleteThing(); break; + default: return; } // Record undo step - context_.endUndoRecord(true); + context_->endUndoRecord(true); } // ----------------------------------------------------------------------------- @@ -978,30 +986,30 @@ void Edit2D::deleteObject() const void Edit2D::deleteVertex() const { // Get selected vertices - auto verts = context_.selection().selectedVertices(); + auto verts = context_->selection().selectedVertices(); int index = -1; if (verts.size() == 1) index = verts[0]->index(); // Clear hilight and selection - context_.selection().clear(); - context_.selection().clearHilight(); + context_->selection().clear(); + context_->selection().clearHilight(); // Begin undo step - context_.beginUndoRecord("Delete Vertices", map_merge_lines_on_delete_vertex, false, true); + context_->beginUndoRecord("Delete Vertices", map_merge_lines_on_delete_vertex, false, true); // Delete them (if any) for (auto& vertex : verts) - context_.map().removeVertex(vertex, map_merge_lines_on_delete_vertex); + context_->map().removeVertex(vertex, map_merge_lines_on_delete_vertex); // Remove detached vertices - context_.map().removeDetachedVertices(); + context_->map().removeDetachedVertices(); // Editor message if (verts.size() == 1) - context_.addEditorMessage(fmt::format("Deleted vertex #{}", index)); + context_->addEditorMessage(fmt::format("Deleted vertex #{}", index)); else if (verts.size() > 1) - context_.addEditorMessage(fmt::format("Deleted {} vertices", verts.size())); + context_->addEditorMessage(fmt::format("Deleted {} vertices", verts.size())); } // ----------------------------------------------------------------------------- @@ -1010,30 +1018,30 @@ void Edit2D::deleteVertex() const void Edit2D::deleteLine() const { // Get selected lines - auto lines = context_.selection().selectedLines(); + auto lines = context_->selection().selectedLines(); int index = -1; if (lines.size() == 1) index = lines[0]->index(); // Clear hilight and selection - context_.selection().clear(); - context_.selection().clearHilight(); + context_->selection().clear(); + context_->selection().clearHilight(); // Begin undo step - context_.beginUndoRecord("Delete Lines", false, false, true); + context_->beginUndoRecord("Delete Lines", false, false, true); // Delete them (if any) for (auto& line : lines) - context_.map().removeLine(line); + context_->map().removeLine(line); // Remove detached vertices - context_.map().removeDetachedVertices(); + context_->map().removeDetachedVertices(); // Editor message if (lines.size() == 1) - context_.addEditorMessage(fmt::format("Deleted line #{}", index)); + context_->addEditorMessage(fmt::format("Deleted line #{}", index)); else if (lines.size() > 1) - context_.addEditorMessage(fmt::format("Deleted {} lines", lines.size())); + context_->addEditorMessage(fmt::format("Deleted {} lines", lines.size())); } // ----------------------------------------------------------------------------- @@ -1042,27 +1050,27 @@ void Edit2D::deleteLine() const void Edit2D::deleteThing() const { // Get selected things - auto things = context_.selection().selectedThings(); + auto things = context_->selection().selectedThings(); int index = -1; if (things.size() == 1) index = things[0]->index(); // Clear hilight and selection - context_.selection().clear(); - context_.selection().clearHilight(); + context_->selection().clear(); + context_->selection().clearHilight(); // Begin undo step - context_.beginUndoRecord("Delete Things", false, false, true); + context_->beginUndoRecord("Delete Things", false, false, true); // Delete them (if any) for (auto& thing : things) - context_.map().removeThing(thing); + context_->map().removeThing(thing); // Editor message if (things.size() == 1) - context_.addEditorMessage(fmt::format("Deleted thing #{}", index)); + context_->addEditorMessage(fmt::format("Deleted thing #{}", index)); else if (things.size() > 1) - context_.addEditorMessage(fmt::format("Deleted {} things", things.size())); + context_->addEditorMessage(fmt::format("Deleted {} things", things.size())); } // ----------------------------------------------------------------------------- @@ -1071,17 +1079,17 @@ void Edit2D::deleteThing() const void Edit2D::deleteSector() const { // Get selected sectors - auto sectors = context_.selection().selectedSectors(); + auto sectors = context_->selection().selectedSectors(); int index = -1; if (sectors.size() == 1) index = sectors[0]->index(); // Clear hilight and selection - context_.selection().clear(); - context_.selection().clearHilight(); + context_->selection().clear(); + context_->selection().clearHilight(); // Begin undo step - context_.beginUndoRecord("Delete Sectors", true, false, true); + context_->beginUndoRecord("Delete Sectors", true, false, true); // Delete them (if any), and keep lists of connected lines and sides vector connected_sides; @@ -1101,7 +1109,7 @@ void Edit2D::deleteSector() const if (side == line->s1() && line->s2()) line->flip(); - context_.map().removeSide(side); + context_->map().removeSide(side); } // Remove resulting invalid lines @@ -1110,7 +1118,7 @@ void Edit2D::deleteSector() const for (auto line : connected_lines) { if (!line->s1() && !line->s2()) - context_.map().removeLine(line); + context_->map().removeLine(line); } } @@ -1137,9 +1145,9 @@ void Edit2D::deleteSector() const // If there still isn't a texture, find an adjacent texture to use if (side->texMiddle() == MapSide::TEX_NONE) { - auto adj_tex = context_.map().adjacentLineTexture(line->v1()); + auto adj_tex = context_->map().adjacentLineTexture(line->v1()); if (adj_tex == MapSide::TEX_NONE) - adj_tex = context_.map().adjacentLineTexture(line->v2()); + adj_tex = context_->map().adjacentLineTexture(line->v2()); if (adj_tex != MapSide::TEX_NONE) side->setTexMiddle(adj_tex); @@ -1152,10 +1160,10 @@ void Edit2D::deleteSector() const // Editor message if (sectors.size() == 1) - context_.addEditorMessage(fmt::format("Deleted sector #{}", index)); + context_->addEditorMessage(fmt::format("Deleted sector #{}", index)); else if (sectors.size() > 1) - context_.addEditorMessage(fmt::format("Deleted {} sector", sectors.size())); + context_->addEditorMessage(fmt::format("Deleted {} sector", sectors.size())); // Remove detached vertices - context_.map().removeDetachedVertices(); + context_->map().removeDetachedVertices(); } diff --git a/src/MapEditor/Edit/Edit2D.h b/src/MapEditor/Edit/Edit2D.h index acd174951..3b36e83a6 100644 --- a/src/MapEditor/Edit/Edit2D.h +++ b/src/MapEditor/Edit/Edit2D.h @@ -1,15 +1,22 @@ #pragma once -#include "SLADEMap/MapObject/MapLine.h" -#include "SLADEMap/MapObject/MapSector.h" -#include "SLADEMap/MapObject/MapSide.h" -#include "SLADEMap/MapObject/MapThing.h" - +// Forward declarations namespace slade { +class MapThing; +class MapSector; +class MapSide; +class MapLine; class MapObject; -class MapEditContext; +namespace mapeditor +{ + class MapEditContext; +} +} // namespace slade + +namespace slade::mapeditor +{ class Edit2D { public: @@ -31,20 +38,20 @@ class Edit2D void joinSectors(bool remove_lines) const; // Things - void changeThingType(); - void thingQuickAngle(Vec2d mouse_pos) const; + void changeThingType() const; + void thingQuickAngle(const Vec2d& mouse_pos) const; // Copy / Paste void copy() const; - void paste(Vec2d mouse_pos) const; + void paste(const Vec2d& mouse_pos) const; void copyProperties(); - void pasteProperties(); + void pasteProperties() const; // Create / Delete - void createObject(Vec2d pos) const; + void createObject(const Vec2d& pos) const; void createVertex(Vec2d pos) const; void createThing(Vec2d pos) const; - void createSector(Vec2d pos) const; + void createSector(const Vec2d& pos) const; void deleteObject() const; void deleteVertex() const; void deleteLine() const; @@ -52,16 +59,16 @@ class Edit2D void deleteSector() const; private: - MapEditContext& context_; + MapEditContext* context_ = nullptr; // Object properties and copy/paste - MapThing copy_thing_; - MapSector copy_sector_; - MapSide copy_side_front_; - MapSide copy_side_back_; - MapLine copy_line_; - bool line_copied_ = false; - bool sector_copied_ = false; - bool thing_copied_ = false; + unique_ptr copy_thing_; + unique_ptr copy_sector_; + unique_ptr copy_side_front_; + unique_ptr copy_side_back_; + unique_ptr copy_line_; + bool line_copied_ = false; + bool sector_copied_ = false; + bool thing_copied_ = false; }; -} // namespace slade +} // namespace slade::mapeditor diff --git a/src/MapEditor/Edit/Edit3D.cpp b/src/MapEditor/Edit/Edit3D.cpp index 0659138c2..36f2a8398 100644 --- a/src/MapEditor/Edit/Edit3D.cpp +++ b/src/MapEditor/Edit/Edit3D.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -34,12 +34,21 @@ #include "Game/Configuration.h" #include "General/UndoRedo.h" #include "MapEditor/MapEditContext.h" +#include "MapEditor/MapEditor.h" #include "MapEditor/MapTextureManager.h" +#include "MapEditor/Renderer/Renderer.h" #include "MapEditor/UndoSteps.h" +#include "OpenGL/GLTexture.h" +#include "SLADEMap/MapObject/MapLine.h" +#include "SLADEMap/MapObject/MapSector.h" +#include "SLADEMap/MapObject/MapSide.h" +#include "SLADEMap/MapObject/MapThing.h" +#include "SLADEMap/MapObject/MapVertex.h" +#include "SLADEMap/SLADEMap.h" #include "Utility/MathStuff.h" using namespace slade; -using mapeditor::ItemType; +using namespace mapeditor; // ----------------------------------------------------------------------------- @@ -52,23 +61,24 @@ using mapeditor::ItemType; // ----------------------------------------------------------------------------- // Edit3D class constructor // ----------------------------------------------------------------------------- -Edit3D::Edit3D(MapEditContext& context) : context_{ context }, link_light_{ false }, link_offset_{ false } +Edit3D::Edit3D(MapEditContext& context) : context_{ &context } { undo_manager_ = std::make_unique(&context.map()); + copy_thing_ = std::make_unique(); } // ----------------------------------------------------------------------------- // Selects all adjacent walls or flats to [item] // ----------------------------------------------------------------------------- -void Edit3D::selectAdjacent(mapeditor::Item item) const +void Edit3D::selectAdjacent(Item item) const { // Check item if (item.index < 0) return; // Select every adjacent item - context_.selection().select(getAdjacent(item)); - context_.selectionUpdated(); + context_->selection().select(getAdjacent(item)); + context_->selectionUpdated(); } // ----------------------------------------------------------------------------- @@ -77,9 +87,9 @@ void Edit3D::selectAdjacent(mapeditor::Item item) const void Edit3D::changeSectorLight(int amount) const { // Get items to process - vector items; - auto& selection_3d = context_.selection(); - auto hilight_3d = context_.hilightItem(); + vector items; + auto& selection_3d = context_->selection(); + auto hilight_3d = context_->hilightItem(); if (selection_3d.empty() && hilight_3d.index >= 0 && hilight_3d.type != ItemType::Thing) items.push_back(hilight_3d); else @@ -94,7 +104,7 @@ void Edit3D::changeSectorLight(int amount) const return; // Begin undo level - context_.beginUndoRecordLocked("Change Sector Light", true, false, false); + context_->beginUndoRecordLocked("Change Sector Light", true, false, false); // Go through items std::set processed; @@ -104,7 +114,7 @@ void Edit3D::changeSectorLight(int amount) const if (item.type == ItemType::WallBottom || item.type == ItemType::WallMiddle || item.type == ItemType::WallTop) { // Get side - auto side = item.asSide(context_.map()); + auto side = item.asSide(context_->map()); if (!side) continue; auto sector = side->sector(); @@ -142,7 +152,7 @@ void Edit3D::changeSectorLight(int amount) const if (item.type == ItemType::Floor || item.type == ItemType::Ceiling) { // Get sector - auto s = context_.map().sector(item.index); + auto s = context_->map().sector(item.index); int where = 0; if (item.type == ItemType::Floor && !link_light_) where = 1; @@ -167,15 +177,15 @@ void Edit3D::changeSectorLight(int amount) const } // End undo level - context_.endUndoRecord(); + context_->endUndoRecord(); // Editor message if (!items.empty()) { if (amount > 0) - context_.addEditorMessage(fmt::format("Light increased by {}", amount)); + context_->addEditorMessage(fmt::format("Light increased by {}", amount)); else - context_.addEditorMessage(fmt::format("Light decreased by {}", -amount)); + context_->addEditorMessage(fmt::format("Light decreased by {}", -amount)); } } @@ -186,9 +196,9 @@ void Edit3D::changeSectorLight(int amount) const void Edit3D::changeOffset(int amount, bool x) const { // Get items to process - vector items; - auto& selection_3d = context_.selection(); - auto hilight_3d = context_.hilightItem(); + vector items; + auto& selection_3d = context_->selection(); + auto hilight_3d = context_->hilightItem(); if (selection_3d.empty()) { if (hilight_3d.index >= 0 && hilight_3d.type != ItemType::Thing) @@ -206,7 +216,7 @@ void Edit3D::changeOffset(int amount, bool x) const return; // Begin undo level - context_.beginUndoRecordLocked("Change Offset", true, false, false); + context_->beginUndoRecordLocked("Change Offset", true, false, false); // Go through items vector done; @@ -218,7 +228,7 @@ void Edit3D::changeOffset(int amount, bool x) const // Wall if (item.type >= ItemType::WallTop && item.type <= ItemType::WallBottom) { - auto side = context_.map().side(index); + auto side = context_->map().side(index); // If offsets are linked, just change the whole side offset if (link_offset_) @@ -262,7 +272,7 @@ void Edit3D::changeOffset(int amount, bool x) const // Flat (UDMF only) else if (item.type == ItemType::Ceiling || item.type == ItemType::Floor) { - auto sector = context_.map().sector(item.index); + auto sector = context_->map().sector(item.index); if (game::configuration().featureSupported(game::UDMFFeature::FlatPanning)) { @@ -301,7 +311,7 @@ void Edit3D::changeOffset(int amount, bool x) const } // End undo level - context_.endUndoRecord(changed); + context_->endUndoRecord(changed); // Editor message if (!items.empty() && changed) @@ -311,9 +321,9 @@ void Edit3D::changeOffset(int amount, bool x) const axis = 'Y'; if (amount > 0) - context_.addEditorMessage(fmt::format("{} offset increased by {}", axis, amount)); + context_->addEditorMessage(fmt::format("{} offset increased by {}", axis, amount)); else - context_.addEditorMessage(fmt::format("{} offset decreased by {}", axis, -amount)); + context_->addEditorMessage(fmt::format("{} offset decreased by {}", axis, -amount)); } } @@ -324,9 +334,9 @@ void Edit3D::changeOffset(int amount, bool x) const void Edit3D::changeSectorHeight(int amount) const { // Get items to process - vector items; - auto& selection_3d = context_.selection(); - auto hilight_3d = context_.hilightItem(); + vector items; + auto& selection_3d = context_->selection(); + auto hilight_3d = context_->hilightItem(); if (selection_3d.empty() && hilight_3d.type != ItemType::Thing && hilight_3d.index >= 0) items.push_back(hilight_3d); else @@ -341,7 +351,7 @@ void Edit3D::changeSectorHeight(int amount) const return; // Begin undo level - context_.beginUndoRecordLocked("Change Sector Height", true, false, false); + context_->beginUndoRecordLocked("Change Sector Height", true, false, false); // Go through items vector ceilings; @@ -351,7 +361,7 @@ void Edit3D::changeSectorHeight(int amount) const if (item.type == ItemType::WallBottom || item.type == ItemType::WallMiddle || item.type == ItemType::WallTop) { // Get sector - auto sector = context_.map().side(item.index)->sector(); + auto sector = context_->map().side(item.index)->sector(); // Check this sector's ceiling hasn't already been changed int index = sector->index(); @@ -371,7 +381,7 @@ void Edit3D::changeSectorHeight(int amount) const bool floor = (item.type == ItemType::Floor); // Get sector - MapSector* sector = context_.map().sector(item.index); + MapSector* sector = context_->map().sector(item.index); if (floor) { @@ -395,29 +405,29 @@ void Edit3D::changeSectorHeight(int amount) const } // End undo level - context_.endUndoRecord(); + context_->endUndoRecord(); // Editor message if (!items.empty()) { if (amount > 0) - context_.addEditorMessage(fmt::format("Height increased by {}", amount)); + context_->addEditorMessage(fmt::format("Height increased by {}", amount)); else - context_.addEditorMessage(fmt::format("Height decreased by {}", -amount)); + context_->addEditorMessage(fmt::format("Height decreased by {}", -amount)); } } // ----------------------------------------------------------------------------- // Aligns X offsets beginning from the wall selection [start] // ----------------------------------------------------------------------------- -void Edit3D::autoAlignX(mapeditor::Item start) const +void Edit3D::autoAlignX(Item start) const { // Check start is a wall if (start.type != ItemType::WallBottom && start.type != ItemType::WallMiddle && start.type != ItemType::WallTop) return; // Get starting side - auto side = context_.map().side(start.index); + auto side = context_->map().side(start.index); if (!side) return; @@ -443,19 +453,19 @@ void Edit3D::autoAlignX(mapeditor::Item start) const tex_width = gl::Texture::info(gl_tex).size.x; // Init aligned wall list - vector walls_done; + vector walls_done; // Begin undo level - context_.beginUndoRecord("Auto Align X", true, false, false); + context_->beginUndoRecord("Auto Align X", true, false, false); // Do alignment doAlignX(side, side->texOffsetX(), tex, walls_done, tex_width); // End undo level - context_.endUndoRecord(); + context_->endUndoRecord(); // Editor message - context_.addEditorMessage("Auto-aligned on X axis"); + context_->addEditorMessage("Auto-aligned on X axis"); } // ----------------------------------------------------------------------------- @@ -466,11 +476,11 @@ void Edit3D::resetOffsets() const using game::UDMFFeature; // Get items to process - vector walls; - vector flats; - vector things; - auto& selection_3d = context_.selection(); - auto hilight_3d = context_.hilightItem(); + vector walls; + vector flats; + vector things; + auto& selection_3d = context_->selection(); + auto hilight_3d = context_->hilightItem(); if (selection_3d.empty()) { if (hilight_3d.type == ItemType::WallTop || hilight_3d.type == ItemType::WallBottom @@ -498,12 +508,12 @@ void Edit3D::resetOffsets() const return; // Begin undo level - context_.beginUndoRecord("Reset Offsets", true, false, false); + context_->beginUndoRecord("Reset Offsets", true, false, false); // Go through walls for (auto& wall : walls) { - auto side = wall.asSide(context_.map()); + auto side = wall.asSide(context_->map()); if (!side) continue; @@ -535,7 +545,7 @@ void Edit3D::resetOffsets() const } // Reset scaling - if (context_.mapDesc().format == MapFormat::UDMF + if (context_->mapDesc().format == MapFormat::UDMF && game::configuration().featureSupported(UDMFFeature::TextureScaling)) { if (wall.type == ItemType::WallTop) @@ -557,11 +567,11 @@ void Edit3D::resetOffsets() const } // Go through flats - if (context_.mapDesc().format == MapFormat::UDMF) + if (context_->mapDesc().format == MapFormat::UDMF) { for (auto& flat : flats) { - auto sector = flat.asSector(context_.map()); + auto sector = flat.asSector(context_->map()); if (!sector) continue; @@ -588,16 +598,16 @@ void Edit3D::resetOffsets() const } // Go through things - if (context_.mapDesc().format != MapFormat::Doom) + if (context_->mapDesc().format != MapFormat::Doom) { for (auto& item : things) { - auto thing = item.asThing(context_.map()); + auto thing = item.asThing(context_->map()); if (!thing) continue; // Reset height - if (context_.mapDesc().format != MapFormat::UDMF) + if (context_->mapDesc().format != MapFormat::UDMF) thing->setZ(0); else { @@ -620,16 +630,16 @@ void Edit3D::resetOffsets() const } // End undo level - context_.endUndoRecord(); + context_->endUndoRecord(); // Editor message - if (context_.mapDesc().format == MapFormat::UDMF + if (context_->mapDesc().format == MapFormat::UDMF && (game::configuration().featureSupported(UDMFFeature::FlatScaling) || game::configuration().featureSupported(UDMFFeature::SideScaling) || game::configuration().featureSupported(UDMFFeature::TextureScaling))) - context_.addEditorMessage("Offsets and scaling reset"); + context_->addEditorMessage("Offsets and scaling reset"); else - context_.addEditorMessage("Offsets reset"); + context_->addEditorMessage("Offsets reset"); } // ----------------------------------------------------------------------------- @@ -637,13 +647,13 @@ void Edit3D::resetOffsets() const // ----------------------------------------------------------------------------- void Edit3D::toggleUnpegged(bool lower) const { - auto& selection_3d = context_.selection(); - auto hilight_3d = context_.hilightItem(); + auto& selection_3d = context_->selection(); + auto hilight_3d = context_->hilightItem(); if (selection_3d.empty() && hilight_3d.index < 0) return; // Get items to process - vector items; + vector items; if (selection_3d.empty()) { if (hilight_3d.type == ItemType::WallTop || hilight_3d.type == ItemType::WallBottom @@ -670,7 +680,7 @@ void Edit3D::toggleUnpegged(bool lower) const vector processed_lines; for (auto& item : items) { - auto side = item.asSide(context_.map()); + auto side = item.asSide(context_->map()); if (!side || !side->parentLine()) continue; @@ -684,16 +694,16 @@ void Edit3D::toggleUnpegged(bool lower) const processed_lines.push_back(line); // Toggle flag - context_.recordPropertyChangeUndoStep(line); + context_->recordPropertyChangeUndoStep(line); if (lower) { - bool unpegged = game::configuration().lineBasicFlagSet("dontpegbottom", line, context_.mapDesc().format); - game::configuration().setLineBasicFlag("dontpegbottom", line, context_.map().currentFormat(), !unpegged); + bool unpegged = game::configuration().lineBasicFlagSet("dontpegbottom", line, context_->mapDesc().format); + game::configuration().setLineBasicFlag("dontpegbottom", line, context_->map().currentFormat(), !unpegged); } else { - bool unpegged = game::configuration().lineBasicFlagSet("dontpegtop", line, context_.mapDesc().format); - game::configuration().setLineBasicFlag("dontpegtop", line, context_.map().currentFormat(), !unpegged); + bool unpegged = game::configuration().lineBasicFlagSet("dontpegtop", line, context_->mapDesc().format); + game::configuration().setLineBasicFlag("dontpegtop", line, context_->map().currentFormat(), !unpegged); } } @@ -702,9 +712,9 @@ void Edit3D::toggleUnpegged(bool lower) const // Editor message if (lower) - context_.addEditorMessage("Lower Unpegged flag toggled"); + context_->addEditorMessage("Lower Unpegged flag toggled"); else - context_.addEditorMessage("Upper Unpegged flag toggled"); + context_->addEditorMessage("Upper Unpegged flag toggled"); } // ----------------------------------------------------------------------------- @@ -712,8 +722,8 @@ void Edit3D::toggleUnpegged(bool lower) const // ----------------------------------------------------------------------------- void Edit3D::copy(CopyType type) { - auto hl = context_.selection().hilight(); - auto& map = context_.map(); + auto hl = context_->selection().hilight(); + auto& map = context_->map(); auto side = hl.asSide(map); auto sector = hl.asSector(map); @@ -766,19 +776,19 @@ void Edit3D::copy(CopyType type) else if (hl.type == ItemType::Thing) { if (auto thing = hl.asThing(map)) - copy_thing_.copy(thing); + copy_thing_->copy(thing); } // Flash - context_.renderer().animateSelectionChange(hl); + context_->renderer().animateSelectionChange(hl); // Editor message if (type == CopyType::TexType) { if (hl.type == ItemType::Thing) - context_.addEditorMessage("Copied Thing Type"); + context_->addEditorMessage("Copied Thing Type"); else - context_.addEditorMessage("Copied Texture"); + context_->addEditorMessage("Copied Texture"); } } @@ -794,13 +804,13 @@ void Edit3D::paste(CopyType type) const undo_manager_->beginRecord(ptype); // Go through items - auto& selection = context_.selection(); + auto& selection = context_->selection(); for (auto& item : selection.selectionOrHilight()) { // Wall - if (auto side = item.asSide(context_.map())) + if (auto side = item.asSide(context_->map())) { - undo_manager_->recordUndoStep(std::make_unique(side)); + undo_manager_->recordUndoStep(std::make_unique(side)); // Upper wall if (item.type == ItemType::WallTop) @@ -828,9 +838,9 @@ void Edit3D::paste(CopyType type) const } // Flat - else if (auto sector = item.asSector(context_.map())) + else if (auto sector = item.asSector(context_->map())) { - undo_manager_->recordUndoStep(std::make_unique(sector)); + undo_manager_->recordUndoStep(std::make_unique(sector)); // Floor if (item.type == ItemType::Floor) @@ -852,13 +862,13 @@ void Edit3D::paste(CopyType type) const // Thing else if (item.type == ItemType::Thing) { - if (auto thing = item.asThing(context_.map())) + if (auto thing = item.asThing(context_->map())) { - undo_manager_->recordUndoStep(std::make_unique(thing)); + undo_manager_->recordUndoStep(std::make_unique(thing)); // Type if (type == CopyType::TexType) - thing->setType(copy_thing_.type()); + thing->setType(copy_thing_->type()); } } } @@ -867,9 +877,9 @@ void Edit3D::paste(CopyType type) const if (type == CopyType::TexType) { if (selection.hilight().type == ItemType::Thing) - context_.addEditorMessage("Pasted Thing Type"); + context_->addEditorMessage("Pasted Thing Type"); else - context_.addEditorMessage("Pasted Texture"); + context_->addEditorMessage("Pasted Texture"); } undo_manager_->endRecord(true); @@ -881,7 +891,7 @@ void Edit3D::paste(CopyType type) const void Edit3D::floodFill(CopyType type) const { // Get items to paste to - auto& selection = context_.selection(); + auto& selection = context_->selection(); auto items = getAdjacent(selection.hilight()); // Restrict floodfill to selection, if any @@ -914,9 +924,9 @@ void Edit3D::floodFill(CopyType type) const for (auto& item : items) { // Wall - if (auto side = item.asSide(context_.map())) + if (auto side = item.asSide(context_->map())) { - undo_manager_->recordUndoStep(std::make_unique(side)); + undo_manager_->recordUndoStep(std::make_unique(side)); // Upper wall if (item.type == ItemType::WallTop) @@ -944,9 +954,9 @@ void Edit3D::floodFill(CopyType type) const } // Flat - else if (auto sector = item.asSector(context_.map())) + else if (auto sector = item.asSector(context_->map())) { - undo_manager_->recordUndoStep(std::make_unique(sector)); + undo_manager_->recordUndoStep(std::make_unique(sector)); // Floor if (item.type == ItemType::Floor) @@ -969,7 +979,7 @@ void Edit3D::floodFill(CopyType type) const // Editor message if (type == CopyType::TexType) { - context_.addEditorMessage("Floodfilled Texture"); + context_->addEditorMessage("Floodfilled Texture"); } undo_manager_->endRecord(true); @@ -981,19 +991,19 @@ void Edit3D::floodFill(CopyType type) const void Edit3D::changeThingZ(int amount) const { // Ignore for doom format - if (context_.map().currentFormat() == MapFormat::Doom) + if (context_->map().currentFormat() == MapFormat::Doom) return; // Go through 3d selection - auto& selection_3d = context_.selection(); + auto& selection_3d = context_->selection(); bool changed = false; for (auto& item : selection_3d) { // Check if thing - if (auto thing = item.asThing(context_.map())) + if (auto thing = item.asThing(context_->map())) { // Change z height - context_.recordPropertyChangeUndoStep(thing); + context_->recordPropertyChangeUndoStep(thing); double z = thing->zPos(); z += amount; thing->setZ(z); @@ -1002,7 +1012,7 @@ void Edit3D::changeThingZ(int amount) const } if (changed) - context_.map().recomputeSpecials(); + context_->map().recomputeSpecials(); } // ----------------------------------------------------------------------------- @@ -1011,18 +1021,18 @@ void Edit3D::changeThingZ(int amount) const void Edit3D::deleteThing() const { // Begin undo level - context_.beginUndoRecord("Delete Thing", false, false, true); + context_->beginUndoRecord("Delete Thing", false, false, true); // Go through 3d selection - auto& selection_3d = context_.selection(); + auto& selection_3d = context_->selection(); for (auto& item : selection_3d) { // Check if thing if (item.type == ItemType::Thing) - context_.map().removeThing(item.index); + context_->map().removeThing(item.index); } - context_.endUndoRecord(); + context_->endUndoRecord(); } // ----------------------------------------------------------------------------- @@ -1034,9 +1044,9 @@ void Edit3D::changeScale(double amount, bool x) const using game::UDMFFeature; // Get items to process - vector items; - auto& selection_3d = context_.selection(); - auto hilight_3d = context_.hilightItem(); + vector items; + auto& selection_3d = context_->selection(); + auto hilight_3d = context_->hilightItem(); if (selection_3d.empty()) { if (hilight_3d.index >= 0 && hilight_3d.type != ItemType::Thing) @@ -1054,7 +1064,7 @@ void Edit3D::changeScale(double amount, bool x) const return; // Begin undo level - context_.beginUndoRecordLocked("Change Scale", true, false, false); + context_->beginUndoRecordLocked("Change Scale", true, false, false); // Go through selection for (auto& item : items) @@ -1063,7 +1073,7 @@ void Edit3D::changeScale(double amount, bool x) const if (game::configuration().featureSupported(UDMFFeature::SideScaling) || game::configuration().featureSupported(UDMFFeature::TextureScaling)) { - if (auto side = item.asSide(context_.map())) + if (auto side = item.asSide(context_->map())) { // Build property string (offset[x/y]_[top/mid/bottom]) string ofs = "scalex"; @@ -1089,7 +1099,7 @@ void Edit3D::changeScale(double amount, bool x) const // Flat (UDMF only) else if (game::configuration().featureSupported(UDMFFeature::FlatScaling)) { - if (auto sector = item.asSector(context_.map())) + if (auto sector = item.asSector(context_->map())) { // Build property string string prop = x ? "xscale" : "yscale"; @@ -1104,7 +1114,7 @@ void Edit3D::changeScale(double amount, bool x) const } // End undo record - context_.endUndoRecord(true); + context_->endUndoRecord(true); // Editor message } @@ -1118,10 +1128,10 @@ void Edit3D::changeScale(double amount, bool x) const void Edit3D::changeHeight(int amount) const { // Get items to process - vector items; - auto& selection_3d = context_.selection(); - auto hilight_3d = context_.hilightItem(); - auto& map = context_.map(); + vector items; + auto& selection_3d = context_->selection(); + auto hilight_3d = context_->hilightItem(); + auto& map = context_->map(); if (selection_3d.empty() && hilight_3d.index >= 0) { if (hilight_3d.type != ItemType::Thing || map.currentFormat() != MapFormat::Doom) @@ -1137,7 +1147,7 @@ void Edit3D::changeHeight(int amount) const return; // Begin undo level - context_.beginUndoRecordLocked("Change Height", true, false, false); + context_->beginUndoRecordLocked("Change Height", true, false, false); // Go through items for (auto& item : items) @@ -1174,7 +1184,7 @@ void Edit3D::changeHeight(int amount) const // Change the offset float offset = side->floatProperty(ofs); - side->setFloatProperty(ofs, offset + amount); + side->setFloatProperty(ofs, offset + static_cast(amount)); } // Flat @@ -1188,15 +1198,15 @@ void Edit3D::changeHeight(int amount) const } // End undo level - context_.endUndoRecord(); + context_->endUndoRecord(); // Editor message if (!items.empty()) { if (amount > 0) - context_.addEditorMessage(fmt::format("Height increased by {}", amount)); + context_->addEditorMessage(fmt::format("Height increased by {}", amount)); else - context_.addEditorMessage(fmt::format("Height decreased by {}", -amount)); + context_->addEditorMessage(fmt::format("Height decreased by {}", -amount)); } } @@ -1207,18 +1217,18 @@ void Edit3D::changeHeight(int amount) const void Edit3D::changeTexture() const { // Check for selection or hilight - auto selection = context_.selection().selectionOrHilight(); + auto selection = context_->selection().selectionOrHilight(); if (selection.empty()) return; // Get initial texture string tex; - auto type = mapeditor::TextureType::Texture; + auto type = TextureType::Texture; auto& first = selection[0]; - auto& map = context_.map(); + auto& map = context_->map(); if (auto sector = first.asSector(map)) { - type = mapeditor::TextureType::Flat; + type = TextureType::Flat; if (first.type == ItemType::Floor) tex = sector->floor().texture; @@ -1242,10 +1252,10 @@ void Edit3D::changeTexture() const bool mix = game::configuration().featureSupported(game::Feature::MixTexFlats); // Begin undo level - context_.beginUndoRecord("Change Texture", true, false, false); + context_->beginUndoRecord("Change Texture", true, false, false); // Apply to flats - if (mix || type == mapeditor::TextureType::Flat) + if (mix || type == TextureType::Flat) { for (auto& item : selection) { @@ -1260,7 +1270,7 @@ void Edit3D::changeTexture() const } // Apply to walls - if (mix || type == mapeditor::TextureType::Texture) + if (mix || type == TextureType::Texture) { for (auto& item : selection) { @@ -1277,7 +1287,7 @@ void Edit3D::changeTexture() const } // End undo level - context_.endUndoRecord(); + context_->endUndoRecord(); } } @@ -1286,8 +1296,8 @@ void Edit3D::changeTexture() const // ----------------------------------------------------------------------------- void Edit3D::deleteTexture() const { - auto& map = context_.map(); - for (auto& item : context_.selection().selectionOrHilight()) + auto& map = context_->map(); + for (auto& item : context_->selection().selectionOrHilight()) { if (item.type == ItemType::Floor) map.sector(item.index)->setStringProperty("texturefloor", "-"); @@ -1306,9 +1316,9 @@ void Edit3D::deleteTexture() const // Returns a list of all walls or flats adjacent to [item]. // Adjacent meaning connected and sharing a texture // ----------------------------------------------------------------------------- -vector Edit3D::getAdjacent(mapeditor::Item item) const +vector Edit3D::getAdjacent(Item item) const { - vector list; + vector list; // Check item if (item.index < 0 || item.type == ItemType::Thing) @@ -1328,7 +1338,7 @@ vector Edit3D::getAdjacent(mapeditor::Item item) const // ----------------------------------------------------------------------------- // Returns true if the texture [part] of [side] matches [tex] // ----------------------------------------------------------------------------- -bool Edit3D::wallMatches(MapSide* side, ItemType part, string_view tex) +bool Edit3D::wallMatches(const MapSide* side, ItemType part, string_view tex) { // Check for blank texture where it isn't needed if (tex == MapSide::TEX_NONE) @@ -1370,7 +1380,7 @@ bool Edit3D::wallMatches(MapSide* side, ItemType part, string_view tex) // Adds all adjacent walls to [item] to [list]. // Adjacent meaning connected and sharing a texture // ----------------------------------------------------------------------------- -void Edit3D::getAdjacentWalls(mapeditor::Item item, vector& list) const +void Edit3D::getAdjacentWalls(Item item, vector& list) const { // Add item to list if needed for (auto& list_item : list) @@ -1381,7 +1391,7 @@ void Edit3D::getAdjacentWalls(mapeditor::Item item, vector& lis list.push_back(item); // Get initial side - auto side = item.asSide(context_.map()); + auto side = item.asSide(context_->map()); if (!side) return; @@ -1415,15 +1425,15 @@ void Edit3D::getAdjacentWalls(mapeditor::Item item, vector& lis { // Upper texture if (wallMatches(side1, ItemType::WallTop, tex)) - getAdjacentWalls({ (int)side1->index(), ItemType::WallTop }, list); + getAdjacentWalls({ static_cast(side1->index()), ItemType::WallTop }, list); // Middle texture if (wallMatches(side1, ItemType::WallMiddle, tex)) - getAdjacentWalls({ (int)side1->index(), ItemType::WallMiddle }, list); + getAdjacentWalls({ static_cast(side1->index()), ItemType::WallMiddle }, list); // Lower texture if (wallMatches(side1, ItemType::WallBottom, tex)) - getAdjacentWalls({ (int)side1->index(), ItemType::WallBottom }, list); + getAdjacentWalls({ static_cast(side1->index()), ItemType::WallBottom }, list); } // Back side @@ -1431,15 +1441,15 @@ void Edit3D::getAdjacentWalls(mapeditor::Item item, vector& lis { // Upper texture if (wallMatches(side2, ItemType::WallTop, tex)) - getAdjacentWalls({ (int)side2->index(), ItemType::WallTop }, list); + getAdjacentWalls({ static_cast(side2->index()), ItemType::WallTop }, list); // Middle texture if (wallMatches(side2, ItemType::WallMiddle, tex)) - getAdjacentWalls({ (int)side2->index(), ItemType::WallMiddle }, list); + getAdjacentWalls({ static_cast(side2->index()), ItemType::WallMiddle }, list); // Lower texture if (wallMatches(side2, ItemType::WallBottom, tex)) - getAdjacentWalls({ (int)side2->index(), ItemType::WallBottom }, list); + getAdjacentWalls({ static_cast(side2->index()), ItemType::WallBottom }, list); } } @@ -1459,15 +1469,15 @@ void Edit3D::getAdjacentWalls(mapeditor::Item item, vector& lis { // Upper texture if (wallMatches(side1, ItemType::WallTop, tex)) - getAdjacentWalls({ (int)side1->index(), ItemType::WallTop }, list); + getAdjacentWalls({ static_cast(side1->index()), ItemType::WallTop }, list); // Middle texture if (wallMatches(side1, ItemType::WallMiddle, tex)) - getAdjacentWalls({ (int)side1->index(), ItemType::WallMiddle }, list); + getAdjacentWalls({ static_cast(side1->index()), ItemType::WallMiddle }, list); // Lower texture if (wallMatches(side1, ItemType::WallBottom, tex)) - getAdjacentWalls({ (int)side1->index(), ItemType::WallBottom }, list); + getAdjacentWalls({ static_cast(side1->index()), ItemType::WallBottom }, list); } // Back side @@ -1475,15 +1485,15 @@ void Edit3D::getAdjacentWalls(mapeditor::Item item, vector& lis { // Upper texture if (wallMatches(side2, ItemType::WallTop, tex)) - getAdjacentWalls({ (int)side2->index(), ItemType::WallTop }, list); + getAdjacentWalls({ static_cast(side2->index()), ItemType::WallTop }, list); // Middle texture if (wallMatches(side2, ItemType::WallMiddle, tex)) - getAdjacentWalls({ (int)side2->index(), ItemType::WallMiddle }, list); + getAdjacentWalls({ static_cast(side2->index()), ItemType::WallMiddle }, list); // Lower texture if (wallMatches(side2, ItemType::WallBottom, tex)) - getAdjacentWalls({ (int)side2->index(), ItemType::WallBottom }, list); + getAdjacentWalls({ static_cast(side2->index()), ItemType::WallBottom }, list); } } } @@ -1492,7 +1502,7 @@ void Edit3D::getAdjacentWalls(mapeditor::Item item, vector& lis // Adds all walls and flats adjacent to [item] to [list]. // Adjacent meaning connected and sharing a texture // ----------------------------------------------------------------------------- -void Edit3D::getAdjacentFlats(mapeditor::Item item, vector& list) const +void Edit3D::getAdjacentFlats(Item item, vector& list) const { // Check item if (item.index < 0 || (item.type != ItemType::Floor && item.type != ItemType::Ceiling)) @@ -1502,7 +1512,7 @@ void Edit3D::getAdjacentFlats(mapeditor::Item item, vector& lis list.push_back(item); // Get initial sector - auto sector = item.asSector(context_.map()); + auto sector = item.asSector(context_->map()); if (!sector) return; @@ -1557,7 +1567,7 @@ void Edit3D::getAdjacentFlats(mapeditor::Item item, vector& lis bool listed = false; for (auto& i : list) { - if (i.type == item.type && i.index == (int)osector->index()) + if (i.type == item.type && i.index == static_cast(osector->index())) { listed = true; break; @@ -1568,7 +1578,7 @@ void Edit3D::getAdjacentFlats(mapeditor::Item item, vector& lis if (!listed) { list.push_back(item); - getAdjacentFlats({ (int)osector->index(), item.type }, list); + getAdjacentFlats({ static_cast(osector->index()), item.type }, list); } } } @@ -1576,17 +1586,17 @@ void Edit3D::getAdjacentFlats(mapeditor::Item item, vector& lis // ----------------------------------------------------------------------------- // Recursive function to align textures on the x axis // ----------------------------------------------------------------------------- -void Edit3D::doAlignX(MapSide* side, int offset, string_view tex, vector& walls_done, int tex_width) +void Edit3D::doAlignX(MapSide* side, int offset, string_view tex, vector& walls_done, int tex_width) { // Check if this wall has already been processed for (auto& item : walls_done) { - if (item.index == (int)side->index()) + if (item.index == static_cast(side->index())) return; } // Add to 'done' list - walls_done.emplace_back((int)side->index(), ItemType::WallMiddle); + walls_done.emplace_back(static_cast(side->index()), ItemType::WallMiddle); // Wrap offset if (tex_width > 0) diff --git a/src/MapEditor/Edit/Edit3D.h b/src/MapEditor/Edit/Edit3D.h index 53a17c85c..94f7ed7ba 100644 --- a/src/MapEditor/Edit/Edit3D.h +++ b/src/MapEditor/Edit/Edit3D.h @@ -1,14 +1,22 @@ #pragma once -#include "MapEditor/MapEditor.h" -#include "SLADEMap/MapObject/MapThing.h" - +// Forward declarations namespace slade { -class MapEditContext; +class MapThing; class MapSide; class UndoManager; +namespace mapeditor +{ + enum class ItemType; + struct Item; + class MapEditContext; +} // namespace mapeditor +} // namespace slade + +namespace slade::mapeditor +{ class Edit3D { public: @@ -41,11 +49,11 @@ class Edit3D link_offset_ = offsets; } - void selectAdjacent(mapeditor::Item item) const; + void selectAdjacent(Item item) const; void changeSectorLight(int amount) const; void changeOffset(int amount, bool x) const; void changeSectorHeight(int amount) const; - void autoAlignX(mapeditor::Item start) const; + void autoAlignX(Item start) const; void resetOffsets() const; void toggleUnpegged(bool lower) const; void copy(CopyType type); @@ -59,26 +67,21 @@ class Edit3D void deleteTexture() const; private: - MapEditContext& context_; + MapEditContext* context_ = nullptr; unique_ptr undo_manager_; - bool link_light_; - bool link_offset_; + bool link_light_ = false; + bool link_offset_ = false; string copy_texture_; - MapThing copy_thing_; + unique_ptr copy_thing_; - vector getAdjacent(mapeditor::Item item) const; + vector getAdjacent(Item item) const; // Helper for selectAdjacent - static bool wallMatches(MapSide* side, mapeditor::ItemType part, string_view tex); - void getAdjacentWalls(mapeditor::Item item, vector& list) const; - void getAdjacentFlats(mapeditor::Item item, vector& list) const; + static bool wallMatches(const MapSide* side, ItemType part, string_view tex); + void getAdjacentWalls(Item item, vector& list) const; + void getAdjacentFlats(Item item, vector& list) const; - // Helper for autoAlignX3d - static void doAlignX( - MapSide* side, - int offset, - string_view tex, - vector& walls_done, - int tex_width); + // Helper for autoAlignX + static void doAlignX(MapSide* side, int offset, string_view tex, vector& walls_done, int tex_width); }; -} // namespace slade +} // namespace slade::mapeditor diff --git a/src/MapEditor/Edit/Input.cpp b/src/MapEditor/Edit/Input.cpp index ab051701d..3070aaf0b 100644 --- a/src/MapEditor/Edit/Input.cpp +++ b/src/MapEditor/Edit/Input.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -32,13 +32,25 @@ #include "Main.h" #include "Input.h" #include "App.h" +#include "Edit2D.h" +#include "Edit3D.h" #include "General/Clipboard.h" #include "General/KeyBind.h" #include "General/UI.h" +#include "LineDraw.h" #include "MapEditor/MapEditContext.h" +#include "MapEditor/MapEditor.h" +#include "MapEditor/Renderer/MCAnimations.h" +#include "MapEditor/Renderer/MapRenderer2D.h" +#include "MapEditor/Renderer/MapRenderer3D.h" #include "MapEditor/Renderer/Overlays/MCOverlay.h" +#include "MapEditor/Renderer/Renderer.h" #include "MapEditor/UI/MapEditorWindow.h" #include "MapEditor/UI/ObjectEditPanel.h" +#include "MoveObjects.h" +#include "ObjectEdit.h" +#include "OpenGL/View.h" +#include "SLADEMap/MapObject/MapThing.h" using namespace slade; using namespace mapeditor; @@ -78,7 +90,7 @@ EXTERN_CVAR(Bool, info_overlay_3d) // ----------------------------------------------------------------------------- // Input class constructor // ----------------------------------------------------------------------------- -Input::Input(MapEditContext& context) : context_{ context } {} +Input::Input(MapEditContext& context) : context_{ &context } {} // ----------------------------------------------------------------------------- // Handles mouse movement to [new_x],[new_y] on the map editor view @@ -86,40 +98,40 @@ Input::Input(MapEditContext& context) : context_{ context } {} bool Input::mouseMove(int new_x, int new_y) { // Check if a full screen overlay is active - if (context_.overlayActive()) + if (context_->overlayActive()) { - context_.currentOverlay()->mouseMotion(new_x, new_y); + context_->currentOverlay()->mouseMotion(new_x, new_y); return false; } // Panning if (panning_) - context_.renderer().pan(mouse_pos_.x - new_x, -(mouse_pos_.y - new_y), true); + context_->renderer().pan(mouse_pos_.x - new_x, -(mouse_pos_.y - new_y), true); // Update mouse variables mouse_pos_ = { new_x, new_y }; - mouse_pos_map_ = context_.renderer().view().canvasPos(mouse_pos_); + mouse_pos_map_ = context_->renderer().view().canvasPos(mouse_pos_); // Update coordinates on status bar - double mx = context_.snapToGrid(mouse_pos_map_.x, false); - double my = context_.snapToGrid(mouse_pos_map_.y, false); + double mx = context_->snapToGrid(mouse_pos_map_.x, false); + double my = context_->snapToGrid(mouse_pos_map_.y, false); string status_text; - if (context_.mapDesc().format == MapFormat::UDMF) + if (context_->mapDesc().format == MapFormat::UDMF) status_text = fmt::format("Position: ({:1.3f}, {:1.3f})", mx, my); else - status_text = fmt::format("Position: ({}, {})", (int)mx, (int)my); + status_text = fmt::format("Position: ({}, {})", static_cast(mx), static_cast(my)); mapeditor::setStatusText(status_text, 3); // Object edit - auto edit_state = context_.objectEdit().state(); + auto edit_state = context_->objectEdit().state(); if (mouse_state_ == MouseState::ObjectEdit) { // Do dragging if left mouse is down if (mouse_button_down_[Left] && edit_state != ObjectEdit::State::None) { - auto& group = context_.objectEdit().group(); + auto& group = context_->objectEdit().group(); - if (context_.objectEdit().rotating()) + if (context_->objectEdit().rotating()) { // Rotate group.doRotate(mouse_down_pos_map_, mouse_pos_map_, !shift_down_); @@ -134,8 +146,8 @@ bool Input::mouseMove(int new_x, int new_y) // Snap to grid if shift not held down if (!shift_down_) { - xoff = context_.snapToGrid(xoff); - yoff = context_.snapToGrid(yoff); + xoff = context_->snapToGrid(xoff); + yoff = context_->snapToGrid(yoff); } if (edit_state == ObjectEdit::State::Move) @@ -150,16 +162,16 @@ bool Input::mouseMove(int new_x, int new_y) group.doScale( xoff, yoff, - context_.objectEdit().stateLeft(false), - context_.objectEdit().stateTop(false), - context_.objectEdit().stateRight(false), - context_.objectEdit().stateBottom(false)); + context_->objectEdit().stateLeft(false), + context_->objectEdit().stateTop(false), + context_->objectEdit().stateRight(false), + context_->objectEdit().stateBottom(false)); mapeditor::window()->objectEditPanel()->update(&group); } } } else - context_.objectEdit().determineState(); + context_->objectEdit().determineState(); return false; } @@ -178,17 +190,17 @@ bool Input::mouseMove(int new_x, int new_y) { mouse_state_ = MouseState::Move; mouse_drag_ = DragType::None; - context_.moveObjects().begin(mouse_down_pos_map_); - context_.renderer().renderer2D().forceUpdate(); + context_->moveObjects().begin(mouse_down_pos_map_); + context_->renderer().renderer2D().forceUpdate(); } // Check if we are in thing quick angle state if (mouse_state_ == MouseState::ThingAngle) - context_.edit2D().thingQuickAngle(mouse_pos_map_); + context_->edit2D().thingQuickAngle(mouse_pos_map_); // Update shape drawing if needed - if (mouse_state_ == MouseState::LineDraw && context_.lineDraw().state() == LineDraw::State::ShapeEdge) - context_.lineDraw().updateShape(mouse_pos_map_); + if (mouse_state_ == MouseState::LineDraw && context_->lineDraw().state() == LineDraw::State::ShapeEdge) + context_->lineDraw().updateShape(mouse_pos_map_); return true; } @@ -201,7 +213,7 @@ bool Input::mouseDown(MouseButton button, bool double_click) { // Update hilight if (mouse_state_ == MouseState::Normal) - context_.selection().updateHilight(mouse_pos_map_, context_.renderer().view().scale()); + context_->selection().updateHilight(mouse_pos_map_, context_->renderer().view().scale()); // Update mouse variables mouse_down_pos_ = mouse_pos_; @@ -210,15 +222,15 @@ bool Input::mouseDown(MouseButton button, bool double_click) mouse_drag_ = DragType::None; // Check if a full screen overlay is active - if (context_.overlayActive()) + if (context_->overlayActive()) { // Left click if (button == Left) - context_.currentOverlay()->mouseLeftClick(); + context_->currentOverlay()->mouseLeftClick(); // Right click else if (button == Right) - context_.currentOverlay()->mouseRightClick(); + context_->currentOverlay()->mouseRightClick(); return false; } @@ -227,20 +239,20 @@ bool Input::mouseDown(MouseButton button, bool double_click) if (button == Left) { // 3d mode - if (context_.editMode() == Mode::Visual) + if (context_->editMode() == Mode::Visual) { // If the mouse is unlocked, lock the mouse - if (!context_.mouseLocked()) - context_.lockMouse(true); + if (!context_->mouseLocked()) + context_->lockMouse(true); else { // Shift down, select all matching adjacent structures if (shift_down_) - context_.edit3D().selectAdjacent(context_.hilightItem()); + context_->edit3D().selectAdjacent(context_->hilightItem()); // Otherwise toggle selection else - context_.selection().toggleCurrent(); + context_->selection().toggleCurrent(); } return false; @@ -255,9 +267,9 @@ bool Input::mouseDown(MouseButton button, bool double_click) nearest_vertex = true; // Line drawing - if (context_.lineDraw().state() == LineDraw::State::Line) + if (context_->lineDraw().state() == LineDraw::State::Line) { - if (context_.lineDraw().addPoint(mouse_down_pos_map_, nearest_vertex)) + if (context_->lineDraw().addPoint(mouse_down_pos_map_, nearest_vertex)) { // If line drawing finished, revert to normal state mouse_state_ = MouseState::Normal; @@ -267,16 +279,16 @@ bool Input::mouseDown(MouseButton button, bool double_click) // Shape drawing else { - if (context_.lineDraw().state() == LineDraw::State::ShapeOrigin) + if (context_->lineDraw().state() == LineDraw::State::ShapeOrigin) { // Set shape origin - context_.lineDraw().setShapeOrigin(mouse_down_pos_map_, nearest_vertex); - context_.lineDraw().setState(LineDraw::State::ShapeEdge); + context_->lineDraw().setShapeOrigin(mouse_down_pos_map_, nearest_vertex); + context_->lineDraw().setState(LineDraw::State::ShapeEdge); } else { // Finish shape draw - context_.lineDraw().end(true); + context_->lineDraw().end(true); mapeditor::window()->showShapeDrawPanel(false); mouse_state_ = MouseState::Normal; } @@ -286,7 +298,7 @@ bool Input::mouseDown(MouseButton button, bool double_click) // Paste state, accept paste else if (mouse_state_ == MouseState::Paste) { - context_.edit2D().paste(mouse_pos_map_); + context_->edit2D().paste(mouse_pos_map_); if (!shift_down_) mouse_state_ = MouseState::Normal; } @@ -294,7 +306,7 @@ bool Input::mouseDown(MouseButton button, bool double_click) // Sector tagging state else if (mouse_state_ == MouseState::TagSectors) { - context_.tagSectorAt(mouse_pos_map_); + context_->tagSectorAt(mouse_pos_map_); } else if (mouse_state_ == MouseState::Normal) @@ -302,16 +314,16 @@ bool Input::mouseDown(MouseButton button, bool double_click) // Double click to edit the current selection if (double_click && property_edit_dclick) { - context_.edit2D().editObjectProperties(); - if (context_.selection().size() == 1) - context_.selection().clear(); + context_->edit2D().editObjectProperties(); + if (context_->selection().size() == 1) + context_->selection().clear(); } // Begin box selection if shift is held down, otherwise toggle selection on hilighted object else if (shift_down_) mouse_state_ = MouseState::Selection; else { - if (!context_.selection().toggleCurrent(selection_clear_click)) + if (!context_->selection().toggleCurrent(selection_clear_click)) mouse_drag_ = DragType::Selection; } } @@ -321,17 +333,17 @@ bool Input::mouseDown(MouseButton button, bool double_click) else if (button == Right) { // 3d mode - if (context_.editMode() == Mode::Visual) + if (context_->editMode() == Mode::Visual) { // Get selection or hilight - auto sel = context_.selection().selectionOrHilight(); + auto sel = context_->selection().selectionOrHilight(); if (!sel.empty()) { // Check type - if (sel[0].type == mapeditor::ItemType::Thing) - context_.edit2D().changeThingType(); + if (sel[0].type == ItemType::Thing) + context_->edit2D().changeThingType(); else - context_.edit3D().changeTexture(); + context_->edit3D().changeTexture(); } } @@ -339,14 +351,14 @@ bool Input::mouseDown(MouseButton button, bool double_click) else if (mouse_state_ == MouseState::LineDraw) { // Line drawing - if (context_.lineDraw().state() == LineDraw::State::Line) - context_.lineDraw().removePoint(); + if (context_->lineDraw().state() == LineDraw::State::Line) + context_->lineDraw().removePoint(); // Shape drawing - else if (context_.lineDraw().state() == LineDraw::State::ShapeEdge) + else if (context_->lineDraw().state() == LineDraw::State::ShapeEdge) { - context_.lineDraw().end(false); - context_.lineDraw().setState(LineDraw::State::ShapeOrigin); + context_->lineDraw().end(false); + context_->lineDraw().setState(LineDraw::State::ShapeOrigin); } } @@ -354,7 +366,7 @@ bool Input::mouseDown(MouseButton button, bool double_click) else if (mouse_state_ == MouseState::Normal) { // Begin move if something is selected/hilighted - if (context_.selection().hasHilightOrSelection()) + if (context_->selection().hasHilightOrSelection()) mouse_drag_ = DragType::Move; } } @@ -375,7 +387,7 @@ bool Input::mouseUp(MouseButton button) mouse_button_down_[button] = false; // Check if a full screen overlay is active - if (context_.overlayActive()) + if (context_->overlayActive()) return false; // Left button @@ -390,7 +402,7 @@ bool Input::mouseUp(MouseButton button) mouse_state_ = MouseState::Normal; // Select - context_.selection().selectWithin( + context_->selection().selectWithin( { min(mouse_down_pos_map_.x, mouse_pos_map_.x), min(mouse_down_pos_map_.y, mouse_pos_map_.y), max(mouse_down_pos_map_.x, mouse_pos_map_.x), @@ -398,13 +410,13 @@ bool Input::mouseUp(MouseButton button) shift_down_); // Begin selection box fade animation - context_.renderer().addAnimation( + context_->renderer().addAnimation( std::make_unique(app::runTimer(), mouse_down_pos_map_, mouse_pos_map_)); } // If we're in object edit mode if (mouse_state_ == MouseState::ObjectEdit) - context_.objectEdit().group().resetPositions(); + context_->objectEdit().group().resetPositions(); } // Right button @@ -414,9 +426,9 @@ bool Input::mouseUp(MouseButton button) if (mouse_state_ == MouseState::Move) { - context_.moveObjects().end(); + context_->moveObjects().end(); mouse_state_ = MouseState::Normal; - context_.renderer().renderer2D().forceUpdate(); + context_->renderer().renderer2D().forceUpdate(); } // Paste state, cancel paste @@ -446,8 +458,8 @@ void Input::mouseWheel(bool up, double amount) KeyBind::keyPressed(Keypress("mwheelup", alt_down_, ctrl_down_, shift_down_)); // Send to overlay if active - if (context_.overlayActive()) - context_.currentOverlay()->keyDown("mwheelup"); + if (context_->overlayActive()) + context_->currentOverlay()->keyDown("mwheelup"); KeyBind::keyReleased("mwheelup"); } @@ -456,8 +468,8 @@ void Input::mouseWheel(bool up, double amount) KeyBind::keyPressed(Keypress("mwheeldown", alt_down_, ctrl_down_, shift_down_)); // Send to overlay if active - if (context_.overlayActive()) - context_.currentOverlay()->keyDown("mwheeldown"); + if (context_->overlayActive()) + context_->currentOverlay()->keyDown("mwheeldown"); KeyBind::keyReleased("mwheeldown"); } @@ -472,7 +484,7 @@ void Input::mouseLeave() if (panning_) { panning_ = false; - context_.setCursor(ui::MouseCursor::Normal); + context_->setCursor(ui::MouseCursor::Normal); } } @@ -490,8 +502,8 @@ void Input::updateKeyModifiersWx(int modifiers) bool Input::keyDown(string_view key) const { // Send to overlay if active - if (context_.overlayActive()) - context_.currentOverlay()->keyDown(key); + if (context_->overlayActive()) + context_->currentOverlay()->keyDown(key); // Let keybind system handle it return KeyBind::keyPressed({ key, alt_down_, ctrl_down_, shift_down_ }); @@ -512,22 +524,22 @@ bool Input::keyUp(string_view key) const void Input::onKeyBindPress(string_view name) { // Check if an overlay is active - if (context_.overlayActive()) + if (context_->overlayActive()) { // Accept edit if (name == "map_edit_accept") { - context_.closeCurrentOverlay(); - context_.renderer().renderer3D().enableHilight(true); - context_.renderer().renderer3D().enableSelection(true); + context_->closeCurrentOverlay(); + context_->renderer().renderer3D().enableHilight(true); + context_->renderer().renderer3D().enableSelection(true); } // Cancel edit else if (name == "map_edit_cancel") { - context_.closeCurrentOverlay(true); - context_.renderer().renderer3D().enableHilight(true); - context_.renderer().renderer3D().enableSelection(true); + context_->closeCurrentOverlay(true); + context_->renderer().renderer3D().enableHilight(true); + context_->renderer().renderer3D().enableSelection(true); } // Nothing else @@ -537,21 +549,21 @@ void Input::onKeyBindPress(string_view name) // Toggle 3d mode if (name == "map_toggle_3d") { - if (context_.editMode() == Mode::Visual) - context_.setPrevEditMode(); + if (context_->editMode() == Mode::Visual) + context_->setPrevEditMode(); else - context_.setEditMode(Mode::Visual); + context_->setEditMode(Mode::Visual); } // Send to edit context first if (mouse_state_ == MouseState::Normal) { - if (context_.handleKeyBind(name, mouse_pos_map_)) + if (context_->handleKeyBind(name, mouse_pos_map_)) return; } // Handle keybinds depending on mode - if (context_.editMode() == Mode::Visual) + if (context_->editMode() == Mode::Visual) handleKeyBind3d(name); else { @@ -569,15 +581,15 @@ void Input::onKeyBindRelease(string_view name) { panning_ = false; if (mouse_state_ == MouseState::Normal) - context_.selection().updateHilight(mouse_pos_map_, context_.renderer().view().scale()); - context_.setCursor(ui::MouseCursor::Normal); + context_->selection().updateHilight(mouse_pos_map_, context_->renderer().view().scale()); + context_->setCursor(ui::MouseCursor::Normal); } else if (name == "me2d_thing_quick_angle" && mouse_state_ == MouseState::ThingAngle) { mouse_state_ = MouseState::Normal; - context_.endUndoRecord(true); - context_.selection().updateHilight(mouse_pos_map_, context_.renderer().view().scale()); + context_->endUndoRecord(true); + context_->selection().updateHilight(mouse_pos_map_, context_->renderer().view().scale()); } } @@ -589,43 +601,43 @@ void Input::handleKeyBind2dView(string_view name) { // Pan left if (name == "me2d_left") - context_.renderer().pan(-128, 0, true); + context_->renderer().pan(-128, 0, true); // Pan right else if (name == "me2d_right") - context_.renderer().pan(128, 0, true); + context_->renderer().pan(128, 0, true); // Pan up else if (name == "me2d_up") - context_.renderer().pan(0, 128, true); + context_->renderer().pan(0, 128, true); // Pan down else if (name == "me2d_down") - context_.renderer().pan(0, -128, true); + context_->renderer().pan(0, -128, true); // Zoom out else if (name == "me2d_zoom_out") - context_.renderer().zoom(0.8); + context_->renderer().zoom(0.8); // Zoom in else if (name == "me2d_zoom_in") - context_.renderer().zoom(1.25); + context_->renderer().zoom(1.25); // Zoom out (follow mouse) if (name == "me2d_zoom_out_m") - context_.renderer().zoom(1.0 - (0.2 * mouse_wheel_speed_), true); + context_->renderer().zoom(1.0 - (0.2 * mouse_wheel_speed_), true); // Zoom in (follow mouse) else if (name == "me2d_zoom_in_m") - context_.renderer().zoom(1.0 + (0.25 * mouse_wheel_speed_), true); + context_->renderer().zoom(1.0 + (0.25 * mouse_wheel_speed_), true); // Zoom in (show object) else if (name == "me2d_show_object") - context_.showItem(-1); + context_->showItem(-1); // Zoom out (full map) else if (name == "me2d_show_all") - context_.renderer().viewFitToMap(); + context_->renderer().viewFitToMap(); // Pan view else if (name == "me2d_pan_view") @@ -633,17 +645,17 @@ void Input::handleKeyBind2dView(string_view name) mouse_down_pos_ = mouse_pos_; panning_ = true; if (mouse_state_ == MouseState::Normal) - context_.selection().clearHilight(); - context_.setCursor(ui::MouseCursor::Move); + context_->selection().clearHilight(); + context_->setCursor(ui::MouseCursor::Move); } // Increment grid else if (name == "me2d_grid_inc") - context_.incrementGrid(); + context_->incrementGrid(); // Decrement grid else if (name == "me2d_grid_dec") - context_.decrementGrid(); + context_->decrementGrid(); } // ----------------------------------------------------------------------------- @@ -658,7 +670,7 @@ void Input::handleKeyBind2d(string_view name) if (name == "map_edit_accept") { mouse_state_ = MouseState::Normal; - context_.lineDraw().end(); + context_->lineDraw().end(); mapeditor::window()->showShapeDrawPanel(false); } @@ -666,7 +678,7 @@ void Input::handleKeyBind2d(string_view name) else if (name == "map_edit_cancel") { mouse_state_ = MouseState::Normal; - context_.lineDraw().end(false); + context_->lineDraw().end(false); mapeditor::window()->showShapeDrawPanel(false); } } @@ -678,7 +690,7 @@ void Input::handleKeyBind2d(string_view name) if (name == "map_edit_accept") { mouse_state_ = MouseState::Normal; - context_.edit2D().paste(mouse_pos_map_); + context_->edit2D().paste(mouse_pos_map_); } // Cancel paste @@ -693,14 +705,14 @@ void Input::handleKeyBind2d(string_view name) if (name == "map_edit_accept") { mouse_state_ = MouseState::Normal; - context_.endTagEdit(true); + context_->endTagEdit(true); } // Cancel else if (name == "map_edit_cancel") { mouse_state_ = MouseState::Normal; - context_.endTagEdit(false); + context_->endTagEdit(false); } } else if (mouse_state_ == MouseState::TagThings) @@ -709,14 +721,14 @@ void Input::handleKeyBind2d(string_view name) if (name == "map_edit_accept") { mouse_state_ = MouseState::Normal; - context_.endTagEdit(true); + context_->endTagEdit(true); } // Cancel else if (name == "map_edit_cancel") { mouse_state_ = MouseState::Normal; - context_.endTagEdit(false); + context_->endTagEdit(false); } } @@ -726,25 +738,25 @@ void Input::handleKeyBind2d(string_view name) // Move toggle if (name == "me2d_move") { - context_.moveObjects().end(); + context_->moveObjects().end(); mouse_state_ = MouseState::Normal; - context_.renderer().renderer2D().forceUpdate(); + context_->renderer().renderer2D().forceUpdate(); } // Accept move else if (name == "map_edit_accept") { - context_.moveObjects().end(); + context_->moveObjects().end(); mouse_state_ = MouseState::Normal; - context_.renderer().renderer2D().forceUpdate(); + context_->renderer().renderer2D().forceUpdate(); } // Cancel move else if (name == "map_edit_cancel") { - context_.moveObjects().end(false); + context_->moveObjects().end(false); mouse_state_ = MouseState::Normal; - context_.renderer().renderer2D().forceUpdate(); + context_->renderer().renderer2D().forceUpdate(); } } @@ -754,19 +766,19 @@ void Input::handleKeyBind2d(string_view name) // Accept edit if (name == "map_edit_accept") { - context_.objectEdit().end(true); + context_->objectEdit().end(true); mouse_state_ = MouseState::Normal; - context_.renderer().renderer2D().forceUpdate(); - context_.setCursor(ui::MouseCursor::Normal); + context_->renderer().renderer2D().forceUpdate(); + context_->setCursor(ui::MouseCursor::Normal); } // Cancel edit else if (name == "map_edit_cancel" || name == "me2d_begin_object_edit") { - context_.objectEdit().end(false); + context_->objectEdit().end(false); mouse_state_ = MouseState::Normal; - context_.renderer().renderer2D().forceUpdate(); - context_.setCursor(ui::MouseCursor::Normal); + context_->renderer().renderer2D().forceUpdate(); + context_->setCursor(ui::MouseCursor::Normal); } } @@ -777,23 +789,23 @@ void Input::handleKeyBind2d(string_view name) // Vertices mode if (name == "me2d_mode_vertices") - context_.setEditMode(Mode::Vertices); + context_->setEditMode(Mode::Vertices); // Lines mode else if (name == "me2d_mode_lines") - context_.setEditMode(Mode::Lines); + context_->setEditMode(Mode::Lines); // Sectors mode else if (name == "me2d_mode_sectors") - context_.setEditMode(Mode::Sectors); + context_->setEditMode(Mode::Sectors); // Things mode else if (name == "me2d_mode_things") - context_.setEditMode(Mode::Things); + context_->setEditMode(Mode::Things); // 3d mode else if (name == "me2d_mode_3d") - context_.setEditMode(Mode::Visual); + context_->setEditMode(Mode::Visual); // Cycle flat type if (name == "me2d_flat_type") @@ -805,9 +817,9 @@ void Input::handleKeyBind2d(string_view name) // Editor message and toolbar update switch (flat_drawtype) { - case 0: SAction::fromId("mapw_flat_none")->setChecked(); break; - case 1: SAction::fromId("mapw_flat_untextured")->setChecked(); break; - case 2: SAction::fromId("mapw_flat_textured")->setChecked(); break; + case 0: SAction::fromId("mapw_flat_none")->setChecked(); break; + case 1: SAction::fromId("mapw_flat_untextured")->setChecked(); break; + case 2: SAction::fromId("mapw_flat_textured")->setChecked(); break; default: break; } @@ -817,53 +829,53 @@ void Input::handleKeyBind2d(string_view name) // Move items (toggle) else if (name == "me2d_move") { - if (context_.moveObjects().begin(mouse_pos_map_)) + if (context_->moveObjects().begin(mouse_pos_map_)) { mouse_state_ = MouseState::Move; - context_.renderer().renderer2D().forceUpdate(); + context_->renderer().renderer2D().forceUpdate(); } } // Edit items else if (name == "me2d_begin_object_edit") - context_.objectEdit().begin(); + context_->objectEdit().begin(); // Split line else if (name == "me2d_split_line") - context_.edit2D().splitLine(mouse_pos_map_.x, mouse_pos_map_.y, 16 / context_.renderer().view().scale()); + context_->edit2D().splitLine(mouse_pos_map_.x, mouse_pos_map_.y, 16 / context_->renderer().view().scale()); // Begin line drawing else if (name == "me2d_begin_linedraw") - context_.lineDraw().begin(); + context_->lineDraw().begin(); // Begin shape drawing else if (name == "me2d_begin_shapedraw") - context_.lineDraw().begin(true); + context_->lineDraw().begin(true); // Create object else if (name == "me2d_create_object") { // If in lines mode, begin line drawing - if (context_.editMode() == Mode::Lines) + if (context_->editMode() == Mode::Lines) { - context_.lineDraw().setState(LineDraw::State::Line); + context_->lineDraw().setState(LineDraw::State::Line); mouse_state_ = MouseState::LineDraw; } else - context_.edit2D().createObject(mouse_pos_map_); + context_->edit2D().createObject(mouse_pos_map_); } // Delete object else if (name == "me2d_delete_object") - context_.edit2D().deleteObject(); + context_->edit2D().deleteObject(); // Copy properties else if (name == "me2d_copy_properties") - context_.edit2D().copyProperties(); + context_->edit2D().copyProperties(); // Paste properties else if (name == "me2d_paste_properties") - context_.edit2D().pasteProperties(); + context_->edit2D().pasteProperties(); // Paste object(s) else if (name == "paste") @@ -891,70 +903,70 @@ void Input::handleKeyBind2d(string_view name) map_show_selection_numbers = !map_show_selection_numbers; if (map_show_selection_numbers) - context_.addEditorMessage("Selection numbers enabled"); + context_->addEditorMessage("Selection numbers enabled"); else - context_.addEditorMessage("Selection numbers disabled"); + context_->addEditorMessage("Selection numbers disabled"); } // Mirror else if (name == "me2d_mirror_x") - context_.edit2D().mirror(true); + context_->edit2D().mirror(true); else if (name == "me2d_mirror_y") - context_.edit2D().mirror(false); + context_->edit2D().mirror(false); // Object Properties else if (name == "me2d_object_properties") - context_.edit2D().editObjectProperties(); + context_->edit2D().editObjectProperties(); // --- Lines edit mode --- - if (context_.editMode() == Mode::Lines) + if (context_->editMode() == Mode::Lines) { // Change line texture if (name == "me2d_line_change_texture") - context_.openLineTextureOverlay(); + context_->openLineTextureOverlay(); // Flip line else if (name == "me2d_line_flip") - context_.edit2D().flipLines(); + context_->edit2D().flipLines(); // Flip line (no sides) else if (name == "me2d_line_flip_nosides") - context_.edit2D().flipLines(false); + context_->edit2D().flipLines(false); // Edit line tags else if (name == "me2d_line_tag_edit") { - if (context_.beginTagEdit() > 0) + if (context_->beginTagEdit() > 0) { mouse_state_ = MouseState::TagSectors; // Setup help text auto key_accept = KeyBind::bind("map_edit_accept").keysAsString(); auto key_cancel = KeyBind::bind("map_edit_cancel").keysAsString(); - context_.setFeatureHelp({ "Tag Edit", - fmt::format("{} = Accept", key_accept), - fmt::format("{} = Cancel", key_cancel), - "Left Click = Toggle tagged sector" }); + context_->setFeatureHelp({ "Tag Edit", + fmt::format("{} = Accept", key_accept), + fmt::format("{} = Cancel", key_cancel), + "Left Click = Toggle tagged sector" }); } } } // --- Things edit mode --- - else if (context_.editMode() == Mode::Things) + else if (context_->editMode() == Mode::Things) { // Change type if (name == "me2d_thing_change_type") - context_.edit2D().changeThingType(); + context_->edit2D().changeThingType(); // Quick angle else if (name == "me2d_thing_quick_angle") { if (mouse_state_ == MouseState::Normal) { - if (context_.selection().hasHilightOrSelection()) - context_.beginUndoRecord("Thing Direction Change", true, false, false); + if (context_->selection().hasHilightOrSelection()) + context_->beginUndoRecord("Thing Direction Change", true, false, false); mouse_state_ = MouseState::ThingAngle; } @@ -963,8 +975,8 @@ void Input::handleKeyBind2d(string_view name) // Rotate Clockwise else if (name == "me2d_thing_rotate_clockwise") { - context_.beginUndoRecord("Rotate Things Clockwise", true, false, false); - auto things = context_.selection().selectedThings(true); + context_->beginUndoRecord("Rotate Things Clockwise", true, false, false); + auto things = context_->selection().selectedThings(true); bool success = false; for (auto& thing : things) { @@ -974,31 +986,31 @@ void Input::handleKeyBind2d(string_view name) thing->setAngle(angle); success = true; } - context_.endUndoRecord(success); + context_->endUndoRecord(success); } // Rotate Counterclockwise else if (name == "me2d_thing_rotate_counterclockwise") { - context_.beginUndoRecord("Rotate Things Counterclockwise", true, false, false); - auto things = context_.selection().selectedThings(true); + context_->beginUndoRecord("Rotate Things Counterclockwise", true, false, false); + auto things = context_->selection().selectedThings(true); bool success = false; for (auto& thing : things) { thing->setAngle((thing->angle() + 45) % 360); success = true; } - context_.endUndoRecord(success); + context_->endUndoRecord(success); } } // --- Sectors edit mode --- - else if (context_.editMode() == Mode::Sectors) + else if (context_->editMode() == Mode::Sectors) { // Change sector texture if (name == "me2d_sector_change_texture") - context_.edit2D().changeSectorTexture(); + context_->edit2D().changeSectorTexture(); } } } @@ -1010,28 +1022,28 @@ void Input::handleKeyBind3d(string_view name) const { // Escape from 3D mode if (name == "map_edit_cancel") - context_.setPrevEditMode(); + context_->setPrevEditMode(); // Toggle fog else if (name == "me3d_toggle_fog") { - bool fog = context_.renderer().renderer3D().fogEnabled(); - context_.renderer().renderer3D().enableFog(!fog); + bool fog = context_->renderer().renderer3D().fogEnabled(); + context_->renderer().renderer3D().enableFog(!fog); if (fog) - context_.addEditorMessage("Fog disabled"); + context_->addEditorMessage("Fog disabled"); else - context_.addEditorMessage("Fog enabled"); + context_->addEditorMessage("Fog enabled"); } // Toggle fullbright else if (name == "me3d_toggle_fullbright") { - bool fb = context_.renderer().renderer3D().fullbrightEnabled(); - context_.renderer().renderer3D().enableFullbright(!fb); + bool fb = context_->renderer().renderer3D().fullbrightEnabled(); + context_->renderer().renderer3D().enableFullbright(!fb); if (fb) - context_.addEditorMessage("Fullbright disabled"); + context_->addEditorMessage("Fullbright disabled"); else - context_.addEditorMessage("Fullbright enabled"); + context_->addEditorMessage("Fullbright enabled"); } // Adjust brightness @@ -1042,7 +1054,7 @@ void Input::handleKeyBind3d(string_view name) const { render_3d_brightness = 1.0; } - context_.addEditorMessage(fmt::format("Brightness set to {:1.1f}", (double)render_3d_brightness)); + context_->addEditorMessage(fmt::format("Brightness set to {:1.1f}", static_cast(render_3d_brightness))); } // Toggle gravity @@ -1050,14 +1062,14 @@ void Input::handleKeyBind3d(string_view name) const { camera_3d_gravity = !camera_3d_gravity; if (!camera_3d_gravity) - context_.addEditorMessage("Gravity disabled"); + context_->addEditorMessage("Gravity disabled"); else - context_.addEditorMessage("Gravity enabled"); + context_->addEditorMessage("Gravity enabled"); } // Release mouse cursor else if (name == "me3d_release_mouse") - context_.lockMouse(false); + context_->lockMouse(false); // Toggle things else if (name == "me3d_toggle_things") @@ -1069,11 +1081,11 @@ void Input::handleKeyBind3d(string_view name) const // Editor message if (render_3d_things == 0) - context_.addEditorMessage("Things disabled"); + context_->addEditorMessage("Things disabled"); else if (render_3d_things == 1) - context_.addEditorMessage("Things enabled: All"); + context_->addEditorMessage("Things enabled: All"); else - context_.addEditorMessage("Things enabled: Decorations only"); + context_->addEditorMessage("Things enabled: Decorations only"); } // Change thing render style @@ -1086,11 +1098,11 @@ void Input::handleKeyBind3d(string_view name) const // Editor message if (render_3d_things_style == 0) - context_.addEditorMessage("Thing render style: Sprites only"); + context_->addEditorMessage("Thing render style: Sprites only"); else if (render_3d_things_style == 1) - context_.addEditorMessage("Thing render style: Sprites + Ground boxes"); + context_->addEditorMessage("Thing render style: Sprites + Ground boxes"); else - context_.addEditorMessage("Thing render style: Sprites + Full boxes"); + context_->addEditorMessage("Thing render style: Sprites + Full boxes"); } // Toggle hilight @@ -1103,11 +1115,11 @@ void Input::handleKeyBind3d(string_view name) const // Editor message if (render_3d_hilight == 0) - context_.addEditorMessage("Hilight disabled"); + context_->addEditorMessage("Hilight disabled"); else if (render_3d_hilight == 1) - context_.addEditorMessage("Hilight enabled: Outline"); + context_->addEditorMessage("Hilight enabled: Outline"); else if (render_3d_hilight == 2) - context_.addEditorMessage("Hilight enabled: Solid"); + context_->addEditorMessage("Hilight enabled: Solid"); } // Toggle info overlay @@ -1116,11 +1128,11 @@ void Input::handleKeyBind3d(string_view name) const // Quick texture else if (name == "me3d_quick_texture") - context_.openQuickTextureOverlay(); + context_->openQuickTextureOverlay(); // Send to map editor else - context_.handleKeyBind(name, mouse_pos_map_); + context_->handleKeyBind(name, mouse_pos_map_); } // ----------------------------------------------------------------------------- @@ -1131,7 +1143,7 @@ bool Input::updateCamera3d(double mult) const // --- Check for held-down keys --- bool moving = false; double speed = shift_down_ ? mult * 8 : mult * 4; - auto& r3d = context_.renderer().renderer3D(); + auto& r3d = context_->renderer().renderer3D(); // Camera forward if (KeyBind::isPressed("me3d_camera_forward")) @@ -1203,11 +1215,11 @@ string Input::mouseButtonKBName(MouseButton button) { switch (button) { - case Left: return "mouse1"; - case Right: return "mouse2"; + case Left: return "mouse1"; + case Right: return "mouse2"; case Middle: return "mouse3"; case Mouse4: return "mouse4"; case Mouse5: return "mouse5"; - default: return fmt::format("mouse{}", static_cast(button)); + default: return fmt::format("mouse{}", static_cast(button)); } } diff --git a/src/MapEditor/Edit/Input.h b/src/MapEditor/Edit/Input.h index 1ffda85bf..2c266bfbd 100644 --- a/src/MapEditor/Edit/Input.h +++ b/src/MapEditor/Edit/Input.h @@ -2,106 +2,107 @@ #include "General/KeyBind.h" -class wxMouseEvent; - #undef None -namespace slade + +// Forward delcarations +class wxMouseEvent; +namespace slade::mapeditor { class MapEditContext; +} -namespace mapeditor +namespace slade::mapeditor +{ +class Input : public KeyBindHandler { - class Input : public KeyBindHandler +public: + enum class MouseState { - public: - enum class MouseState - { - Normal, - Selection, - Move, - ThingAngle, - LineDraw, - ObjectEdit, - Paste, - TagSectors, - TagThings - }; + Normal, + Selection, + Move, + ThingAngle, + LineDraw, + ObjectEdit, + Paste, + TagSectors, + TagThings + }; - enum class DragType - { - None, - Selection, - Move - }; + enum class DragType + { + None, + Selection, + Move + }; - enum MouseButton - { - Left = 0, - Middle, - Right, - Mouse4, - Mouse5 - }; + enum MouseButton + { + Left = 0, + Middle, + Right, + Mouse4, + Mouse5 + }; - Input(MapEditContext& context); + Input(MapEditContext& context); - bool panning() const { return panning_; } - MouseState mouseState() const { return mouse_state_; } - Vec2i mousePos() const { return mouse_pos_; } - Vec2d mousePosMap() const { return mouse_pos_map_; } - Vec2i mouseDownPos() const { return mouse_down_pos_; } - Vec2d mouseDownPosMap() const { return mouse_down_pos_map_; } - bool shiftDown() const { return shift_down_; } - bool ctrlDown() const { return ctrl_down_; } - bool altDown() const { return alt_down_; } + bool panning() const { return panning_; } + MouseState mouseState() const { return mouse_state_; } + Vec2i mousePos() const { return mouse_pos_; } + Vec2d mousePosMap() const { return mouse_pos_map_; } + Vec2i mouseDownPos() const { return mouse_down_pos_; } + Vec2d mouseDownPosMap() const { return mouse_down_pos_map_; } + bool shiftDown() const { return shift_down_; } + bool ctrlDown() const { return ctrl_down_; } + bool altDown() const { return alt_down_; } - // Mouse handling - void setMouseState(MouseState state) { mouse_state_ = state; } - bool mouseMove(int new_x, int new_y); - bool mouseDown(MouseButton button, bool double_click = false); - bool mouseUp(MouseButton button); - void mouseWheel(bool up, double amount); - void mouseLeave(); + // Mouse handling + void setMouseState(MouseState state) { mouse_state_ = state; } + bool mouseMove(int new_x, int new_y); + bool mouseDown(MouseButton button, bool double_click = false); + bool mouseUp(MouseButton button); + void mouseWheel(bool up, double amount); + void mouseLeave(); - // Keyboard handling - void updateKeyModifiers(bool shift, bool ctrl, bool alt) - { - shift_down_ = shift; - ctrl_down_ = ctrl; - alt_down_ = alt; - } - void updateKeyModifiersWx(int modifiers); - bool keyDown(string_view key) const; - bool keyUp(string_view key) const; + // Keyboard handling + void updateKeyModifiers(bool shift, bool ctrl, bool alt) + { + shift_down_ = shift; + ctrl_down_ = ctrl; + alt_down_ = alt; + } + void updateKeyModifiersWx(int modifiers); + bool keyDown(string_view key) const; + bool keyUp(string_view key) const; - // Keybind handling - void onKeyBindPress(string_view name) override; - void onKeyBindRelease(string_view name) override; - void handleKeyBind2dView(string_view name); - void handleKeyBind2d(string_view name); - void handleKeyBind3d(string_view name) const; - bool updateCamera3d(double mult) const; + // Keybind handling + void onKeyBindPress(string_view name) override; + void onKeyBindRelease(string_view name) override; + void handleKeyBind2dView(string_view name); + void handleKeyBind2d(string_view name); + void handleKeyBind3d(string_view name) const; + bool updateCamera3d(double mult) const; - static string mouseButtonKBName(MouseButton button); + static string mouseButtonKBName(MouseButton button); - private: - MapEditContext& context_; +private: + MapEditContext* context_ = nullptr; - // Mouse - MouseState mouse_state_ = MouseState::Normal; - bool mouse_button_down_[5] = { false, false, false, false, false }; - Vec2i mouse_pos_ = { 0, 0 }; - Vec2d mouse_pos_map_ = { 0, 0 }; - Vec2i mouse_down_pos_ = { -1, -1 }; - Vec2d mouse_down_pos_map_ = { -1, -1 }; - DragType mouse_drag_ = DragType::None; - double mouse_wheel_speed_ = 0; - bool panning_ = false; + // Mouse + MouseState mouse_state_ = MouseState::Normal; + bool mouse_button_down_[5] = { false, false, false, false, false }; + Vec2i mouse_pos_ = { 0, 0 }; + Vec2d mouse_pos_map_ = { 0, 0 }; + Vec2i mouse_down_pos_ = { -1, -1 }; + Vec2d mouse_down_pos_map_ = { -1, -1 }; + DragType mouse_drag_ = DragType::None; + double mouse_wheel_speed_ = 0; + bool panning_ = false; - // Keyboard - bool shift_down_ = false; - bool ctrl_down_ = false; - bool alt_down_ = false; - }; -} // namespace mapeditor -} // namespace slade + // Keyboard + bool shift_down_ = false; + bool ctrl_down_ = false; + bool alt_down_ = false; +}; +} // namespace slade::mapeditor diff --git a/src/MapEditor/Edit/LineDraw.cpp b/src/MapEditor/Edit/LineDraw.cpp index 9e8d62434..b0c2901cc 100644 --- a/src/MapEditor/Edit/LineDraw.cpp +++ b/src/MapEditor/Edit/LineDraw.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -32,8 +32,15 @@ #include "Main.h" #include "LineDraw.h" #include "General/KeyBind.h" +#include "Input.h" #include "MapEditor/MapEditContext.h" #include "MapEditor/MapEditor.h" +#include "SLADEMap/MapObject/MapLine.h" +#include "SLADEMap/MapObject/MapSide.h" +#include "SLADEMap/MapObject/MapVertex.h" +#include "SLADEMap/MapObjectList/LineList.h" +#include "SLADEMap/MapObjectList/VertexList.h" +#include "SLADEMap/SLADEMap.h" #include "Utility/MathStuff.h" using namespace slade; @@ -79,16 +86,16 @@ bool LineDraw::addPoint(Vec2d point, bool nearest) // Snap to nearest vertex if necessary if (nearest) { - auto vertex = context_.map().vertices().nearest(point); + auto vertex = context_->map().vertices().nearest(point); if (vertex) point = vertex->position(); } // Otherwise, snap to grid if necessary - else if (context_.gridSnap()) + else if (context_->gridSnap()) { - point.x = context_.snapToGrid(point.x); - point.y = context_.snapToGrid(point.y); + point.x = context_->snapToGrid(point.x); + point.y = context_->snapToGrid(point.y); } // Check if this is the same as the last point @@ -140,16 +147,16 @@ void LineDraw::setShapeOrigin(Vec2d point, bool nearest) // Snap to nearest vertex if necessary if (nearest) { - auto vertex = context_.map().vertices().nearest(point); + auto vertex = context_->map().vertices().nearest(point); if (vertex) point = vertex->position(); } // Otherwise, snap to grid if necessary - else if (context_.gridSnap()) + else if (context_->gridSnap()) { - point.x = context_.snapToGrid(point.x); - point.y = context_.snapToGrid(point.y); + point.x = context_->snapToGrid(point.x); + point.y = context_->snapToGrid(point.y); } draw_origin_ = point; @@ -165,10 +172,10 @@ void LineDraw::updateShape(Vec2d point) draw_points_.clear(); // Snap edge to grid if needed - if (context_.gridSnap()) + if (context_->gridSnap()) { - point.x = context_.snapToGrid(point.x); - point.y = context_.snapToGrid(point.y); + point.x = context_->snapToGrid(point.x); + point.y = context_->snapToGrid(point.y); } // Lock width:height at 1:1 if needed @@ -239,7 +246,7 @@ void LineDraw::updateShape(Vec2d point) // Add point draw_points_.push_back(p); - rot -= (3.1415926535897932384626433832795 * 2) / (double)shapedraw_sides; + rot -= (3.1415926535897932384626433832795 * 2) / static_cast(shapedraw_sides); if (a == 0) start = p; @@ -257,28 +264,28 @@ void LineDraw::begin(bool shape) { // Setup state state_current_ = shape ? State::ShapeOrigin : State::Line; - context_.input().setMouseState(Input::MouseState::LineDraw); + context_->input().setMouseState(Input::MouseState::LineDraw); // Setup help text auto key_accept = KeyBind::bind("map_edit_accept").keysAsString(); auto key_cancel = KeyBind::bind("map_edit_cancel").keysAsString(); if (shape) { - context_.setFeatureHelp({ "Shape Drawing", - fmt::format("{} = Accept", key_accept), - fmt::format("{} = Cancel", key_cancel), - "Left Click = Draw point", - "Right Click = Undo previous point" }); + context_->setFeatureHelp({ "Shape Drawing", + fmt::format("{} = Accept", key_accept), + fmt::format("{} = Cancel", key_cancel), + "Left Click = Draw point", + "Right Click = Undo previous point" }); mapeditor::showShapeDrawPanel(true); } else { - context_.setFeatureHelp({ "Line Drawing", - fmt::format("{} = Accept", key_accept), - fmt::format("{} = Cancel", key_cancel), - "Left Click = Draw point", - "Right Click = Undo previous point", - "Shift = Snap to nearest vertex" }); + context_->setFeatureHelp({ "Line Drawing", + fmt::format("{} = Accept", key_accept), + fmt::format("{} = Cancel", key_cancel), + "Left Click = Draw point", + "Right Click = Undo previous point", + "Shift = Snap to nearest vertex" }); } } @@ -294,15 +301,15 @@ void LineDraw::end(bool apply) if (!apply || draw_points_.size() <= 1) { draw_points_.clear(); - context_.setFeatureHelp({}); + context_->setFeatureHelp({}); return; } // Begin undo level - context_.beginUndoRecord("Line Draw"); + context_->beginUndoRecord("Line Draw"); // Add extra points if any lines overlap existing vertices - auto& map = context_.map(); + auto& map = context_->map(); for (unsigned a = 0; a < draw_points_.size() - 1; a++) { auto v = map.vertices().firstCrossed({ draw_points_[a], draw_points_[a + 1] }); @@ -365,11 +372,11 @@ void LineDraw::end(bool apply) map.correctSectors(invalid_lines); // End recording undo level - context_.endUndoRecord(true); + context_->endUndoRecord(true); // Clear draw points draw_points_.clear(); // Clear feature help text - context_.setFeatureHelp({}); + context_->setFeatureHelp({}); } diff --git a/src/MapEditor/Edit/LineDraw.h b/src/MapEditor/Edit/LineDraw.h index 8bb262fac..299a94dd6 100644 --- a/src/MapEditor/Edit/LineDraw.h +++ b/src/MapEditor/Edit/LineDraw.h @@ -1,6 +1,6 @@ #pragma once -namespace slade +namespace slade::mapeditor { class MapEditContext; @@ -14,7 +14,7 @@ class LineDraw ShapeEdge }; - explicit LineDraw(MapEditContext& context) : context_(context) {} + explicit LineDraw(MapEditContext& context) : context_(&context) {} State state() const { return state_current_; } unsigned nPoints() const { return draw_points_.size(); } @@ -31,9 +31,10 @@ class LineDraw void end(bool apply = true); private: - vector draw_points_; - Vec2d draw_origin_; - MapEditContext& context_; - State state_current_ = State::Line; + MapEditContext* context_; + + vector draw_points_; + Vec2d draw_origin_; + State state_current_ = State::Line; }; -} // namespace slade +} // namespace slade::mapeditor diff --git a/src/MapEditor/Edit/MoveObjects.cpp b/src/MapEditor/Edit/MoveObjects.cpp index e40634afa..18f383111 100644 --- a/src/MapEditor/Edit/MoveObjects.cpp +++ b/src/MapEditor/Edit/MoveObjects.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -33,9 +33,20 @@ #include "Main.h" #include "MoveObjects.h" #include "MapEditor/MapEditContext.h" +#include "MapEditor/MapEditor.h" #include "MapEditor/UndoSteps.h" +#include "SLADEMap/MapObject/MapLine.h" +#include "SLADEMap/MapObject/MapSector.h" +#include "SLADEMap/MapObject/MapSide.h" +#include "SLADEMap/MapObject/MapThing.h" +#include "SLADEMap/MapObject/MapVertex.h" +#include "SLADEMap/MapObjectList/LineList.h" +#include "SLADEMap/MapObjectList/SectorList.h" +#include "SLADEMap/MapObjectList/ThingList.h" +#include "SLADEMap/SLADEMap.h" using namespace slade; +using namespace mapeditor; // ----------------------------------------------------------------------------- @@ -57,35 +68,35 @@ CVAR(Bool, selection_clear_move, true, CVar::Flag::Save) // ----------------------------------------------------------------------------- // MoveObjects class constructor // ----------------------------------------------------------------------------- -MoveObjects::MoveObjects(MapEditContext& context) : context_{ context } {} +MoveObjects::MoveObjects(MapEditContext& context) : context_{ &context } {} // ----------------------------------------------------------------------------- // Begins a move operation, starting from [mouse_pos] // ----------------------------------------------------------------------------- -bool MoveObjects::begin(Vec2d mouse_pos) +bool MoveObjects::begin(const Vec2d& mouse_pos) { using mapeditor::Mode; // Check if we have any selection or hilight - if (!context_.selection().hasHilightOrSelection()) + if (!context_->selection().hasHilightOrSelection()) return false; // Begin move operation origin_ = mouse_pos; - items_ = context_.selection().selectionOrHilight(); + items_ = context_->selection().selectionOrHilight(); // Get list of vertices being moved (if any) vector move_verts; - if (context_.editMode() != Mode::Things) + if (context_->editMode() != Mode::Things) { for (auto& item : items_) { // Vertex - if (auto vertex = item.asVertex(context_.map())) + if (auto vertex = item.asVertex(context_->map())) move_verts.push_back(vertex); // Line - else if (auto line = item.asLine(context_.map())) + else if (auto line = item.asLine(context_->map())) { // Duplicate vertices shouldn't matter here move_verts.push_back(line->v1()); @@ -93,17 +104,17 @@ bool MoveObjects::begin(Vec2d mouse_pos) } // Sector - else if (auto sector = item.asSector(context_.map())) + else if (auto sector = item.asSector(context_->map())) sector->putVertices(move_verts); } } // Filter out map objects being moved - if (context_.editMode() == Mode::Things) + if (context_->editMode() == Mode::Things) { // Filter moving things for (auto& item : items_) - if (auto thing = item.asThing(context_.map())) + if (auto thing = item.asThing(context_->map())) thing->filter(true); } else @@ -122,20 +133,20 @@ bool MoveObjects::begin(Vec2d mouse_pos) // ----------------------------------------------------------------------------- // Updates the current move operation (moving from start to [mouse_pos]) // ----------------------------------------------------------------------------- -void MoveObjects::update(Vec2d mouse_pos) +void MoveObjects::update(const Vec2d& mouse_pos) { using mapeditor::Mode; // Special case: single vertex or thing - if (items_.size() == 1 && (context_.editMode() == Mode::Vertices || context_.editMode() == Mode::Things)) + if (items_.size() == 1 && (context_->editMode() == Mode::Vertices || context_->editMode() == Mode::Things)) { // Get new position - Vec2d np{ context_.snapToGrid(mouse_pos.x, false), context_.snapToGrid(mouse_pos.y, false) }; + Vec2d np{ context_->snapToGrid(mouse_pos.x, false), context_->snapToGrid(mouse_pos.y, false) }; // Update move vector - if (auto vertex = items_[0].asVertex(context_.map())) + if (auto vertex = items_[0].asVertex(context_->map())) offset_.set(np - vertex->position()); - else if (auto thing = items_[0].asThing(context_.map())) + else if (auto thing = items_[0].asThing(context_->map())) offset_.set(np - thing->position()); return; @@ -143,7 +154,7 @@ void MoveObjects::update(Vec2d mouse_pos) // Update move vector offset_.set( - context_.snapToGrid(mouse_pos.x - origin_.x, false), context_.snapToGrid(mouse_pos.y - origin_.y, false)); + context_->snapToGrid(mouse_pos.x - origin_.x, false), context_->snapToGrid(mouse_pos.y - origin_.y, false)); } // ----------------------------------------------------------------------------- @@ -154,53 +165,53 @@ void MoveObjects::end(bool accept) using mapeditor::Mode; // Un-filter objects - for (const auto& line : context_.map().lines()) + for (const auto& line : context_->map().lines()) line->filter(false); - for (const auto& thing : context_.map().things()) + for (const auto& thing : context_->map().things()) thing->filter(false); // Clear selection if (accept && selection_clear_move) - context_.selection().clear(); + context_->selection().clear(); // Move depending on edit mode - if (context_.editMode() == Mode::Things && accept) + if (context_->editMode() == Mode::Things && accept) { // Move things - context_.beginUndoRecord("Move Things", true, false, false); + context_->beginUndoRecord("Move Things", true, false, false); for (auto& item : items_) { - if (auto thing = item.asThing(context_.map())) + if (auto thing = item.asThing(context_->map())) { - context_.undoManager()->recordUndoStep(std::make_unique(thing)); + context_->undoManager()->recordUndoStep(std::make_unique(thing)); thing->move(thing->position() + offset_); } } - context_.endUndoRecord(true); + context_->endUndoRecord(true); } else if (accept) { // Any other edit mode we're technically moving vertices - context_.beginUndoRecord(fmt::format("Move {}", context_.modeString())); + context_->beginUndoRecord(fmt::format("Move {}", context_->modeString())); // Get list of vertices being moved - vector move_verts(context_.map().nVertices()); - memset(move_verts.data(), 0, context_.map().nVertices()); + vector move_verts(context_->map().nVertices()); + memset(move_verts.data(), 0, context_->map().nVertices()); // Get list of things (inside sectors) being moved - vector move_things(context_.map().nThings()); - memset(move_things.data(), 0, context_.map().nThings()); + vector move_things(context_->map().nThings()); + memset(move_things.data(), 0, context_->map().nThings()); - if (context_.editMode() == Mode::Vertices) + if (context_->editMode() == Mode::Vertices) { for (auto& item : items_) move_verts[item.index] = 1; } - else if (context_.editMode() == Mode::Lines) + else if (context_->editMode() == Mode::Lines) { for (auto& item : items_) { - if (auto line = item.asLine(context_.map())) + if (auto line = item.asLine(context_->map())) { if (line->v1()) move_verts[line->v1()->index()] = 1; @@ -209,11 +220,11 @@ void MoveObjects::end(bool accept) } } } - else if (context_.editMode() == Mode::Sectors) + else if (context_->editMode() == Mode::Sectors) { vector sv; for (auto& item : items_) - if (auto sector = item.asSector(context_.map())) + if (auto sector = item.asSector(context_->map())) sector->putVertices(sv); for (auto vertex : sv) @@ -221,7 +232,7 @@ void MoveObjects::end(bool accept) } // Find moved sectors to move things - for (auto& sector : context_.map().sectors()) + for (auto& sector : context_->map().sectors()) { bool allMoved = true; for (auto& side : sector->connectedSides()) @@ -241,7 +252,7 @@ void MoveObjects::end(bool accept) if (!allMoved) continue; // All the vertices are moved, so move its things - for (auto& thing : context_.map().things()) + for (auto& thing : context_->map().things()) { if (sector->containsPoint(thing->position())) move_things[thing->index()] = 1; @@ -250,24 +261,24 @@ void MoveObjects::end(bool accept) // Move vertices vector moved_verts; - for (unsigned a = 0; a < context_.map().nVertices(); a++) + for (unsigned a = 0; a < context_->map().nVertices(); a++) { if (!move_verts[a]) continue; - auto vertex = context_.map().vertex(a); + auto vertex = context_->map().vertex(a); vertex->move(vertex->xPos() + offset_.x, vertex->yPos() + offset_.y); moved_verts.push_back(vertex); } // Move things - for (unsigned a = 0; a < context_.map().nThings(); a++) + for (unsigned a = 0; a < context_->map().nThings(); a++) { if (!move_things[a]) continue; - auto thing = context_.map().thing(a); + auto thing = context_->map().thing(a); thing->move(thing->position() + offset_, true); } @@ -275,19 +286,19 @@ void MoveObjects::end(bool accept) // Begin extra 'Merge' undo step if wanted if (map_merge_undo_step) { - context_.endUndoRecord(true); - context_.beginUndoRecord("Merge"); + context_->endUndoRecord(true); + context_->beginUndoRecord("Merge"); } // Do merge - bool merge = context_.map().mergeArch(moved_verts); + bool merge = context_->map().mergeArch(moved_verts); - context_.endUndoRecord(merge || !map_merge_undo_step); + context_->endUndoRecord(merge || !map_merge_undo_step); } // Clear moving items items_.clear(); // Update map item indices - // context_.map().refreshIndices(); + // context_->map().refreshIndices(); } diff --git a/src/MapEditor/Edit/MoveObjects.h b/src/MapEditor/Edit/MoveObjects.h index 3d32d7abf..1876f228b 100644 --- a/src/MapEditor/Edit/MoveObjects.h +++ b/src/MapEditor/Edit/MoveObjects.h @@ -1,9 +1,8 @@ #pragma once -#include "MapEditor/MapEditor.h" - -namespace slade +namespace slade::mapeditor { +struct Item; class MapEditContext; class MoveObjects @@ -11,18 +10,17 @@ class MoveObjects public: MoveObjects(MapEditContext& context); - const vector& items() const { return items_; } - Vec2d offset() const { return offset_; } + const vector& items() const { return items_; } + Vec2d offset() const { return offset_; } - bool begin(Vec2d mouse_pos); - void update(Vec2d mouse_pos); + bool begin(const Vec2d& mouse_pos); + void update(const Vec2d& mouse_pos); void end(bool accept = true); private: - MapEditContext& context_; - Vec2d origin_; - Vec2d offset_; - vector items_; - mapeditor::Item item_closest_ = 0; + MapEditContext* context_; + Vec2d origin_; + Vec2d offset_; + vector items_; }; -} // namespace slade +} // namespace slade::mapeditor diff --git a/src/MapEditor/Edit/ObjectEdit.cpp b/src/MapEditor/Edit/ObjectEdit.cpp index dff46e3bd..2bdaeee03 100644 --- a/src/MapEditor/Edit/ObjectEdit.cpp +++ b/src/MapEditor/Edit/ObjectEdit.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -36,8 +36,16 @@ #include "ObjectEdit.h" #include "General/KeyBind.h" #include "General/UI.h" +#include "Input.h" #include "MapEditor/MapEditContext.h" #include "MapEditor/MapEditor.h" +#include "MapEditor/Renderer/MapRenderer2D.h" +#include "MapEditor/Renderer/Renderer.h" +#include "OpenGL/View.h" +#include "SLADEMap/MapObject/MapLine.h" +#include "SLADEMap/MapObject/MapSector.h" +#include "SLADEMap/MapObject/MapThing.h" +#include "SLADEMap/MapObject/MapVertex.h" #include "SLADEMap/SLADEMap.h" #include "Utility/MathStuff.h" @@ -137,7 +145,7 @@ void ObjectEditGroup::addThing(MapThing* thing) // ----------------------------------------------------------------------------- // Returns true if [line] is connected to the group vertices // ----------------------------------------------------------------------------- -bool ObjectEditGroup::hasLine(MapLine* line) +bool ObjectEditGroup::hasLine(const MapLine* line) const { for (auto& l : lines_) if (l.map_line == line) @@ -149,7 +157,7 @@ bool ObjectEditGroup::hasLine(MapLine* line) // ----------------------------------------------------------------------------- // Returns the group info about [vertex] // ----------------------------------------------------------------------------- -ObjectEditGroup::Vertex* ObjectEditGroup::findVertex(MapVertex* vertex) +ObjectEditGroup::Vertex* ObjectEditGroup::findVertex(const MapVertex* vertex) const { for (auto& v : vertices_) if (v->map_vertex == vertex) @@ -176,7 +184,7 @@ void ObjectEditGroup::clear() // ----------------------------------------------------------------------------- // Sets filtering on all group objects to [filter] // ----------------------------------------------------------------------------- -void ObjectEditGroup::filterObjects(bool filter) +void ObjectEditGroup::filterObjects(bool filter) const { // Vertices for (auto& vertex : vertices_) @@ -225,7 +233,7 @@ void ObjectEditGroup::resetPositions() // and sets [v1]/[v2] to the line vertices. // Returns true if a line was found within the distance specified // ----------------------------------------------------------------------------- -bool ObjectEditGroup::nearestLineEndpoints(Vec2d pos, double min, Vec2d& v1, Vec2d& v2) +bool ObjectEditGroup::nearestLineEndpoints(const Vec2d& pos, double min, Vec2d& v1, Vec2d& v2) const { double min_dist = min; for (auto& line : lines_) @@ -246,7 +254,7 @@ bool ObjectEditGroup::nearestLineEndpoints(Vec2d pos, double min, Vec2d& v1, Vec // ----------------------------------------------------------------------------- // Fills [list] with the positions of all group vertices // ----------------------------------------------------------------------------- -void ObjectEditGroup::putVerticesToDraw(vector& list) +void ObjectEditGroup::putVerticesToDraw(vector& list) const { for (auto& vertex : vertices_) if (!vertex->ignored) @@ -256,7 +264,7 @@ void ObjectEditGroup::putVerticesToDraw(vector& list) // ----------------------------------------------------------------------------- // Fills [list] with all lines in the group // ----------------------------------------------------------------------------- -void ObjectEditGroup::putLinesToDraw(vector& list) +void ObjectEditGroup::putLinesToDraw(vector& list) const { for (auto line : lines_) list.push_back(line); @@ -265,7 +273,7 @@ void ObjectEditGroup::putLinesToDraw(vector& list) // ----------------------------------------------------------------------------- // Fills [list] with all things in the group // ----------------------------------------------------------------------------- -void ObjectEditGroup::putThingsToDraw(vector& list) +void ObjectEditGroup::putThingsToDraw(vector& list) const { for (const auto& thing : things_) list.push_back(thing); @@ -399,7 +407,7 @@ void ObjectEditGroup::doScale(double xoff, double yoff, bool left, bool top, boo // This is used when rotating via the mouse ([p1] is the drag origin and [p2] // is the current point) // ----------------------------------------------------------------------------- -void ObjectEditGroup::doRotate(Vec2d p1, Vec2d p2, bool lock45) +void ObjectEditGroup::doRotate(const Vec2d& p1, const Vec2d& p2, bool lock45) { // Get midpoint Vec2d mid(old_bbox_.min.x + old_bbox_.width() * 0.5, old_bbox_.min.y + old_bbox_.height() * 0.5); @@ -556,7 +564,7 @@ void ObjectEditGroup::doAll( // ----------------------------------------------------------------------------- // Applies new group object positions to the actual map objects being edited // ----------------------------------------------------------------------------- -void ObjectEditGroup::applyEdit() +void ObjectEditGroup::applyEdit() const { // Get map SLADEMap* map; @@ -592,7 +600,7 @@ void ObjectEditGroup::applyEdit() // ----------------------------------------------------------------------------- // Adds all group vertices to [list] // ----------------------------------------------------------------------------- -void ObjectEditGroup::putMapVertices(vector& list) +void ObjectEditGroup::putMapVertices(vector& list) const { for (auto& vertex : vertices_) { @@ -615,15 +623,15 @@ void ObjectEditGroup::putMapVertices(vector& list) bool ObjectEdit::begin() { // Things mode - if (context_.editMode() == Mode::Things) + if (context_->editMode() == Mode::Things) { // Get selected things - auto edit_objects = context_.selection().selectedObjects(); + auto edit_objects = context_->selection().selectedObjects(); // Setup object group group_.clear(); for (auto& object : edit_objects) - group_.addThing((MapThing*)object); + group_.addThing(dynamic_cast(object)); // Filter objects group_.filterObjects(true); @@ -633,17 +641,17 @@ bool ObjectEdit::begin() vector edit_objects; // Vertices mode - if (context_.editMode() == Mode::Vertices) + if (context_->editMode() == Mode::Vertices) { // Get selected vertices - edit_objects = context_.selection().selectedObjects(); + edit_objects = context_->selection().selectedObjects(); } // Lines mode - else if (context_.editMode() == Mode::Lines) + else if (context_->editMode() == Mode::Lines) { // Get vertices of selected lines - auto lines = context_.selection().selectedLines(); + auto lines = context_->selection().selectedLines(); for (auto& line : lines) { VECTOR_ADD_UNIQUE(edit_objects, line->v1()); @@ -652,10 +660,10 @@ bool ObjectEdit::begin() } // Sectors mode - else if (context_.editMode() == Mode::Sectors) + else if (context_->editMode() == Mode::Sectors) { // Get vertices of selected sectors - auto sectors = context_.selection().selectedSectors(); + auto sectors = context_->selection().selectedSectors(); for (auto& sector : sectors) sector->putVertices(edit_objects); } @@ -663,7 +671,7 @@ bool ObjectEdit::begin() // Setup object group group_.clear(); for (auto& object : edit_objects) - group_.addVertex((MapVertex*)object); + group_.addVertex(dynamic_cast(object)); group_.addConnectedLines(); // Filter objects @@ -675,18 +683,18 @@ bool ObjectEdit::begin() mapeditor::showObjectEditPanel(true, &group_); - context_.input().setMouseState(Input::MouseState::ObjectEdit); - context_.renderer().renderer2D().forceUpdate(); + context_->input().setMouseState(Input::MouseState::ObjectEdit); + context_->renderer().renderer2D().forceUpdate(); // Setup help text auto key_accept = KeyBind::bind("map_edit_accept").keysAsString(); auto key_cancel = KeyBind::bind("map_edit_cancel").keysAsString(); auto key_toggle = KeyBind::bind("me2d_begin_object_edit").keysAsString(); - context_.setFeatureHelp({ "Object Edit", - fmt::format("{} = Accept", key_accept), - fmt::format("{} or {} = Cancel", key_cancel, key_toggle), - "Shift = Disable grid snapping", - "Ctrl = Rotate" }); + context_->setFeatureHelp({ "Object Edit", + fmt::format("{} = Accept", key_accept), + fmt::format("{} or {} = Cancel", key_cancel, key_toggle), + "Shift = Disable grid snapping", + "Ctrl = Rotate" }); return true; } @@ -694,7 +702,7 @@ bool ObjectEdit::begin() // ----------------------------------------------------------------------------- // Ends the object edit operation and applies changes if [accept] is true // ----------------------------------------------------------------------------- -void ObjectEdit::end(bool accept) +void ObjectEdit::end(bool accept) const { // Un-filter objects group_.filterObjects(false); @@ -703,35 +711,35 @@ void ObjectEdit::end(bool accept) if (accept) { // Begin recording undo level - context_.beginUndoRecord(fmt::format("Edit {}", context_.modeString())); + context_->beginUndoRecord(fmt::format("Edit {}", context_->modeString())); // Apply changes group_.applyEdit(); // Do merge bool merge = true; - if (context_.editMode() != Mode::Things) + if (context_->editMode() != Mode::Things) { // Begin extra 'Merge' undo step if wanted if (map_merge_undo_step) { - context_.endUndoRecord(true); - context_.beginUndoRecord("Merge"); + context_->endUndoRecord(true); + context_->beginUndoRecord("Merge"); } vector vertices; group_.putMapVertices(vertices); - merge = context_.map().mergeArch(vertices); + merge = context_->map().mergeArch(vertices); } // Clear selection - context_.selection().clear(); + context_->selection().clear(); - context_.endUndoRecord(merge || !map_merge_undo_step); + context_->endUndoRecord(merge || !map_merge_undo_step); } mapeditor::showObjectEditPanel(false, nullptr); - context_.setFeatureHelp({}); + context_->setFeatureHelp({}); } // ----------------------------------------------------------------------------- @@ -743,19 +751,19 @@ void ObjectEdit::determineState() // Get object edit bbox auto bbox = group_.bbox(); int bbox_pad = 8; - int left = context_.renderer().view().screenX(bbox.min.x) - bbox_pad; - int right = context_.renderer().view().screenX(bbox.max.x) + bbox_pad; - int top = context_.renderer().view().screenY(bbox.max.y) - bbox_pad; - int bottom = context_.renderer().view().screenY(bbox.min.y) + bbox_pad; - rotating_ = context_.input().ctrlDown(); + int left = context_->renderer().view().screenX(bbox.min.x) - bbox_pad; + int right = context_->renderer().view().screenX(bbox.max.x) + bbox_pad; + int top = context_->renderer().view().screenY(bbox.max.y) - bbox_pad; + int bottom = context_->renderer().view().screenY(bbox.min.y) + bbox_pad; + rotating_ = context_->input().ctrlDown(); // Check if mouse is outside the bbox - auto mouse_pos = context_.input().mousePos(); + auto mouse_pos = context_->input().mousePos(); if (mouse_pos.x < left || mouse_pos.x > right || mouse_pos.y < top || mouse_pos.y > bottom) { // Outside bbox state_ = State::None; - context_.setCursor(ui::MouseCursor::Normal); + context_->setCursor(ui::MouseCursor::Normal); return; } @@ -766,21 +774,21 @@ void ObjectEdit::determineState() if (mouse_pos.y < top + bbox_pad && bbox.height() > 0) { state_ = State::TopLeft; - context_.setCursor(rotating_ ? ui::MouseCursor::Cross : ui::MouseCursor::SizeNWSE); + context_->setCursor(rotating_ ? ui::MouseCursor::Cross : ui::MouseCursor::SizeNWSE); } // Bottom left else if (mouse_pos.y > bottom - bbox_pad && bbox.height() > 0) { state_ = State::BottomLeft; - context_.setCursor(rotating_ ? ui::MouseCursor::Cross : ui::MouseCursor::SizeNESW); + context_->setCursor(rotating_ ? ui::MouseCursor::Cross : ui::MouseCursor::SizeNESW); } // Left else if (!rotating_) { state_ = State::Left; - context_.setCursor(ui::MouseCursor::SizeWE); + context_->setCursor(ui::MouseCursor::SizeWE); } } @@ -791,21 +799,21 @@ void ObjectEdit::determineState() if (mouse_pos.y < top + bbox_pad && bbox.height() > 0) { state_ = State::TopRight; - context_.setCursor(rotating_ ? ui::MouseCursor::Cross : ui::MouseCursor::SizeNESW); + context_->setCursor(rotating_ ? ui::MouseCursor::Cross : ui::MouseCursor::SizeNESW); } // Bottom right else if (mouse_pos.y > bottom - bbox_pad && bbox.height() > 0) { state_ = State::BottomRight; - context_.setCursor(rotating_ ? ui::MouseCursor::Cross : ui::MouseCursor::SizeNWSE); + context_->setCursor(rotating_ ? ui::MouseCursor::Cross : ui::MouseCursor::SizeNWSE); } // Right else if (!rotating_) { state_ = State::Right; - context_.setCursor(ui::MouseCursor::SizeWE); + context_->setCursor(ui::MouseCursor::SizeWE); } } @@ -813,20 +821,20 @@ void ObjectEdit::determineState() else if (mouse_pos.y < top + bbox_pad && bbox.height() > 0 && !rotating_) { state_ = State::Top; - context_.setCursor(ui::MouseCursor::SizeNS); + context_->setCursor(ui::MouseCursor::SizeNS); } // Bottom else if (mouse_pos.y > bottom - bbox_pad && bbox.height() > 0 && !rotating_) { state_ = State::Bottom; - context_.setCursor(ui::MouseCursor::SizeNS); + context_->setCursor(ui::MouseCursor::SizeNS); } // Middle else { state_ = rotating_ ? State::None : State::Move; - context_.setCursor(rotating_ ? ui::MouseCursor::Normal : ui::MouseCursor::Move); + context_->setCursor(rotating_ ? ui::MouseCursor::Normal : ui::MouseCursor::Move); } } diff --git a/src/MapEditor/Edit/ObjectEdit.h b/src/MapEditor/Edit/ObjectEdit.h index 9f86eaec6..4ea46929e 100644 --- a/src/MapEditor/Edit/ObjectEdit.h +++ b/src/MapEditor/Edit/ObjectEdit.h @@ -1,14 +1,19 @@ #pragma once -#include "Utility/Structs.h" - namespace slade { -class MapEditContext; class MapVertex; class MapLine; class MapThing; +namespace mapeditor +{ + class MapEditContext; +} +} // namespace slade + +namespace slade::mapeditor +{ class ObjectEditGroup { public: @@ -43,26 +48,26 @@ class ObjectEditGroup void addVertex(MapVertex* vertex, bool ignored = false); void addConnectedLines(); void addThing(MapThing* thing); - bool hasLine(MapLine* line); - Vertex* findVertex(MapVertex* vertex); + bool hasLine(const MapLine* line) const; + Vertex* findVertex(const MapVertex* vertex) const; void clear(); - void filterObjects(bool filter); + void filterObjects(bool filter) const; void resetPositions(); bool empty() const { return vertices_.empty() && things_.empty(); } - bool nearestLineEndpoints(Vec2d pos, double min, Vec2d& v1, Vec2d& v2); - void putMapVertices(vector& list); + bool nearestLineEndpoints(const Vec2d& pos, double min, Vec2d& v1, Vec2d& v2) const; + void putMapVertices(vector& list) const; // Drawing - void putVerticesToDraw(vector& list); - void putLinesToDraw(vector& list); - void putThingsToDraw(vector& list); + void putVerticesToDraw(vector& list) const; + void putLinesToDraw(vector& list) const; + void putThingsToDraw(vector& list) const; // Modification void doMove(double xoff, double yoff); void doScale(double xoff, double yoff, bool left, bool top, bool right, bool bottom); - void doRotate(Vec2d p1, Vec2d p2, bool lock45); + void doRotate(const Vec2d& p1, const Vec2d& p2, bool lock45); void doAll(double xoff, double yoff, double xscale, double yscale, double rotation, bool mirror_x, bool mirror_y); - void applyEdit(); + void applyEdit() const; private: vector> vertices_; @@ -95,7 +100,7 @@ class ObjectEdit BottomRight, }; - ObjectEdit(MapEditContext& context) : context_{ context } {} + ObjectEdit(mapeditor::MapEditContext& context) : context_{ &context } {} ObjectEditGroup& group() { return group_; } State state() const { return state_; } @@ -126,13 +131,13 @@ class ObjectEdit } bool begin(); - void end(bool accept); + void end(bool accept) const; void determineState(); private: - MapEditContext& context_; - ObjectEditGroup group_; - State state_ = State::None; - bool rotating_ = false; + mapeditor::MapEditContext* context_; + ObjectEditGroup group_; + State state_ = State::None; + bool rotating_ = false; }; -} // namespace slade +} // namespace slade::mapeditor diff --git a/src/MapEditor/Item.cpp b/src/MapEditor/Item.cpp new file mode 100644 index 000000000..0f8578d6a --- /dev/null +++ b/src/MapEditor/Item.cpp @@ -0,0 +1,146 @@ + +#include "Main.h" +#include "Item.h" +#include "SLADEMap/MapObject/MapLine.h" +#include "SLADEMap/MapObject/MapSector.h" +#include "SLADEMap/MapObject/MapSide.h" +#include "SLADEMap/MapObject/MapThing.h" +#include "SLADEMap/MapObject/MapVertex.h" +#include "SLADEMap/SLADEMap.h" + +using namespace slade; +using namespace mapeditor; + +// ----------------------------------------------------------------------------- +// +// Item Struct Functions +// +// ----------------------------------------------------------------------------- + + +// ----------------------------------------------------------------------------- +// Returns the vertex in [map] matching this item, or null if the item isn't a +// vertex +// ----------------------------------------------------------------------------- +MapVertex* Item::asVertex(const SLADEMap& map) const +{ + if (type == ItemType::Vertex) + return map.vertex(index); + + return nullptr; +} + +// ----------------------------------------------------------------------------- +// Returns the line in [map] matching this item, or null if the item isn't a +// line +// ----------------------------------------------------------------------------- +MapLine* Item::asLine(const SLADEMap& map) const +{ + if (type == ItemType::Line) + return map.line(index); + + return nullptr; +} + +// ----------------------------------------------------------------------------- +// Returns the side in [map] matching this item, or null if the item isn't a +// side +// ----------------------------------------------------------------------------- +MapSide* Item::asSide(const SLADEMap& map) const +{ + if (type == ItemType::Side || type == ItemType::WallBottom || type == ItemType::WallMiddle + || type == ItemType::WallTop) + return map.side(index); + + return nullptr; +} + +// ----------------------------------------------------------------------------- +// Returns the sector in [map] matching this item, or null if the item isn't a +// sector +// ----------------------------------------------------------------------------- +MapSector* Item::asSector(const SLADEMap& map) const +{ + if (type == ItemType::Sector || type == ItemType::Ceiling || type == ItemType::Floor) + return map.sector(index); + + return nullptr; +} + +// ----------------------------------------------------------------------------- +// Returns the thing in [map] matching this item, or null if the item isn't a +// thing +// ----------------------------------------------------------------------------- +MapThing* Item::asThing(const SLADEMap& map) const +{ + if (type == ItemType::Thing) + return map.thing(index); + + return nullptr; +} + +// ----------------------------------------------------------------------------- +// Returns the object in [map] matching this item +// ----------------------------------------------------------------------------- +MapObject* Item::asObject(const SLADEMap& map) const +{ + switch (type) + { + case ItemType::Vertex: return map.vertex(index); + case ItemType::Side: + case ItemType::WallTop: + case ItemType::WallMiddle: + case ItemType::WallBottom: + case ItemType::Line: return map.line(index); + case ItemType::Floor: + case ItemType::Ceiling: + case ItemType::Sector: return map.sector(index); + case ItemType::Thing: return map.thing(index); + default: return nullptr; + } +} + + +// ----------------------------------------------------------------------------- +// +// MapEditor Namespace Functions +// +// ----------------------------------------------------------------------------- + +// ----------------------------------------------------------------------------- +// Returns the 'base' item type for [type] +// (eg. WallMiddle is technically a Side) +// ----------------------------------------------------------------------------- +ItemType mapeditor::baseItemType(const ItemType& type) +{ + switch (type) + { + case ItemType::Vertex: return ItemType::Vertex; + case ItemType::Line: return ItemType::Line; + case ItemType::Side: + case ItemType::WallBottom: + case ItemType::WallMiddle: + case ItemType::WallTop: return ItemType::Side; + case ItemType::Sector: + case ItemType::Ceiling: + case ItemType::Floor: return ItemType::Sector; + case ItemType::Thing: return ItemType::Thing; + default: return ItemType::Any; + } +} + +// ----------------------------------------------------------------------------- +// Returns the map editor item type of the given map [object] +// ----------------------------------------------------------------------------- +ItemType mapeditor::itemTypeFromObject(const MapObject* object) +{ + switch (object->objType()) + { + case MapObject::Type::Vertex: return ItemType::Vertex; + case MapObject::Type::Line: return ItemType::Line; + case MapObject::Type::Side: return ItemType::Side; + case MapObject::Type::Sector: return ItemType::Sector; + case MapObject::Type::Thing: return ItemType::Thing; + default: return ItemType::Any; + } +} diff --git a/src/MapEditor/Item.h b/src/MapEditor/Item.h new file mode 100644 index 000000000..aba969d51 --- /dev/null +++ b/src/MapEditor/Item.h @@ -0,0 +1,83 @@ +#pragma once + +// Forward declarations +namespace slade +{ +class MapLine; +class MapObject; +class MapSector; +class MapSide; +class MapThing; +class MapVertex; +class SLADEMap; +} // namespace slade + +namespace slade::mapeditor +{ +enum class ItemType +{ + // 2d modes + Vertex, + Line, + Sector, + + // 3d mode + Side, + WallTop, + WallMiddle, + WallBottom, + Floor, + Ceiling, + Thing, // (also 2d things mode) + + Any +}; + +struct Item +{ + int index; + ItemType type; + int real_index; + int control_line; + + Item(int index = -1, ItemType type = ItemType::Any) : + index{ index }, + type{ type }, + real_index{ -1 }, + control_line{ -1 } + { + } + + // Comparison operators + bool operator<(const Item& other) const + { + if (type == other.type) + { + if (index == other.index) + return real_index < other.real_index; + else + return index < other.index; + } + else + return type < other.type; + } + bool operator==(const Item& other) const + { + return index == other.index && (type == ItemType::Any || type == other.type) && real_index == other.real_index; + } + bool operator!=(const Item& other) const { return !(*this == other); } + + // Conversion operators + explicit operator int() const { return index; } + + MapVertex* asVertex(const SLADEMap& map) const; + MapLine* asLine(const SLADEMap& map) const; + MapSide* asSide(const SLADEMap& map) const; + MapSector* asSector(const SLADEMap& map) const; + MapThing* asThing(const SLADEMap& map) const; + MapObject* asObject(const SLADEMap& map) const; +}; + +ItemType baseItemType(const ItemType& type); +ItemType itemTypeFromObject(const MapObject* object); +} // namespace slade::mapeditor diff --git a/src/MapEditor/ItemSelection.cpp b/src/MapEditor/ItemSelection.cpp index dfa92ba15..4acbec319 100644 --- a/src/MapEditor/ItemSelection.cpp +++ b/src/MapEditor/ItemSelection.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -35,28 +35,36 @@ #include "ItemSelection.h" #include "Game/Configuration.h" #include "MapEditContext.h" +#include "MapEditor.h" +#include "SLADEMap/MapObject/MapLine.h" +#include "SLADEMap/MapObject/MapSector.h" +#include "SLADEMap/MapObject/MapSide.h" +#include "SLADEMap/MapObject/MapThing.h" +#include "SLADEMap/MapObject/MapVertex.h" +#include "SLADEMap/MapObjectList/LineList.h" +#include "SLADEMap/MapObjectList/SectorList.h" +#include "SLADEMap/MapObjectList/ThingList.h" +#include "SLADEMap/MapObjectList/VertexList.h" +#include "SLADEMap/SLADEMap.h" #include "UI/MapCanvas.h" #include "Utility/MathStuff.h" using namespace slade; - +using namespace mapeditor; // ----------------------------------------------------------------------------- // // ItemSelection Class Functions // // ----------------------------------------------------------------------------- -using mapeditor::ItemType; -using mapeditor::Mode; -using mapeditor::SectorMode; // ----------------------------------------------------------------------------- // Returns the currently selected items, or the currently hilighted item if // nothing is selected // ----------------------------------------------------------------------------- -vector ItemSelection::selectionOrHilight() +vector ItemSelection::selectionOrHilight() { - vector list; + vector list; if (!selection_.empty()) list.assign(selection_.begin(), selection_.end()); @@ -70,7 +78,7 @@ vector ItemSelection::selectionOrHilight() // Returns the first selected item, or the currently hilighted item if nothing // is selected // ----------------------------------------------------------------------------- -mapeditor::Item ItemSelection::firstSelectedOrHilight() +Item ItemSelection::firstSelectedOrHilight() const { if (!selection_.empty()) return selection_[0]; @@ -83,7 +91,7 @@ mapeditor::Item ItemSelection::firstSelectedOrHilight() // ----------------------------------------------------------------------------- // Sets the current hilight to [item]. Returns true if the hilight was changed // ----------------------------------------------------------------------------- -bool ItemSelection::setHilight(const mapeditor::Item& item) +bool ItemSelection::setHilight(const Item& item) { if (item != hilight_) { @@ -119,7 +127,7 @@ bool ItemSelection::setHilight(int index) // Hilights the map object closest to [mouse_pos], and updates anything needed // if the hilight is changed // ----------------------------------------------------------------------------- -bool ItemSelection::updateHilight(Vec2d mouse_pos, double dist_scale) +bool ItemSelection::updateHilight(const Vec2d& mouse_pos, double dist_scale) { // Do nothing if hilight is locked or we have no context if (hilight_lock_ || !context_) @@ -132,17 +140,17 @@ bool ItemSelection::updateHilight(Vec2d mouse_pos, double dist_scale) if (context_->editMode() == Mode::Vertices) { auto vertex = map.vertices().nearest(mouse_pos, 32 / dist_scale); - hilight_ = { vertex ? (int)vertex->index() : -1, ItemType::Vertex }; + hilight_ = { vertex ? static_cast(vertex->index()) : -1, ItemType::Vertex }; } else if (context_->editMode() == Mode::Lines) { auto line = map.lines().nearest(mouse_pos, 32 / dist_scale); - hilight_ = { line ? (int)line->index() : -1, ItemType::Line }; + hilight_ = { line ? static_cast(line->index()) : -1, ItemType::Line }; } else if (context_->editMode() == Mode::Sectors) { auto sector = map.sectors().atPos(mouse_pos); - hilight_ = { sector ? (int)sector->index() : -1, ItemType::Sector }; + hilight_ = { sector ? static_cast(sector->index()) : -1, ItemType::Sector }; } else if (context_->editMode() == Mode::Things) { @@ -177,10 +185,10 @@ bool ItemSelection::updateHilight(Vec2d mouse_pos, double dist_scale) switch (context_->editMode()) { case Mode::Vertices: mapeditor::openObjectProperties(map.vertex(hilight_.index)); break; - case Mode::Lines: mapeditor::openObjectProperties(map.line(hilight_.index)); break; - case Mode::Sectors: mapeditor::openObjectProperties(map.sector(hilight_.index)); break; - case Mode::Things: mapeditor::openObjectProperties(map.thing(hilight_.index)); break; - default: break; + case Mode::Lines: mapeditor::openObjectProperties(map.line(hilight_.index)); break; + case Mode::Sectors: mapeditor::openObjectProperties(map.sector(hilight_.index)); break; + case Mode::Things: mapeditor::openObjectProperties(map.thing(hilight_.index)); break; + default: break; } context_->resetLastUndoLevel(); @@ -210,7 +218,7 @@ void ItemSelection::clear() // Changes the selection status of [item] to [select]. // If [new_change] is true, a new change set is started // ----------------------------------------------------------------------------- -void ItemSelection::select(const mapeditor::Item& item, bool select, bool new_change) +void ItemSelection::select(const Item& item, bool select, bool new_change) { // Start new change set if specified if (new_change) @@ -223,7 +231,7 @@ void ItemSelection::select(const mapeditor::Item& item, bool select, bool new_ch // Changes the selection status of all items in [items] to [select]. // If [new_change] is true, a new change set is started // ----------------------------------------------------------------------------- -void ItemSelection::select(const vector& items, bool select, bool new_change) +void ItemSelection::select(const vector& items, bool select, bool new_change) { // Start new change set if specified if (new_change) @@ -250,22 +258,22 @@ void ItemSelection::selectAll() if (context_->editMode() == Mode::Vertices) { for (unsigned a = 0; a < map.nVertices(); a++) - selectItem({ (int)a, ItemType::Vertex }); + selectItem({ static_cast(a), ItemType::Vertex }); } else if (context_->editMode() == Mode::Lines) { for (unsigned a = 0; a < map.nLines(); a++) - selectItem({ (int)a, ItemType::Line }); + selectItem({ static_cast(a), ItemType::Line }); } else if (context_->editMode() == Mode::Sectors) { for (unsigned a = 0; a < map.nSectors(); a++) - selectItem({ (int)a, ItemType::Sector }); + selectItem({ static_cast(a), ItemType::Sector }); } else if (context_->editMode() == Mode::Things) { for (unsigned a = 0; a < map.nThings(); a++) - selectItem({ (int)a, ItemType::Thing }); + selectItem({ static_cast(a), ItemType::Thing }); } context_->addEditorMessage(fmt::format("Selected all {} {}", selection_.size(), context_->modeString())); @@ -314,7 +322,7 @@ void ItemSelection::selectVerticesWithin(const SLADEMap& map, const Rectd& rect) // Select vertices within bounds for (unsigned a = 0; a < map.nVertices(); a++) if (rect.contains(map.vertex(a)->position())) - selectItem({ (int)a, ItemType::Vertex }); + selectItem({ static_cast(a), ItemType::Vertex }); } // ----------------------------------------------------------------------------- @@ -328,7 +336,7 @@ void ItemSelection::selectLinesWithin(const SLADEMap& map, const Rectd& rect) // Select lines within bounds for (unsigned a = 0; a < map.nLines(); a++) if (rect.contains(map.line(a)->v1()->position()) && rect.contains(map.line(a)->v2()->position())) - selectItem({ (int)a, ItemType::Line }); + selectItem({ static_cast(a), ItemType::Line }); } // ----------------------------------------------------------------------------- @@ -342,7 +350,7 @@ void ItemSelection::selectSectorsWithin(const SLADEMap& map, const Rectd& rect) // Select sectors within bounds for (unsigned a = 0; a < map.nSectors(); a++) if (map.sector(a)->boundingBox().isWithin(rect.tl, rect.br)) - selectItem({ (int)a, ItemType::Sector }); + selectItem({ static_cast(a), ItemType::Sector }); } // ----------------------------------------------------------------------------- @@ -356,7 +364,7 @@ void ItemSelection::selectThingsWithin(const SLADEMap& map, const Rectd& rect) // Select vertices within bounds for (unsigned a = 0; a < map.nThings(); a++) if (rect.contains(map.thing(a)->position())) - selectItem({ (int)a, ItemType::Thing }); + selectItem({ static_cast(a), ItemType::Thing }); } // ----------------------------------------------------------------------------- @@ -377,10 +385,10 @@ bool ItemSelection::selectWithin(const Rectd& rect, bool add) switch (context_->editMode()) { case Mode::Vertices: selectVerticesWithin(context_->map(), rect); break; - case Mode::Lines: selectLinesWithin(context_->map(), rect); break; - case Mode::Sectors: selectSectorsWithin(context_->map(), rect); break; - case Mode::Things: selectThingsWithin(context_->map(), rect); break; - default: break; + case Mode::Lines: selectLinesWithin(context_->map(), rect); break; + case Mode::Sectors: selectSectorsWithin(context_->map(), rect); break; + case Mode::Things: selectThingsWithin(context_->map(), rect); break; + default: break; } context_->selectionUpdated(); @@ -448,10 +456,10 @@ MapObject* ItemSelection::hilightedObject() const switch (context_->editMode()) { case Mode::Vertices: return hilightedVertex(); - case Mode::Lines: return hilightedLine(); - case Mode::Sectors: return hilightedSector(); - case Mode::Things: return hilightedThing(); - default: return nullptr; + case Mode::Lines: return hilightedLine(); + case Mode::Sectors: return hilightedSector(); + case Mode::Things: return hilightedThing(); + default: return nullptr; } } @@ -579,10 +587,10 @@ vector ItemSelection::selectedObjects(bool try_hilight) const switch (context_->editMode()) { case Mode::Vertices: type = MapObject::Type::Vertex; break; - case Mode::Lines: type = MapObject::Type::Line; break; - case Mode::Sectors: type = MapObject::Type::Sector; break; - case Mode::Things: type = MapObject::Type::Thing; break; - default: return {}; + case Mode::Lines: type = MapObject::Type::Line; break; + case Mode::Sectors: type = MapObject::Type::Sector; break; + case Mode::Things: type = MapObject::Type::Thing; break; + default: return {}; } // Get selected objects @@ -608,7 +616,7 @@ vector ItemSelection::selectedObjects(bool try_hilight) const // ----------------------------------------------------------------------------- void ItemSelection::migrate(Mode from_edit_mode, Mode to_edit_mode) { - std::set new_selection; + std::set new_selection; // 3D to 2D: select anything of the right type if (from_edit_mode == Mode::Visual) @@ -629,7 +637,7 @@ void ItemSelection::migrate(Mode from_edit_mode, Mode to_edit_mode) auto side = context_->map().side(item.index); if (!side) continue; - new_selection.insert({ (int)side->parentLine()->index(), ItemType::Line }); + new_selection.insert({ static_cast(side->parentLine()->index()), ItemType::Line }); } } } @@ -657,19 +665,19 @@ void ItemSelection::migrate(Mode from_edit_mode, Mode to_edit_mode) // Only select the visible areas -- i.e., the ones that need texturing int textures = line->needsTexture(); if (front && textures & MapLine::Part::FrontUpper) - new_selection.insert({ (int)front->index(), ItemType::WallTop }); + new_selection.insert({ static_cast(front->index()), ItemType::WallTop }); if (front && textures & MapLine::Part::FrontLower) - new_selection.insert({ (int)front->index(), ItemType::WallBottom }); + new_selection.insert({ static_cast(front->index()), ItemType::WallBottom }); if (back && textures & MapLine::Part::BackUpper) - new_selection.insert({ (int)back->index(), ItemType::WallTop }); + new_selection.insert({ static_cast(back->index()), ItemType::WallTop }); if (back && textures & MapLine::Part::BackLower) - new_selection.insert({ (int)back->index(), ItemType::WallBottom }); + new_selection.insert({ static_cast(back->index()), ItemType::WallBottom }); // Also include any two-sided middle textures if (front && (textures & MapLine::Part::FrontMiddle || front->texMiddle() != MapSide::TEX_NONE)) - new_selection.insert({ (int)front->index(), ItemType::WallMiddle }); + new_selection.insert({ static_cast(front->index()), ItemType::WallMiddle }); if (back && (textures & MapLine::Part::BackMiddle || back->texMiddle() != MapSide::TEX_NONE)) - new_selection.insert({ (int)back->index(), ItemType::WallMiddle }); + new_selection.insert({ static_cast(back->index()), ItemType::WallMiddle }); } // Thing @@ -695,7 +703,7 @@ void ItemSelection::migrate(Mode from_edit_mode, Mode to_edit_mode) vector lines; sector->putLines(lines); for (auto line : lines) - new_selection.insert({ (int)line->index(), ItemType::Line }); + new_selection.insert({ static_cast(line->index()), ItemType::Line }); } // To vertices mode @@ -704,7 +712,7 @@ void ItemSelection::migrate(Mode from_edit_mode, Mode to_edit_mode) vector vertices; sector->putVertices(vertices); for (auto vertex : vertices) - new_selection.insert({ (int)vertex->index(), ItemType::Vertex }); + new_selection.insert({ static_cast(vertex->index()), ItemType::Vertex }); } // To things mode @@ -713,7 +721,7 @@ void ItemSelection::migrate(Mode from_edit_mode, Mode to_edit_mode) for (auto& thing : context_->map().things()) { if (sector->containsPoint(thing->position())) - new_selection.insert({ (int)thing->index(), ItemType::Thing }); + new_selection.insert({ static_cast(thing->index()), ItemType::Thing }); } } } @@ -727,8 +735,8 @@ void ItemSelection::migrate(Mode from_edit_mode, Mode to_edit_mode) auto line = context_->map().line(item.index); if (!line) continue; - new_selection.insert({ (int)line->v1()->index(), ItemType::Vertex }); - new_selection.insert({ (int)line->v2()->index(), ItemType::Vertex }); + new_selection.insert({ static_cast(line->v1()->index()), ItemType::Vertex }); + new_selection.insert({ static_cast(line->v2()->index()), ItemType::Vertex }); } } @@ -740,7 +748,7 @@ void ItemSelection::migrate(Mode from_edit_mode, Mode to_edit_mode) // Selects or deselects [item] depending on the value of [select] and updates // the current ChangeSet // ----------------------------------------------------------------------------- -void ItemSelection::selectItem(const mapeditor::Item& item, bool select) +void ItemSelection::selectItem(const Item& item, bool select) { // Check if already selected bool selected = VECTOR_EXISTS(selection_, item); diff --git a/src/MapEditor/ItemSelection.h b/src/MapEditor/ItemSelection.h index 562a7420a..816938268 100644 --- a/src/MapEditor/ItemSelection.h +++ b/src/MapEditor/ItemSelection.h @@ -1,17 +1,21 @@ #pragma once -#include "MapEditor.h" +#include "Item.h" namespace slade { class MapCanvas; -class MapEditContext; class MapLine; class MapObject; class MapSector; class MapThing; class MapVertex; class SLADEMap; +namespace mapeditor +{ + enum class Mode; + class MapEditContext; +} // namespace mapeditor class ItemSelection { @@ -21,7 +25,7 @@ class ItemSelection typedef vector::iterator iterator; typedef vector::value_type value_type; - ItemSelection(MapEditContext* context = nullptr) : context_{ context } {} + ItemSelection(mapeditor::MapEditContext* context = nullptr) : context_{ context } {} // Accessors mapeditor::Item hilight() const { return hilight_; } @@ -37,7 +41,7 @@ class ItemSelection const mapeditor::Item& operator[](unsigned index) const { return selection_[index]; } vector selectionOrHilight(); - mapeditor::Item firstSelectedOrHilight(); + mapeditor::Item firstSelectedOrHilight() const; // Setters void lockHilight(bool lock = true) { hilight_lock_ = lock; } @@ -57,7 +61,7 @@ class ItemSelection bool isSelected(const mapeditor::Item& item) const { return VECTOR_EXISTS(selection_, item); } bool isHilighted(const mapeditor::Item& item) const { return item == hilight_; } - bool updateHilight(Vec2d mouse_pos, double dist_scale); + bool updateHilight(const Vec2d& mouse_pos, double dist_scale); void clear(); void select(const mapeditor::Item& item, bool select = true, bool new_change = true); @@ -85,15 +89,12 @@ class ItemSelection void migrate(mapeditor::Mode from_edit_mode, mapeditor::Mode to_edit_mode); - // void showItem(int index); - // void selectItem3d(MapEditor::Item item, int sel); - private: - mapeditor::Item hilight_ = { -1, mapeditor::ItemType::Any }; - vector selection_; - bool hilight_lock_ = false; - ChangeSet last_change_; - MapEditContext* context_ = nullptr; + mapeditor::Item hilight_ = { -1, mapeditor::ItemType::Any }; + vector selection_; + bool hilight_lock_ = false; + ChangeSet last_change_; + mapeditor::MapEditContext* context_ = nullptr; void selectItem(const mapeditor::Item& item, bool select = true); }; diff --git a/src/MapEditor/MapBackupManager.cpp b/src/MapEditor/MapBackupManager.cpp index d65d6acc6..e83478ad2 100644 --- a/src/MapEditor/MapBackupManager.cpp +++ b/src/MapEditor/MapBackupManager.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -69,9 +69,9 @@ string mb_ignore_entries[] = { "NODES", "SSECTORS", "ZNODES", "SEGS", "R // in [map_data] // ----------------------------------------------------------------------------- bool MapBackupManager::writeBackup( - vector>& map_data, - std::string_view archive_name, - std::string_view map_name) const + const vector>& map_data, + std::string_view archive_name, + std::string_view map_name) const { // Create backup directory if needed auto backup_dir = app::path("backups", app::Dir::User); @@ -151,7 +151,7 @@ bool MapBackupManager::writeBackup( // Check for max backups & remove old ones if over map_dir = backup->dirAtPath(map_name); - while ((int)map_dir->numSubdirs() > max_map_backups) + while (static_cast(map_dir->numSubdirs()) > max_map_backups) backup->removeDir(map_dir->subdirAt(0)->name(), map_dir); // Save backup file diff --git a/src/MapEditor/MapBackupManager.h b/src/MapEditor/MapBackupManager.h index c2ce47962..6d487523b 100644 --- a/src/MapEditor/MapBackupManager.h +++ b/src/MapEditor/MapBackupManager.h @@ -10,7 +10,8 @@ class MapBackupManager MapBackupManager() = default; ~MapBackupManager() = default; - bool writeBackup(vector>& map_data, string_view archive_name, string_view map_name) const; + bool writeBackup(const vector>& map_data, string_view archive_name, string_view map_name) + const; Archive* openBackup(string_view archive_name, string_view map_name) const; }; } // namespace slade diff --git a/src/MapEditor/MapChecks.cpp b/src/MapEditor/MapChecks.cpp index f1d1ac8c5..5331b0665 100644 --- a/src/MapEditor/MapChecks.cpp +++ b/src/MapEditor/MapChecks.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -31,12 +31,23 @@ // ----------------------------------------------------------------------------- #include "Main.h" #include "MapChecks.h" +#include "Edit/Edit2D.h" +#include "Game/ActionSpecial.h" #include "Game/Configuration.h" +#include "Game/Game.h" #include "Game/ThingType.h" #include "General/SAction.h" #include "MapEditor/MapEditContext.h" #include "MapEditor/MapEditor.h" #include "MapTextureManager.h" +#include "OpenGL/GLTexture.h" +#include "SLADEMap/MapObject/MapLine.h" +#include "SLADEMap/MapObject/MapSector.h" +#include "SLADEMap/MapObject/MapSide.h" +#include "SLADEMap/MapObject/MapThing.h" +#include "SLADEMap/MapObjectList/LineList.h" +#include "SLADEMap/MapObjectList/SectorList.h" +#include "SLADEMap/MapObjectList/ThingList.h" #include "SLADEMap/SLADEMap.h" #include "UI/Dialogs/MapTextureBrowser.h" #include "UI/Dialogs/ThingTypeBrowser.h" @@ -44,6 +55,7 @@ #include "Utility/StringUtils.h" using namespace slade; +using namespace mapeditor; // ----------------------------------------------------------------------------- @@ -165,12 +177,13 @@ class MissingTextureCheck : public MapCheck { switch (part) { - case MapLine::Part::FrontUpper: return "front upper texture"; + case MapLine::Part::FrontUpper: return "front upper texture"; case MapLine::Part::FrontMiddle: return "front middle texture"; - case MapLine::Part::FrontLower: return "front lower texture"; - case MapLine::Part::BackUpper: return "back upper texture"; - case MapLine::Part::BackMiddle: return "back middle texture"; - case MapLine::Part::BackLower: return "back lower texture"; + case MapLine::Part::FrontLower: return "front lower texture"; + case MapLine::Part::BackUpper: return "back upper texture"; + case MapLine::Part::BackMiddle: return "back middle texture"; + case MapLine::Part::BackLower: return "back lower texture"; + default: break; } return ""; @@ -206,10 +219,10 @@ class MissingTextureCheck : public MapCheck lines_[index]->setStringProperty("side1.texturemiddle", texture); break; case MapLine::Part::FrontLower: lines_[index]->setStringProperty("side1.texturebottom", texture); break; - case MapLine::Part::BackUpper: lines_[index]->setStringProperty("side2.texturetop", texture); break; + case MapLine::Part::BackUpper: lines_[index]->setStringProperty("side2.texturetop", texture); break; case MapLine::Part::BackMiddle: lines_[index]->setStringProperty("side2.texturemiddle", texture); break; - case MapLine::Part::BackLower: lines_[index]->setStringProperty("side2.texturebottom", texture); break; - default: return false; + case MapLine::Part::BackLower: lines_[index]->setStringProperty("side2.texturebottom", texture); break; + default: return false; } editor->endUndoRecord(); @@ -387,7 +400,7 @@ class MissingTaggedCheck : public MapCheck // Ignore the Heresiarch which does not have a real special if (thingmode) { - auto& tt = game::configuration().thingType(((MapThing*)mo)->type()); + auto& tt = game::configuration().thingType(dynamic_cast(mo)->type()); if (tt.flags() & game::ThingType::Flags::Script) continue; } @@ -493,7 +506,7 @@ class LinesIntersectCheck : public MapCheck public: LinesIntersectCheck(SLADEMap* map) : MapCheck(map) {} - void checkIntersections(vector lines) + void checkIntersections(const vector& lines) { Vec2d pos; MapLine* line1; @@ -1111,10 +1124,10 @@ class UnknownTexturesCheck : public MapCheck lines_[index]->setStringProperty("side1.texturemiddle", texture); break; case MapLine::Part::FrontLower: lines_[index]->setStringProperty("side1.texturebottom", texture); break; - case MapLine::Part::BackUpper: lines_[index]->setStringProperty("side2.texturetop", texture); break; + case MapLine::Part::BackUpper: lines_[index]->setStringProperty("side2.texturetop", texture); break; case MapLine::Part::BackMiddle: lines_[index]->setStringProperty("side2.texturemiddle", texture); break; - case MapLine::Part::BackLower: lines_[index]->setStringProperty("side2.texturebottom", texture); break; - default: return false; + case MapLine::Part::BackLower: lines_[index]->setStringProperty("side2.texturebottom", texture); break; + default: return false; } editor->endUndoRecord(); @@ -1376,7 +1389,7 @@ class StuckThingsCheck : public MapCheck continue; radius = tt.radius() - 1; - Rectf bbox(thing->xPos(), thing->yPos(), radius * 2, radius * 2, 1); + Rectf bbox(thing->xPos(), thing->yPos(), radius * 2, radius * 2, true); // Go through lines for (auto& check_line : check_lines) @@ -1736,7 +1749,6 @@ class UnknownSectorCheck : public MapCheck for (unsigned a = 0; a < map_->nSectors(); a++) { int special = map_->sector(a)->special(); - int base = game::configuration().baseSectorType(special); if (game::configuration().sectorTypeName(special) == "Unknown") sectors_.push_back(a); } @@ -1909,7 +1921,6 @@ class ObsoleteThingCheck : public MapCheck string problemDesc(unsigned index) override { - bool special = (map_->currentFormat() == MapFormat::Hexen || map_->currentFormat() == MapFormat::UDMF); if (index >= things_.size()) return "No obsolete things found"; @@ -1971,22 +1982,22 @@ unique_ptr MapCheck::standardCheck(StandardCheck type, SLADEMap* map, { switch (type) { - case MissingTexture: return std::make_unique(map); - case SpecialTag: return std::make_unique(map); + case MissingTexture: return std::make_unique(map); + case SpecialTag: return std::make_unique(map); case IntersectingLine: return std::make_unique(map); - case OverlappingLine: return std::make_unique(map); + case OverlappingLine: return std::make_unique(map); case OverlappingThing: return std::make_unique(map); - case UnknownTexture: return std::make_unique(map, texman); - case UnknownFlat: return std::make_unique(map, texman); + case UnknownTexture: return std::make_unique(map, texman); + case UnknownFlat: return std::make_unique(map, texman); case UnknownThingType: return std::make_unique(map); - case StuckThing: return std::make_unique(map); - case SectorReference: return std::make_unique(map); - case InvalidLine: return std::make_unique(map); - case MissingTagged: return std::make_unique(map); - case UnknownSector: return std::make_unique(map); - case UnknownSpecial: return std::make_unique(map); - case ObsoleteThing: return std::make_unique(map); - default: return std::make_unique(map); + case StuckThing: return std::make_unique(map); + case SectorReference: return std::make_unique(map); + case InvalidLine: return std::make_unique(map); + case MissingTagged: return std::make_unique(map); + case UnknownSector: return std::make_unique(map); + case UnknownSpecial: return std::make_unique(map); + case ObsoleteThing: return std::make_unique(map); + default: return std::make_unique(map); } } diff --git a/src/MapEditor/MapChecks.h b/src/MapEditor/MapChecks.h index 94cbbfef9..693e3c509 100644 --- a/src/MapEditor/MapChecks.h +++ b/src/MapEditor/MapChecks.h @@ -5,7 +5,11 @@ namespace slade class SLADEMap; class MapTextureManager; class MapObject; -class MapEditContext; + +namespace mapeditor +{ + class MapEditContext; +} class MapCheck { @@ -34,11 +38,11 @@ class MapCheck MapCheck(SLADEMap* map) : map_{ map } {} virtual ~MapCheck() = default; - virtual void doCheck() = 0; - virtual unsigned nProblems() = 0; - virtual string problemDesc(unsigned index) = 0; - virtual bool fixProblem(unsigned index, unsigned fix_type, MapEditContext* editor) = 0; - virtual MapObject* getObject(unsigned index) = 0; + virtual void doCheck() = 0; + virtual unsigned nProblems() = 0; + virtual string problemDesc(unsigned index) = 0; + virtual bool fixProblem(unsigned index, unsigned fix_type, mapeditor::MapEditContext* editor) = 0; + virtual MapObject* getObject(unsigned index) = 0; virtual string progressText() { return "Checking..."; } virtual string fixText(unsigned fix_type, unsigned index) { return ""; } diff --git a/src/MapEditor/MapClipboardItems.cpp b/src/MapEditor/MapClipboardItems.cpp new file mode 100644 index 000000000..5e87280f4 --- /dev/null +++ b/src/MapEditor/MapClipboardItems.cpp @@ -0,0 +1,432 @@ + +// ----------------------------------------------------------------------------- +// SLADE - It's a Doom Editor +// Copyright(C) 2008 - 2024 Simon Judd +// +// Email: sirjuddington@gmail.com +// Web: http://slade.mancubus.net +// Filename: MapClipboardItems.cpp +// Description: Map Editor clipboard item implementations +// +// This program is free software; you can redistribute it and/or modify it +// under the terms of the GNU General Public License as published by the Free +// Software Foundation; either version 2 of the License, or (at your option) +// any later version. +// +// This program is distributed in the hope that it will be useful, but WITHOUT +// ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or +// FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for +// more details. +// +// You should have received a copy of the GNU General Public License along with +// this program; if not, write to the Free Software Foundation, Inc., +// 51 Franklin Street, Fifth Floor, Boston, MA 02110 - 1301, USA. +// ----------------------------------------------------------------------------- + + +// ----------------------------------------------------------------------------- +// +// Includes +// +// ----------------------------------------------------------------------------- +#include "Main.h" +#include "MapClipboardItems.h" +#include "Game/Configuration.h" +#include "SLADEMap/MapObject/MapLine.h" +#include "SLADEMap/MapObject/MapSector.h" +#include "SLADEMap/MapObject/MapSide.h" +#include "SLADEMap/MapObject/MapThing.h" +#include "SLADEMap/MapObject/MapVertex.h" +#include "SLADEMap/SLADEMap.h" + +using namespace slade; +using namespace mapeditor; + + +// ----------------------------------------------------------------------------- +// +// Functions +// +// ----------------------------------------------------------------------------- + + +// ----------------------------------------------------------------------------- +// Template function to find something in an associative map. +// M::mapped_type should be default constructible, or just provide +// a value for the third argument (the default value if not found). +// This really only works for value types right now, like maps to pointers. +// ----------------------------------------------------------------------------- +template +#if defined(_MSC_VER) && (_MSC_VER < 1500) +// MSVC++ 2005 will give error C2899 if attempting to compile "typename M::mapped_type()". +typename M::mapped_type findInMap(M& m, const typename M::key_type& k, typename M::mapped_type def = M::mapped_type()) +{ +#else +// On the other hand, other compilers will fail if this typename isn't there. +typename M::mapped_type findInMap( + M& m, + const typename M::key_type& k, + typename M::mapped_type def = typename M::mapped_type()) +{ +#endif + typename M::iterator i = m.find(k); + if (i == m.end()) + { + return const_cast(def); + } + else + { + return i->second; + } +} + + +// ----------------------------------------------------------------------------- +// +// MapArchClipboardItem Class Functions +// +// ----------------------------------------------------------------------------- + +// ----------------------------------------------------------------------------- +// Copies [lines] and all related map structures +// ----------------------------------------------------------------------------- +void MapArchClipboardItem::addLines(const vector& lines) +{ + // Get sectors and sides to copy + vector copy_sectors; + vector copy_sides; + for (auto line : lines) + { + auto s1 = line->s1(); + auto s2 = line->s2(); + + // Front side + if (s1) + { + copy_sides.push_back(s1); + if (std::find(copy_sectors.begin(), copy_sectors.end(), s1->sector()) == copy_sectors.end()) + copy_sectors.push_back(s1->sector()); + } + + // Back side + if (s2) + { + copy_sides.push_back(s2); + if (std::find(copy_sectors.begin(), copy_sectors.end(), s2->sector()) == copy_sectors.end()) + copy_sectors.push_back(s2->sector()); + } + } + + // Copy sectors + for (auto& sector : copy_sectors) + { + auto copy = std::make_unique(); + copy->copy(sector); + sectors_.push_back(std::move(copy)); + } + + // Copy sides + for (auto& side : copy_sides) + { + auto copy = std::make_unique(); + copy->copy(side); + + // Set relative sector + for (unsigned b = 0; b < copy_sectors.size(); b++) + { + if (side->sector() == copy_sectors[b]) + { + copy->setSector(sectors_[b].get()); + break; + } + } + + sides_.push_back(std::move(copy)); + } + + // Get vertices to copy (and determine midpoint) + double min_x = 9999999; + double max_x = -9999999; + double min_y = 9999999; + double max_y = -9999999; + vector copy_verts; + for (auto line : lines) + { + auto v1 = line->v1(); + auto v2 = line->v2(); + + // Add vertices to copy list + if (std::find(copy_verts.begin(), copy_verts.end(), v1) == copy_verts.end()) + copy_verts.push_back(v1); + if (std::find(copy_verts.begin(), copy_verts.end(), v2) == copy_verts.end()) + copy_verts.push_back(v2); + + // Update min/max + if (v1->xPos() < min_x) + min_x = v1->xPos(); + if (v1->xPos() > max_x) + max_x = v1->xPos(); + if (v1->yPos() < min_y) + min_y = v1->yPos(); + if (v1->yPos() > max_y) + max_y = v1->yPos(); + if (v2->xPos() < min_x) + min_x = v2->xPos(); + if (v2->xPos() > max_x) + max_x = v2->xPos(); + if (v2->yPos() < min_y) + min_y = v2->yPos(); + if (v2->yPos() > max_y) + max_y = v2->yPos(); + } + + // Determine midpoint + double mid_x = min_x + ((max_x - min_x) * 0.5); + double mid_y = min_y + ((max_y - min_y) * 0.5); + midpoint_.set(mid_x, mid_y); + + // Copy vertices + for (auto& vertex : copy_verts) + { + auto copy = std::make_unique(vertex->position() - midpoint_); + copy->copy(vertex); + vertices_.push_back(std::move(copy)); + } + + // Copy lines + for (auto line : lines) + { + // Get relative sides + MapSide* s1 = nullptr; + MapSide* s2 = nullptr; + bool s1_found = false; + bool s2_found = !(line->s2()); + for (unsigned i = 0; i < copy_sides.size(); i++) + { + if (line->s1() == copy_sides[i]) + { + s1 = sides_[i].get(); + s1_found = true; + } + if (line->s2() == copy_sides[i]) + { + s2 = sides_[i].get(); + s2_found = true; + } + + if (s1_found && s2_found) + break; + } + + // Get relative vertices + MapVertex* v1 = nullptr; + MapVertex* v2 = nullptr; + for (unsigned i = 0; i < copy_verts.size(); i++) + { + if (line->v1() == copy_verts[i]) + v1 = vertices_[i].get(); + if (line->v2() == copy_verts[i]) + v2 = vertices_[i].get(); + + if (v1 && v2) + break; + } + + // Copy line + auto copy = std::make_unique(v1, v2, s1, s2); + copy->copy(line); + lines_.push_back(std::move(copy)); + } +} + +// ----------------------------------------------------------------------------- +// Returns a string with info on what items are copied +// ----------------------------------------------------------------------------- +string MapArchClipboardItem::info() const +{ + return fmt::format( + "{} Vertices, {} Lines, {} Sides and {} Sectors", + vertices_.size(), + lines_.size(), + sides_.size(), + sectors_.size()); +} + +// ----------------------------------------------------------------------------- +// Pastes copied architecture to [map] at [position] +// ----------------------------------------------------------------------------- +vector MapArchClipboardItem::pasteToMap(SLADEMap* map, const Vec2d& position) const +{ + std::map vertMap; + std::map sectMap; + std::map sideMap; + // Not used yet... + // std::map lineMap; + + // Add vertices + vector new_verts; + for (auto& vertex : vertices_) + { + new_verts.push_back(map->createVertex(position + vertex->position())); + new_verts.back()->copy(vertex.get()); + vertMap[vertex.get()] = new_verts.back(); + } + + // Add sectors + for (auto& sector : sectors_) + { + auto new_sector = map->createSector(); + new_sector->copy(sector.get()); + sectMap[sector.get()] = new_sector; + } + + // Add sides + // int first_new_side = map->nSides(); + for (auto& side : sides_) + { + // Get relative sector + auto sector = findInMap(sectMap, side->sector()); + + auto new_side = map->createSide(sector); + new_side->copy(side.get()); + sideMap[side.get()] = new_side; + } + + // Add lines + // int first_new_line = map->nLines(); + for (auto& line : lines_) + { + // Get relative vertices + auto v1 = findInMap(vertMap, line->v1()); + auto v2 = findInMap(vertMap, line->v2()); + + if (!v1) + { + log::info(1, "no v1"); + continue; + } + if (!v2) + { + log::info(1, "no v2"); + } + + auto newline = map->createLine(v1, v2, true); + newline->copy(line.get()); + + // Set relative sides + auto newS1 = findInMap(sideMap, line->s1()); + auto newS2 = findInMap(sideMap, line->s2()); + if (newS1) + newline->setS1(newS1); + if (newS2) + newline->setS2(newS2); + + // Set important flags (needed when copying from Doom/Hexen format to UDMF) + // Won't be needed when proper map format conversion stuff is implemented + game::configuration().setLineBasicFlag("twosided", newline, map->currentFormat(), (newS1 && newS2)); + game::configuration().setLineBasicFlag("blocking", newline, map->currentFormat(), !newS2); + } + + // TODO: + // - Split lines + // - Merge lines + + //// Fix sector references + //// TODO: figure out what lines are 'outside' on copy, only fix said lines + // for (unsigned a = first_new_line; a < map->nLines(); a++) + //{ + // MapLine* line = map->getLine(a); + // MapSector* sec1 = map->getLineSideSector(line, true); + // MapSector* sec2 = map->getLineSideSector(line, false); + // int i1 = -1; + // int i2 = -2; + // if (sec1) i1 = sec1->getIndex(); + // if (sec2) i2 = sec2->getIndex(); + // map->setLineSector(a, i1, true); + // map->setLineSector(a, i2, false); + //} + + return new_verts; +} + +// ----------------------------------------------------------------------------- +// Adds all copied lines to [list] +// ----------------------------------------------------------------------------- +void MapArchClipboardItem::putLines(vector& list) const +{ + for (auto& line : lines_) + list.push_back(line.get()); +} + + +// ----------------------------------------------------------------------------- +// +// MapThingsClipboardItem Class Functions +// +// ----------------------------------------------------------------------------- + +// ----------------------------------------------------------------------------- +// Copies [things] +// ----------------------------------------------------------------------------- +void MapThingsClipboardItem::addThings(const vector& things) +{ + // Copy things + double min_x = 99999999; + double min_y = 99999999; + double max_x = -99999999; + double max_y = -99999999; + for (auto& thing : things) + { + auto copy_thing = std::make_unique(); + copy_thing->copy(thing); + things_.push_back(std::move(copy_thing)); + + if (thing->xPos() < min_x) + min_x = thing->xPos(); + if (thing->yPos() < min_y) + min_y = thing->yPos(); + if (thing->xPos() > max_x) + max_x = thing->xPos(); + if (thing->yPos() > max_y) + max_y = thing->yPos(); + } + + // Get midpoint + double mid_x = min_x + ((max_x - min_x) * 0.5); + double mid_y = min_y + ((max_y - min_y) * 0.5); + midpoint_.set(mid_x, mid_y); + + // Adjust thing positions + for (auto& thing : things_) + thing->move(thing->position() - midpoint_); +} + +// ----------------------------------------------------------------------------- +// Returns a string with info on what items are copied +// ----------------------------------------------------------------------------- +string MapThingsClipboardItem::info() const +{ + return fmt::format("{} Things", things_.size()); +} + +// ----------------------------------------------------------------------------- +// Pastes copied things to [map] at [position] +// ----------------------------------------------------------------------------- +void MapThingsClipboardItem::pasteToMap(SLADEMap* map, const Vec2d& position) const +{ + for (auto& thing : things_) + { + auto newthing = map->createThing({ 0., 0. }); + newthing->copy(thing.get()); + newthing->move(position + thing->position()); + } +} + +// ----------------------------------------------------------------------------- +// Adds all copied things to [list] +// ----------------------------------------------------------------------------- +void MapThingsClipboardItem::putThings(vector& list) const +{ + for (auto& thing : things_) + list.push_back(thing.get()); +} diff --git a/src/MapEditor/MapClipboardItems.h b/src/MapEditor/MapClipboardItems.h new file mode 100644 index 000000000..c0f2d6f82 --- /dev/null +++ b/src/MapEditor/MapClipboardItems.h @@ -0,0 +1,55 @@ +#pragma once + +#include "General/Clipboard.h" + +// Forward declarations +namespace slade +{ +class MapThing; +class MapSector; +class MapSide; +class SLADEMap; +class MapVertex; +class MapLine; +} // namespace slade + + +namespace slade::mapeditor +{ +class MapArchClipboardItem : public ClipboardItem +{ +public: + MapArchClipboardItem() : ClipboardItem(Type::MapArchitecture) {} + ~MapArchClipboardItem() override = default; + + void addLines(const vector& lines); + string info() const; + vector pasteToMap(SLADEMap* map, const Vec2d& position) const; + void putLines(vector& list) const; + Vec2d midpoint() const { return midpoint_; } + +private: + vector> vertices_; + vector> sides_; + vector> lines_; + vector> sectors_; + Vec2d midpoint_; +}; + +class MapThingsClipboardItem : public ClipboardItem +{ +public: + MapThingsClipboardItem() : ClipboardItem(Type::MapThings) {} + ~MapThingsClipboardItem() override = default; + + void addThings(const vector& things); + string info() const; + void pasteToMap(SLADEMap* map, const Vec2d& position) const; + void putThings(vector& list) const; + Vec2d midpoint() const { return midpoint_; } + +private: + vector> things_; + Vec2d midpoint_; +}; +} // namespace slade::mapeditor diff --git a/src/MapEditor/MapEditContext.cpp b/src/MapEditor/MapEditContext.cpp index 38c8b72f6..fe1c9e4aa 100644 --- a/src/MapEditor/MapEditContext.cpp +++ b/src/MapEditor/MapEditContext.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -34,11 +34,20 @@ #include "Main.h" #include "MapEditContext.h" #include "App.h" +#include "Edit/Edit2D.h" +#include "Edit/Edit3D.h" +#include "Edit/Input.h" +#include "Edit/LineDraw.h" +#include "Edit/MoveObjects.h" +#include "Edit/ObjectEdit.h" +#include "Game/ActionSpecial.h" #include "Game/Configuration.h" -#include "General/Clipboard.h" +#include "Game/Game.h" #include "General/Console.h" +#include "General/UI.h" #include "General/UndoRedo.h" #include "MapChecks.h" +#include "MapEditor.h" #include "MapEditor/Renderer/Overlays/InfoOverlay3d.h" #include "MapEditor/Renderer/Overlays/LineTextureOverlay.h" #include "MapEditor/Renderer/Overlays/QuickTextureOverlay3d.h" @@ -47,16 +56,31 @@ #include "MapEditor/UI/Dialogs/SectorSpecialDialog.h" #include "MapEditor/UI/Dialogs/ShowItemDialog.h" #include "MapTextureManager.h" +#include "OpenGL/View.h" +#include "Renderer/MapRenderer2D.h" +#include "Renderer/MapRenderer3D.h" +#include "Renderer/Overlays/LineInfoOverlay.h" +#include "Renderer/Overlays/SectorInfoOverlay.h" +#include "Renderer/Overlays/ThingInfoOverlay.h" +#include "Renderer/Overlays/VertexInfoOverlay.h" +#include "Renderer/Renderer.h" +#include "SLADEMap/MapObject/MapLine.h" +#include "SLADEMap/MapObject/MapSide.h" +#include "SLADEMap/MapObject/MapThing.h" +#include "SLADEMap/MapObject/MapVertex.h" +#include "SLADEMap/MapObjectList/LineList.h" +#include "SLADEMap/MapObjectList/SectorList.h" +#include "SLADEMap/MapObjectList/ThingList.h" +#include "SLADEMap/MapSpecials.h" +#include "SLADEMap/SLADEMap.h" #include "UI/MapCanvas.h" #include "UI/MapEditorWindow.h" #include "UndoSteps.h" #include "Utility/StringUtils.h" +#include using namespace slade; - -using mapeditor::Input; -using mapeditor::Mode; -using mapeditor::SectorMode; +using namespace mapeditor; // ----------------------------------------------------------------------------- @@ -82,44 +106,6 @@ EXTERN_CVAR(Int, flat_drawtype) EXTERN_CVAR(Bool, thing_preview_lights) -// ----------------------------------------------------------------------------- -// -// Functions -// -// ----------------------------------------------------------------------------- - - -// ----------------------------------------------------------------------------- -// Template function to find something in an associative map. -// M::mapped_type should be default constructible, or just provide -// a value for the third argument (the default value if not found). -// This really only works for value types right now, like maps to pointers. -// ----------------------------------------------------------------------------- -template -#if defined(_MSC_VER) && (_MSC_VER < 1500) -// MSVC++ 2005 will give error C2899 if attempting to compile "typename M::mapped_type()". -typename M::mapped_type findInMap(M& m, const typename M::key_type& k, typename M::mapped_type def = M::mapped_type()) -{ -#else -// On the other hand, other compilers will fail if this typename isn't there. -typename M::mapped_type findInMap( - M& m, - const typename M::key_type& k, - typename M::mapped_type def = typename M::mapped_type()) -{ -#endif - typename M::iterator i = m.find(k); - if (i == m.end()) - { - return const_cast(def); - } - else - { - return i->second; - } -} - - // ----------------------------------------------------------------------------- // // MapEditContext Class Functions @@ -130,9 +116,25 @@ typename M::mapped_type findInMap( // ----------------------------------------------------------------------------- // MapEditContext class constructor // ----------------------------------------------------------------------------- -MapEditContext::MapEditContext() +MapEditContext::MapEditContext() : + map_{ new SLADEMap() }, + edit_mode_{ Mode::Lines }, + edit_mode_prev_{ Mode::Lines }, + sector_mode_{ SectorMode::Both }, + move_objects_{ new MoveObjects(*this) }, + line_draw_{ new LineDraw(*this) }, + edit_2d_{ new Edit2D(*this) }, + edit_3d_{ new Edit3D(*this) }, + object_edit_{ new ObjectEdit(*this) }, + renderer_{ new Renderer(*this) }, + input_{ new Input(*this) }, + info_vertex_{ new VertexInfoOverlay() }, + info_line_{ new LineInfoOverlay() }, + info_sector_{ new SectorInfoOverlay() }, + info_thing_{ new ThingInfoOverlay() }, + info_3d_{ new InfoOverlay3D() } { - undo_manager_ = std::make_unique(&map_); + undo_manager_ = std::make_unique(map_.get()); } // ----------------------------------------------------------------------------- @@ -154,14 +156,14 @@ void MapEditContext::setEditMode(Mode mode) // Clear 3d mode undo manager etc on exiting 3d mode if (edit_mode_ == Mode::Visual && mode != Mode::Visual) { - info_3d_.reset(); - undo_manager_->createMergedLevel(edit_3d_.undoManager(), "3D Mode Editing"); - edit_3d_.undoManager()->clear(); + info_3d_->reset(); + undo_manager_->createMergedLevel(edit_3d_->undoManager(), "3D Mode Editing"); + edit_3d_->undoManager()->clear(); } // Set undo manager for history panel if (mode == Mode::Visual && edit_mode_ != Mode::Visual) - mapeditor::setUndoManager(edit_3d_.undoManager()); + mapeditor::setUndoManager(edit_3d_->undoManager()); else if (edit_mode_ == Mode::Visual && mode != Mode::Visual) mapeditor::setUndoManager(undo_manager_.get()); @@ -185,10 +187,10 @@ void MapEditContext::setEditMode(Mode mode) switch (edit_mode_) { case Mode::Vertices: addEditorMessage("Vertices mode"); break; - case Mode::Lines: addEditorMessage("Lines mode"); break; - case Mode::Sectors: addEditorMessage("Sectors mode (Normal)"); break; - case Mode::Things: addEditorMessage("Things mode"); break; - case Mode::Visual: addEditorMessage("3d mode"); break; + case Mode::Lines: addEditorMessage("Lines mode"); break; + case Mode::Sectors: addEditorMessage("Sectors mode (Normal)"); break; + case Mode::Things: addEditorMessage("Things mode"); break; + case Mode::Visual: addEditorMessage("3d mode"); break; }; if (edit_mode_ != Mode::Visual) @@ -237,7 +239,7 @@ void MapEditContext::setEditMode(Mode mode) SAction::fromId("mapw_mode_3d")->setChecked(); KeyBind::releaseAll(); lockMouse(true); - renderer_.renderer3D().refresh(); + renderer_->renderer3D().refresh(); } mapeditor::window()->refreshToolBar(); } @@ -269,9 +271,9 @@ void MapEditContext::cycleSectorEditMode() { switch (sector_mode_) { - case SectorMode::Both: setSectorEditMode(SectorMode::Floor); break; + case SectorMode::Both: setSectorEditMode(SectorMode::Floor); break; case SectorMode::Floor: setSectorEditMode(SectorMode::Ceiling); break; - default: setSectorEditMode(SectorMode::Both); + default: setSectorEditMode(SectorMode::Both); } } @@ -291,7 +293,7 @@ void MapEditContext::lockMouse(bool lock) bool MapEditContext::update(long frametime) { // Force an update if animations are active - if (renderer_.animationsActive() || selection_.hasHilight()) + if (renderer_->animationsActive() || selection_.hasHilight()) next_frame_length_ = 2; // Ignore if we aren't ready to update @@ -299,38 +301,41 @@ bool MapEditContext::update(long frametime) return false; // Get frame time multiplier - double mult = (double)frametime / 10.0f; + double mult = static_cast(frametime) / 10.0f; // 3d mode if (edit_mode_ == Mode::Visual && !overlayActive()) { // Update camera - if (input_.updateCamera3d(mult)) + if (input_->updateCamera3d(mult)) next_frame_length_ = 2; // Update status bar - auto pos = renderer_.renderer3D().camPosition(); - mapeditor::setStatusText(fmt::format("Position: ({}, {}, {})", (int)pos.x, (int)pos.y, (int)pos.z), 3); + auto pos = renderer_->renderer3D().camPosition(); + mapeditor::setStatusText( + fmt::format( + "Position: ({}, {}, {})", static_cast(pos.x), static_cast(pos.y), static_cast(pos.z)), + 3); // Update hilight - mapeditor::Item hl{ -1, mapeditor::ItemType::Any }; + Item hl{ -1, ItemType::Any }; if (!selection_.hilightLocked()) { auto old_hl = selection_.hilight(); - hl = renderer_.renderer3D().determineHilight(); + hl = renderer_->renderer3D().determineHilight(); if (selection_.setHilight(hl)) { // Update 3d info overlay if (info_overlay_3d && hl.index >= 0) { - info_3d_.update(hl, &map_); + info_3d_->update(hl, map_.get()); info_showing_ = true; } else info_showing_ = false; // Animation - renderer_.animateHilightChange(old_hl); + renderer_->animateHilightChange(old_hl); } } } @@ -340,16 +345,16 @@ bool MapEditContext::update(long frametime) { // Update hilight if needed auto prev_hl = selection_.hilight(); - if (input_.mouseState() == mapeditor::Input::MouseState::Normal /* && !mouse_movebegin*/) + if (input_->mouseState() == Input::MouseState::Normal /* && !mouse_movebegin*/) { auto old_hl = selection_.hilightedObject(); - if (selection_.updateHilight(input_.mousePosMap(), renderer_.view().scale()) && hilight_smooth) - renderer_.animateHilightChange({}, old_hl); + if (selection_.updateHilight(input_->mousePosMap(), renderer_->view().scale()) && hilight_smooth) + renderer_->animateHilightChange({}, old_hl); } // Do item moving if needed - if (input_.mouseState() == mapeditor::Input::MouseState::Move) - move_objects_.update(input_.mousePosMap()); + if (input_->mouseState() == Input::MouseState::Move) + move_objects_->update(input_->mousePosMap()); // Check if we have to update the info overlay if (selection_.hilight() != prev_hl) @@ -365,7 +370,7 @@ bool MapEditContext::update(long frametime) overlay_current_->update(frametime); // Update animations - renderer_.updateAnimations(mult); + renderer_->updateAnimations(mult); return true; } @@ -373,10 +378,10 @@ bool MapEditContext::update(long frametime) // ----------------------------------------------------------------------------- // Opens [map] // ----------------------------------------------------------------------------- -bool MapEditContext::openMap(Archive::MapDesc map) +bool MapEditContext::openMap(const MapDesc& map) { log::info("Opening map {}", map.name); - if (!map_.readMap(map)) + if (!map_->readMap(map)) return false; // Find camera thing @@ -384,9 +389,9 @@ bool MapEditContext::openMap(Archive::MapDesc map) { MapThing* cam = nullptr; MapThing* pstart = nullptr; - for (unsigned a = 0; a < map_.nThings(); a++) + for (unsigned a = 0; a < map_->nThings(); a++) { - auto thing = map_.thing(a); + auto thing = map_->thing(a); if (thing->type() == 32000) cam = thing; if (thing->type() == 1) @@ -398,21 +403,21 @@ bool MapEditContext::openMap(Archive::MapDesc map) // Set canvas 3d camera if (cam) - renderer_.setCameraThing(cam); + renderer_->setCameraThing(cam); else if (pstart) - renderer_.setCameraThing(pstart); + renderer_->setCameraThing(pstart); // Reset rendering data forceRefreshRenderer(); } - edit_3d_.setLinked(true, true); + edit_3d_->setLinked(true, true); updateStatusText(); updateThingLists(); // Process specials - map_.mapSpecials()->processMapSpecials(&(map_)); + map_->mapSpecials()->processMapSpecials(map_.get()); return true; } @@ -427,8 +432,8 @@ void MapEditContext::clearMap() selection_.clearHilight(); // Reset state - edit_3d_.setLinked(true, true); - input_.setMouseState(mapeditor::Input::MouseState::Normal); + edit_3d_->setLinked(true, true); + input_->setMouseState(Input::MouseState::Normal); mapeditor::resetObjectPropertiesPanel(); // Clear undo manager @@ -437,10 +442,10 @@ void MapEditContext::clearMap() // Clear other data updateTagged(); - info_3d_.reset(); + info_3d_->reset(); // Clear map - map_.clearMap(); + map_->clearMap(); } // ----------------------------------------------------------------------------- @@ -453,30 +458,30 @@ void MapEditContext::showItem(int index) // Show current selection/hilight if index is not specified if (index < 0) { - renderer_.viewFitToObjects(selection_.selectedObjects()); + renderer_->viewFitToObjects(selection_.selectedObjects()); return; } selection_.clear(); - int max; - mapeditor::ItemType type; + int max; + ItemType type; switch (edit_mode_) { case Mode::Vertices: - type = mapeditor::ItemType::Vertex; - max = map_.nVertices(); + type = ItemType::Vertex; + max = map_->nVertices(); break; case Mode::Lines: - type = mapeditor::ItemType::Line; - max = map_.nLines(); + type = ItemType::Line; + max = map_->nLines(); break; case Mode::Sectors: - type = mapeditor::ItemType::Sector; - max = map_.nSectors(); + type = ItemType::Sector; + max = map_->nSectors(); break; case Mode::Things: - type = mapeditor::ItemType::Thing; - max = map_.nThings(); + type = ItemType::Thing; + max = map_->nThings(); break; default: return; } @@ -484,7 +489,7 @@ void MapEditContext::showItem(int index) if (index < max) { selection_.select({ index, type }); - renderer_.viewFitToObjects(selection_.selectedObjects(false)); + renderer_->viewFitToObjects(selection_.selectedObjects(false)); } } @@ -496,10 +501,10 @@ string MapEditContext::modeString(bool plural) const switch (edit_mode_) { case Mode::Vertices: return plural ? "Vertices" : "Vertex"; - case Mode::Lines: return plural ? "Lines" : "Line"; - case Mode::Sectors: return plural ? "Sectors" : "Sector"; - case Mode::Things: return plural ? "Things" : "Thing"; - case Mode::Visual: return "3D"; + case Mode::Lines: return plural ? "Lines" : "Line"; + case Mode::Sectors: return plural ? "Sectors" : "Sector"; + case Mode::Things: return plural ? "Things" : "Thing"; + case Mode::Visual: return "3D"; }; return plural ? "Items" : "Object"; @@ -511,8 +516,8 @@ string MapEditContext::modeString(bool plural) const void MapEditContext::updateThingLists() { pathed_things_.clear(); - map_.things().putAllPathed(pathed_things_); - map_.setThingsUpdated(); + map_->things().putAllPathed(pathed_things_); + map_->setThingsUpdated(); } // ----------------------------------------------------------------------------- @@ -526,19 +531,19 @@ void MapEditContext::setCursor(ui::MouseCursor cursor) const // ----------------------------------------------------------------------------- // Forces a full refresh of the 2d/3d renderers // ----------------------------------------------------------------------------- -void MapEditContext::forceRefreshRenderer() +void MapEditContext::forceRefreshRenderer() const { // Update 3d mode info overlay if needed if (edit_mode_ == Mode::Visual) { - auto hl = renderer_.renderer3D().determineHilight(); - info_3d_.update(hl, &map_); + auto hl = renderer_->renderer3D().determineHilight(); + info_3d_->update(hl, map_.get()); } if (!canvas_->setActive()) return; - renderer_.forceUpdate(); + renderer_->forceUpdate(); } // ----------------------------------------------------------------------------- @@ -565,23 +570,23 @@ void MapEditContext::updateTagged() if (edit_mode_ == Mode::Lines) { type = SLADEMap::LINEDEFS; - tag = map_.line(hilight_item)->id(); + tag = map_->line(hilight_item)->id(); } else if (edit_mode_ == Mode::Things) { type = SLADEMap::THINGS; - tag = map_.thing(hilight_item)->id(); - ttype = map_.thing(hilight_item)->type(); + tag = map_->thing(hilight_item)->id(); + ttype = map_->thing(hilight_item)->type(); } else if (edit_mode_ == Mode::Sectors) { type = SLADEMap::SECTORS; - tag = map_.sector(hilight_item)->tag(); + tag = map_->sector(hilight_item)->tag(); } if (tag) { - map_.lines().putAllTaggingWithId(tag, type, tagging_lines_); - map_.things().putAllTaggingWithId(tag, type, tagging_things_, ttype); + map_->lines().putAllTaggingWithId(tag, type, tagging_lines_); + map_->things().putAllTaggingWithId(tag, type, tagging_things_, ttype); } // Gather affected objects @@ -596,7 +601,7 @@ void MapEditContext::updateTagged() tag = arg2 = arg3 = arg4 = arg5 = tid = 0; if (edit_mode_ == Mode::Lines) { - auto line = map_.line(hilight_item); + auto line = map_->line(hilight_item); if (line->s2()) back = line->s2()->sector(); if (line->s1()) @@ -613,7 +618,7 @@ void MapEditContext::updateTagged() } else // edit_mode == Mode::Things { - auto thing = map_.thing(hilight_item); + auto thing = map_->thing(hilight_item); if (game::configuration().thingType(thing->type()).flags() & game::ThingType::Flags::Script) needs_tag = TagType::None; else @@ -632,7 +637,7 @@ void MapEditContext::updateTagged() // Sector tag if (needs_tag == TagType::Sector || (needs_tag == TagType::SectorAndBack && tag > 0)) - map_.sectors().putAllWithId(tag, tagged_sectors_); + map_->sectors().putAllWithId(tag, tagged_sectors_); // Backside sector (for local doors) else if ((needs_tag == TagType::Back || needs_tag == TagType::SectorAndBack) && back) @@ -642,18 +647,18 @@ void MapEditContext::updateTagged() else if (needs_tag == TagType::SectorOrBack) { if (tag > 0) - map_.sectors().putAllWithId(tag, tagged_sectors_); + map_->sectors().putAllWithId(tag, tagged_sectors_); else if (back) tagged_sectors_.push_back(back); } // Thing ID else if (needs_tag == TagType::Thing) - map_.things().putAllWithId(tag, tagged_things_); + map_->things().putAllWithId(tag, tagged_things_); // Line ID else if (needs_tag == TagType::Line) - map_.lines().putAllWithId(tag, tagged_lines_); + map_->lines().putAllWithId(tag, tagged_lines_); // ZDoom quirkiness else if (needs_tag != TagType::None) @@ -671,77 +676,77 @@ void MapEditContext::updateTagged() if ((thingtag | sectag) == 0) break; else if (thingtag == 0) - map_.sectors().putAllWithId(sectag, tagged_sectors_); + map_->sectors().putAllWithId(sectag, tagged_sectors_); else if (sectag == 0) - map_.things().putAllWithId(thingtag, tagged_things_); + map_->things().putAllWithId(thingtag, tagged_things_); else // neither thingtag nor sectag are 0 - map_.putThingsWithIdInSectorTag(thingtag, sectag, tagged_things_); + map_->putThingsWithIdInSectorTag(thingtag, sectag, tagged_things_); } break; case TagType::Thing1Thing2Thing3: if (arg3) - map_.things().putAllWithId(arg3, tagged_things_); + map_->things().putAllWithId(arg3, tagged_things_); case TagType::Thing1Thing2: if (arg2) - map_.things().putAllWithId(arg2, tagged_things_); + map_->things().putAllWithId(arg2, tagged_things_); case TagType::Thing1Thing4: if (tag) - map_.things().putAllWithId(tag, tagged_things_); + map_->things().putAllWithId(tag, tagged_things_); case TagType::Thing4: if (needs_tag == TagType::Thing1Thing4 || needs_tag == TagType::Thing4) if (arg4) - map_.things().putAllWithId(arg4, tagged_things_); + map_->things().putAllWithId(arg4, tagged_things_); break; case TagType::Thing5: if (arg5) - map_.things().putAllWithId(arg5, tagged_things_); + map_->things().putAllWithId(arg5, tagged_things_); break; case TagType::LineNegative: if (tag) - map_.lines().putAllWithId(abs(tag), tagged_lines_); + map_->lines().putAllWithId(abs(tag), tagged_lines_); break; case TagType::LineId1Line2: if (arg2) - map_.lines().putAllWithId(arg2, tagged_lines_); + map_->lines().putAllWithId(arg2, tagged_lines_); break; case TagType::Line1Sector2: if (tag) - map_.lines().putAllWithId(tag, tagged_lines_); + map_->lines().putAllWithId(tag, tagged_lines_); if (arg2) - map_.sectors().putAllWithId(arg2, tagged_sectors_); + map_->sectors().putAllWithId(arg2, tagged_sectors_); break; case TagType::Sector1Thing2Thing3Thing5: if (arg5) - map_.things().putAllWithId(arg5, tagged_things_); + map_->things().putAllWithId(arg5, tagged_things_); if (arg3) - map_.things().putAllWithId(arg3, tagged_things_); + map_->things().putAllWithId(arg3, tagged_things_); case TagType::Sector1Sector2Sector3Sector4: if (arg4) - map_.sectors().putAllWithId(arg4, tagged_sectors_); + map_->sectors().putAllWithId(arg4, tagged_sectors_); if (arg3) - map_.sectors().putAllWithId(arg3, tagged_sectors_); + map_->sectors().putAllWithId(arg3, tagged_sectors_); case TagType::Sector1Sector2: if (arg2) - map_.sectors().putAllWithId(arg2, tagged_sectors_); + map_->sectors().putAllWithId(arg2, tagged_sectors_); if (tag) - map_.sectors().putAllWithId(tag, tagged_sectors_); + map_->sectors().putAllWithId(tag, tagged_sectors_); break; case TagType::Sector2Is3Line: if (tag) { if (arg2 == 3) - map_.lines().putAllWithId(tag, tagged_lines_); + map_->lines().putAllWithId(tag, tagged_lines_); else - map_.sectors().putAllWithId(tag, tagged_sectors_); + map_->sectors().putAllWithId(tag, tagged_sectors_); } break; case TagType::Patrol: if (tid) - map_.things().putAllWithId(tid, tagged_things_, 0, 9047); + map_->things().putAllWithId(tid, tagged_things_, 0, 9047); break; case TagType::Interpolation: if (tid) - map_.things().putAllWithId(tid, tagged_things_, 0, 9075); + map_->things().putAllWithId(tid, tagged_things_, 0, 9075); break; default: break; } @@ -761,7 +766,7 @@ void MapEditContext::selectionUpdated() last_undo_level_ = ""; - renderer_.animateSelectionChange(selection_); + renderer_->animateSelectionChange(selection_); updateStatusText(); } @@ -783,7 +788,7 @@ void MapEditContext::incrementGrid() if (grid_size_ > 20) grid_size_ = 20; - addEditorMessage(fmt::format("Grid Size: {}x{}", (int)gridSize(), (int)gridSize())); + addEditorMessage(fmt::format("Grid Size: {}x{}", static_cast(gridSize()), static_cast(gridSize()))); updateStatusText(); } @@ -793,11 +798,11 @@ void MapEditContext::incrementGrid() void MapEditContext::decrementGrid() { grid_size_--; - int mingrid = (map_.currentFormat() == MapFormat::UDMF) ? 0 : 4; + int mingrid = (map_->currentFormat() == MapFormat::UDMF) ? 0 : 4; if (grid_size_ < mingrid) grid_size_ = mingrid; - addEditorMessage(fmt::format("Grid Size: {}x{}", (int)gridSize(), (int)gridSize())); + addEditorMessage(fmt::format("Grid Size: {}x{}", static_cast(gridSize()), static_cast(gridSize()))); updateStatusText(); } @@ -809,7 +814,7 @@ double MapEditContext::snapToGrid(double position, bool force) const { if (!force && !grid_snap_) { - if (map_.currentFormat() == MapFormat::UDMF) + if (map_->currentFormat() == MapFormat::UDMF) return position; else return ceil(position - 0.5); @@ -822,7 +827,7 @@ double MapEditContext::snapToGrid(double position, bool force) const // Used for pasting. Given an [origin] point and the current [mouse_pos], snaps // in such a way that the mouse is a number of grid units away from the origin. // ----------------------------------------------------------------------------- -Vec2d MapEditContext::relativeSnapToGrid(Vec2d origin, Vec2d mouse_pos) const +Vec2d MapEditContext::relativeSnapToGrid(const Vec2d& origin, const Vec2d& mouse_pos) const { auto delta = mouse_pos - origin; delta.x = snapToGrid(delta.x, false); @@ -847,7 +852,7 @@ int MapEditContext::beginTagEdit() // Get current tag int tag = lines[0]->arg(0); if (tag == 0) - tag = map_.sectors().firstFreeId(); + tag = map_->sectors().firstFreeId(); current_tag_ = tag; // Clear tagged lists @@ -856,9 +861,9 @@ int MapEditContext::beginTagEdit() tagged_things_.clear(); // Sector tag (for now, 2 will be thing id tag) - for (unsigned a = 0; a < map_.nSectors(); a++) + for (unsigned a = 0; a < map_->nSectors(); a++) { - auto sector = map_.sector(a); + auto sector = map_->sector(a); if (sector->tag() == current_tag_) tagged_sectors_.push_back(sector); } @@ -869,9 +874,9 @@ int MapEditContext::beginTagEdit() // Applies the current tag edit tag to the sector at [x,y], or clears the // sector tag if it is already the same // ----------------------------------------------------------------------------- -void MapEditContext::tagSectorAt(Vec2d pos) +void MapEditContext::tagSectorAt(const Vec2d& pos) { - auto sector = map_.sectors().atPos(pos); + auto sector = map_->sectors().atPos(pos); if (!sector) return; @@ -907,9 +912,9 @@ void MapEditContext::endTagEdit(bool accept) beginUndoRecord("Tag Edit", true, false, false); // Clear sector tags - for (unsigned a = 0; a < map_.nSectors(); a++) + for (unsigned a = 0; a < map_->nSectors(); a++) { - auto sector = map_.sector(a); + auto sector = map_->sector(a); if (sector->tag() == current_tag_) sector->setTag(0); } @@ -947,7 +952,7 @@ void MapEditContext::endTagEdit(bool accept) const string& MapEditContext::editorMessage(int index) { // Check index - if (index < 0 || index >= (int)editor_messages_.size()) + if (index < 0 || index >= static_cast(editor_messages_.size())) return strutil::EMPTY; return editor_messages_[index].message; @@ -956,10 +961,10 @@ const string& MapEditContext::editorMessage(int index) // ----------------------------------------------------------------------------- // Returns the amount of time the editor message at [index] has been active // ----------------------------------------------------------------------------- -long MapEditContext::editorMessageTime(int index) +long MapEditContext::editorMessageTime(int index) const { // Check index - if (index < 0 || index >= (int)editor_messages_.size()) + if (index < 0 || index >= static_cast(editor_messages_.size())) return -1; return app::runTimer() - editor_messages_[index].act_time; @@ -1046,7 +1051,7 @@ bool MapEditContext::handleKeyBind(string_view key, Vec2d position) // Copy else if (key == "copy") - edit_2d_.copy(); + edit_2d_->copy(); else handled = false; @@ -1060,45 +1065,45 @@ bool MapEditContext::handleKeyBind(string_view key, Vec2d position) { // Height changes if (key == "me2d_sector_floor_up8") - edit_2d_.changeSectorHeight(8, true, false); + edit_2d_->changeSectorHeight(8, true, false); else if (key == "me2d_sector_floor_up") - edit_2d_.changeSectorHeight(1, true, false); + edit_2d_->changeSectorHeight(1, true, false); else if (key == "me2d_sector_floor_down8") - edit_2d_.changeSectorHeight(-8, true, false); + edit_2d_->changeSectorHeight(-8, true, false); else if (key == "me2d_sector_floor_down") - edit_2d_.changeSectorHeight(-1, true, false); + edit_2d_->changeSectorHeight(-1, true, false); else if (key == "me2d_sector_ceil_up8") - edit_2d_.changeSectorHeight(8, false, true); + edit_2d_->changeSectorHeight(8, false, true); else if (key == "me2d_sector_ceil_up") - edit_2d_.changeSectorHeight(1, false, true); + edit_2d_->changeSectorHeight(1, false, true); else if (key == "me2d_sector_ceil_down8") - edit_2d_.changeSectorHeight(-8, false, true); + edit_2d_->changeSectorHeight(-8, false, true); else if (key == "me2d_sector_ceil_down") - edit_2d_.changeSectorHeight(-1, false, true); + edit_2d_->changeSectorHeight(-1, false, true); else if (key == "me2d_sector_height_up8") - edit_2d_.changeSectorHeight(8, true, true); + edit_2d_->changeSectorHeight(8, true, true); else if (key == "me2d_sector_height_up") - edit_2d_.changeSectorHeight(1, true, true); + edit_2d_->changeSectorHeight(1, true, true); else if (key == "me2d_sector_height_down8") - edit_2d_.changeSectorHeight(-8, true, true); + edit_2d_->changeSectorHeight(-8, true, true); else if (key == "me2d_sector_height_down") - edit_2d_.changeSectorHeight(-1, true, true); + edit_2d_->changeSectorHeight(-1, true, true); // Light changes else if (key == "me2d_sector_light_up16") - edit_2d_.changeSectorLight(true, false); + edit_2d_->changeSectorLight(true, false); else if (key == "me2d_sector_light_up") - edit_2d_.changeSectorLight(true, true); + edit_2d_->changeSectorLight(true, true); else if (key == "me2d_sector_light_down16") - edit_2d_.changeSectorLight(false, false); + edit_2d_->changeSectorLight(false, false); else if (key == "me2d_sector_light_down") - edit_2d_.changeSectorLight(false, true); + edit_2d_->changeSectorLight(false, true); // Join else if (key == "me2d_sector_join") - edit_2d_.joinSectors(true); + edit_2d_->joinSectors(true); else if (key == "me2d_sector_join_keep") - edit_2d_.joinSectors(false); + edit_2d_->joinSectors(false); else return false; @@ -1108,7 +1113,7 @@ bool MapEditContext::handleKeyBind(string_view key, Vec2d position) else if (strutil::startsWith(key, "me3d_") && edit_mode_ == Mode::Visual) { // Check is UDMF - bool is_udmf = map_.currentFormat() == MapFormat::UDMF; + bool is_udmf = map_->currentFormat() == MapFormat::UDMF; // Clear selection if (key == "me3d_clear_selection") @@ -1124,7 +1129,7 @@ bool MapEditContext::handleKeyBind(string_view key, Vec2d position) addEditorMessage("Unlinked light levels not supported in this game configuration"); else { - if (edit_3d_.toggleLightLink()) + if (edit_3d_->toggleLightLink()) addEditorMessage("Flat light levels linked"); else addEditorMessage("Flat light levels unlinked"); @@ -1138,7 +1143,7 @@ bool MapEditContext::handleKeyBind(string_view key, Vec2d position) addEditorMessage("Unlinked wall offsets not supported in this game configuration"); else { - if (edit_3d_.toggleOffsetLink()) + if (edit_3d_->toggleOffsetLink()) addEditorMessage("Wall offsets linked"); else addEditorMessage("Wall offsets unlinked"); @@ -1147,111 +1152,111 @@ bool MapEditContext::handleKeyBind(string_view key, Vec2d position) // Copy/paste else if (key == "me3d_copy_tex_type") - edit_3d_.copy(Edit3D::CopyType::TexType); + edit_3d_->copy(Edit3D::CopyType::TexType); else if (key == "me3d_paste_tex_type") - edit_3d_.paste(Edit3D::CopyType::TexType); + edit_3d_->paste(Edit3D::CopyType::TexType); else if (key == "me3d_paste_tex_adj") - edit_3d_.floodFill(Edit3D::CopyType::TexType); + edit_3d_->floodFill(Edit3D::CopyType::TexType); // Delete texture else if (key == "me3d_delete_texture") - edit_3d_.deleteTexture(); + edit_3d_->deleteTexture(); // Light changes else if (key == "me3d_light_up16") - edit_3d_.changeSectorLight(16); + edit_3d_->changeSectorLight(16); else if (key == "me3d_light_up") - edit_3d_.changeSectorLight(1); + edit_3d_->changeSectorLight(1); else if (key == "me3d_light_down16") - edit_3d_.changeSectorLight(-16); + edit_3d_->changeSectorLight(-16); else if (key == "me3d_light_down") - edit_3d_.changeSectorLight(-1); + edit_3d_->changeSectorLight(-1); // Wall/Flat offset changes else if (key == "me3d_xoff_up8") - edit_3d_.changeOffset(8, true); + edit_3d_->changeOffset(8, true); else if (key == "me3d_xoff_up") - edit_3d_.changeOffset(1, true); + edit_3d_->changeOffset(1, true); else if (key == "me3d_xoff_down8") - edit_3d_.changeOffset(-8, true); + edit_3d_->changeOffset(-8, true); else if (key == "me3d_xoff_down") - edit_3d_.changeOffset(-1, true); + edit_3d_->changeOffset(-1, true); else if (key == "me3d_yoff_up8") - edit_3d_.changeOffset(8, false); + edit_3d_->changeOffset(8, false); else if (key == "me3d_yoff_up") - edit_3d_.changeOffset(1, false); + edit_3d_->changeOffset(1, false); else if (key == "me3d_yoff_down8") - edit_3d_.changeOffset(-8, false); + edit_3d_->changeOffset(-8, false); else if (key == "me3d_yoff_down") - edit_3d_.changeOffset(-1, false); + edit_3d_->changeOffset(-1, false); // Height changes else if (key == "me3d_flat_height_up8") - edit_3d_.changeSectorHeight(8); + edit_3d_->changeSectorHeight(8); else if (key == "me3d_flat_height_up") - edit_3d_.changeSectorHeight(1); + edit_3d_->changeSectorHeight(1); else if (key == "me3d_flat_height_down8") - edit_3d_.changeSectorHeight(-8); + edit_3d_->changeSectorHeight(-8); else if (key == "me3d_flat_height_down") - edit_3d_.changeSectorHeight(-1); + edit_3d_->changeSectorHeight(-1); // Thing height changes else if (key == "me3d_thing_up") - edit_3d_.changeThingZ(1); + edit_3d_->changeThingZ(1); else if (key == "me3d_thing_up8") - edit_3d_.changeThingZ(8); + edit_3d_->changeThingZ(8); else if (key == "me3d_thing_down") - edit_3d_.changeThingZ(-1); + edit_3d_->changeThingZ(-1); else if (key == "me3d_thing_down8") - edit_3d_.changeThingZ(-8); + edit_3d_->changeThingZ(-8); // Generic height change else if (key == "me3d_generic_up8") - edit_3d_.changeHeight(8); + edit_3d_->changeHeight(8); else if (key == "me3d_generic_up") - edit_3d_.changeHeight(1); + edit_3d_->changeHeight(1); else if (key == "me3d_generic_down8") - edit_3d_.changeHeight(-8); + edit_3d_->changeHeight(-8); else if (key == "me3d_generic_down") - edit_3d_.changeHeight(-1); + edit_3d_->changeHeight(-1); // Wall/Flat scale changes else if (key == "me3d_scalex_up_l" && is_udmf) - edit_3d_.changeScale(1, true); + edit_3d_->changeScale(1, true); else if (key == "me3d_scalex_up_s" && is_udmf) - edit_3d_.changeScale(0.1, true); + edit_3d_->changeScale(0.1, true); else if (key == "me3d_scalex_down_l" && is_udmf) - edit_3d_.changeScale(-1, true); + edit_3d_->changeScale(-1, true); else if (key == "me3d_scalex_down_s" && is_udmf) - edit_3d_.changeScale(-0.1, true); + edit_3d_->changeScale(-0.1, true); else if (key == "me3d_scaley_up_l" && is_udmf) - edit_3d_.changeScale(1, false); + edit_3d_->changeScale(1, false); else if (key == "me3d_scaley_up_s" && is_udmf) - edit_3d_.changeScale(0.1, false); + edit_3d_->changeScale(0.1, false); else if (key == "me3d_scaley_down_l" && is_udmf) - edit_3d_.changeScale(-1, false); + edit_3d_->changeScale(-1, false); else if (key == "me3d_scaley_down_s" && is_udmf) - edit_3d_.changeScale(-0.1, false); + edit_3d_->changeScale(-0.1, false); // Auto-align else if (key == "me3d_wall_autoalign_x") - edit_3d_.autoAlignX(selection_.hilight()); + edit_3d_->autoAlignX(selection_.hilight()); // Reset wall offsets else if (key == "me3d_wall_reset") - edit_3d_.resetOffsets(); + edit_3d_->resetOffsets(); // Toggle lower unpegged else if (key == "me3d_wall_unpeg_lower") - edit_3d_.toggleUnpegged(true); + edit_3d_->toggleUnpegged(true); // Toggle upper unpegged else if (key == "me3d_wall_unpeg_upper") - edit_3d_.toggleUnpegged(false); + edit_3d_->toggleUnpegged(false); // Remove thing else if (key == "me3d_thing_remove") - edit_3d_.deleteThing(); + edit_3d_->deleteThing(); else return false; @@ -1266,7 +1271,7 @@ bool MapEditContext::handleKeyBind(string_view key, Vec2d position) // Updates the map object properties panel and current info overlay from the // current hilight/selection // ----------------------------------------------------------------------------- -void MapEditContext::updateDisplay() +void MapEditContext::updateDisplay() const { // Update map object properties panel auto selection = selection_.selectedObjects(); @@ -1290,24 +1295,24 @@ void MapEditContext::updateStatusText() const switch (edit_mode_) { case Mode::Vertices: mode += "Vertices"; break; - case Mode::Lines: mode += "Lines"; break; - case Mode::Sectors: mode += "Sectors"; break; - case Mode::Things: mode += "Things"; break; - case Mode::Visual: mode += "3D"; break; + case Mode::Lines: mode += "Lines"; break; + case Mode::Sectors: mode += "Sectors"; break; + case Mode::Things: mode += "Things"; break; + case Mode::Visual: mode += "3D"; break; } if (edit_mode_ == Mode::Sectors) { switch (sector_mode_) { - case SectorMode::Both: mode += " (Normal)"; break; - case SectorMode::Floor: mode += " (Floors)"; break; + case SectorMode::Both: mode += " (Normal)"; break; + case SectorMode::Floor: mode += " (Floors)"; break; case SectorMode::Ceiling: mode += " (Ceilings)"; break; } } if (edit_mode_ != Mode::Visual && !selection_.empty()) - mode += fmt::format(" ({} selected)", (int)selection_.size()); + mode += fmt::format(" ({} selected)", static_cast(selection_.size())); mapeditor::setStatusText(mode, 1); @@ -1337,7 +1342,7 @@ void MapEditContext::updateStatusText() const void MapEditContext::beginUndoRecord(string_view name, bool mod, bool create, bool del) { // Setup - UndoManager* manager = (edit_mode_ == Mode::Visual) ? edit_3d_.undoManager() : undo_manager_.get(); + UndoManager* manager = (edit_mode_ == Mode::Visual) ? edit_3d_->undoManager() : undo_manager_.get(); if (manager->currentlyRecording()) return; undo_modified_ = mod; @@ -1351,7 +1356,7 @@ void MapEditContext::beginUndoRecord(string_view name, bool mod, bool create, bo if (undo_modified_) MapObject::beginPropBackup(app::runTimer()); if (undo_deleted_ || undo_created_) - us_create_delete_ = std::make_unique(); + us_create_delete_ = std::make_unique(); // Make sure all modified objects will be picked up wxMilliSleep(5); @@ -1379,7 +1384,7 @@ void MapEditContext::beginUndoRecordLocked(string_view name, bool mod, bool crea // ----------------------------------------------------------------------------- void MapEditContext::endUndoRecord(bool success) { - auto manager = (edit_mode_ == Mode::Visual) ? edit_3d_.undoManager() : undo_manager_.get(); + auto manager = (edit_mode_ == Mode::Visual) ? edit_3d_->undoManager() : undo_manager_.get(); if (manager->currentlyRecording()) { @@ -1388,10 +1393,10 @@ void MapEditContext::endUndoRecord(bool success) bool modified = false; bool created_deleted = false; if (undo_modified_) - modified = manager->recordUndoStep(std::make_unique()); + modified = manager->recordUndoStep(std::make_unique()); if (undo_created_ || undo_deleted_) { - auto ustep = dynamic_cast(us_create_delete_.get()); + auto ustep = dynamic_cast(us_create_delete_.get()); ustep->checkChanges(); created_deleted = manager->recordUndoStep(std::move(us_create_delete_)); } @@ -1401,7 +1406,7 @@ void MapEditContext::endUndoRecord(bool success) } updateThingLists(); us_create_delete_.reset(nullptr); - map_.recomputeSpecials(); + map_->recomputeSpecials(); } // ----------------------------------------------------------------------------- @@ -1409,8 +1414,8 @@ void MapEditContext::endUndoRecord(bool success) // ----------------------------------------------------------------------------- void MapEditContext::recordPropertyChangeUndoStep(MapObject* object) const { - auto manager = (edit_mode_ == Mode::Visual) ? edit_3d_.undoManager() : undo_manager_.get(); - manager->recordUndoStep(std::make_unique(object)); + auto manager = (edit_mode_ == Mode::Visual) ? edit_3d_->undoManager() : undo_manager_.get(); + manager->recordUndoStep(std::make_unique(object)); } // ----------------------------------------------------------------------------- @@ -1419,7 +1424,7 @@ void MapEditContext::recordPropertyChangeUndoStep(MapObject* object) const void MapEditContext::doUndo() { // Don't undo if the input state isn't normal - if (input_.mouseState() != Input::MouseState::Normal) + if (input_->mouseState() != Input::MouseState::Normal) return; // Clear selection first, since part of it may become invalid @@ -1427,7 +1432,7 @@ void MapEditContext::doUndo() // Undo auto time = app::runTimer() - 1; - auto manager = (edit_mode_ == Mode::Visual) ? edit_3d_.undoManager() : undo_manager_.get(); + auto manager = (edit_mode_ == Mode::Visual) ? edit_3d_->undoManager() : undo_manager_.get(); auto undo_name = manager->undo(); // Editor message @@ -1437,14 +1442,14 @@ void MapEditContext::doUndo() // Refresh stuff // updateTagged(); - map_.rebuildConnectedLines(); - map_.rebuildConnectedSides(); - map_.setGeometryUpdated(); - map_.updateGeometryInfo(time); + map_->rebuildConnectedLines(); + map_->rebuildConnectedSides(); + map_->setGeometryUpdated(); + map_->updateGeometryInfo(time); last_undo_level_ = ""; } updateThingLists(); - map_.recomputeSpecials(); + map_->recomputeSpecials(); } // ----------------------------------------------------------------------------- @@ -1453,7 +1458,7 @@ void MapEditContext::doUndo() void MapEditContext::doRedo() { // Don't redo if the input state isn't normal - if (input_.mouseState() != Input::MouseState::Normal) + if (input_->mouseState() != Input::MouseState::Normal) return; // Clear selection first, since part of it may become invalid @@ -1461,7 +1466,7 @@ void MapEditContext::doRedo() // Redo int time = app::runTimer() - 1; - auto manager = (edit_mode_ == Mode::Visual) ? edit_3d_.undoManager() : undo_manager_.get(); + auto manager = (edit_mode_ == Mode::Visual) ? edit_3d_->undoManager() : undo_manager_.get(); auto undo_name = manager->redo(); // Editor message @@ -1471,14 +1476,14 @@ void MapEditContext::doRedo() // Refresh stuff // updateTagged(); - map_.rebuildConnectedLines(); - map_.rebuildConnectedSides(); - map_.setGeometryUpdated(); - map_.updateGeometryInfo(time); + map_->rebuildConnectedLines(); + map_->rebuildConnectedSides(); + map_->setGeometryUpdated(); + map_->updateGeometryInfo(time); last_undo_level_ = ""; } updateThingLists(); - map_.recomputeSpecials(); + map_->recomputeSpecials(); } // ----------------------------------------------------------------------------- @@ -1500,10 +1505,10 @@ void MapEditContext::swapPlayerStart3d() { // Find player 1 start MapThing* pstart = nullptr; - for (int a = map_.nThings() - 1; a >= 0; a--) - if (map_.thing(a)->type() == 1) + for (int a = map_->nThings() - 1; a >= 0; a--) + if (map_->thing(a)->type() == 1) { - pstart = map_.thing(a); + pstart = map_->thing(a); break; } if (!pstart) @@ -1513,22 +1518,22 @@ void MapEditContext::swapPlayerStart3d() player_start_pos_.set(pstart->position()); player_start_dir_ = pstart->angle(); - auto campos = renderer_.cameraPos2D(); + auto campos = renderer_->cameraPos2D(); pstart->move(campos, false); - pstart->setAnglePoint(campos + renderer_.cameraDir2D(), false); + pstart->setAnglePoint(campos + renderer_->cameraDir2D(), false); } // ----------------------------------------------------------------------------- // Moves the player 1 start thing to [pos] // ----------------------------------------------------------------------------- -void MapEditContext::swapPlayerStart2d(Vec2d pos) +void MapEditContext::swapPlayerStart2d(const Vec2d& pos) { // Find player 1 start MapThing* pstart = nullptr; - for (int a = map_.nThings() - 1; a >= 0; a--) - if (map_.thing(a)->type() == 1) + for (int a = map_->nThings() - 1; a >= 0; a--) + if (map_->thing(a)->type() == 1) { - pstart = map_.thing(a); + pstart = map_->thing(a); break; } if (!pstart) @@ -1548,10 +1553,10 @@ void MapEditContext::resetPlayerStart() const { // Find player 1 start MapThing* pstart = nullptr; - for (int a = map_.nThings() - 1; a >= 0; a--) - if (map_.thing(a)->type() == 1) + for (int a = map_->nThings() - 1; a >= 0; a--) + if (map_->thing(a)->type() == 1) { - pstart = map_.thing(a); + pstart = map_->thing(a); break; } if (!pstart) @@ -1564,7 +1569,7 @@ void MapEditContext::resetPlayerStart() const // ----------------------------------------------------------------------------- // Opens the sector texture selection overlay // ----------------------------------------------------------------------------- -void MapEditContext::openSectorTextureOverlay(vector& sectors) +void MapEditContext::openSectorTextureOverlay(const vector& sectors) { overlay_current_ = std::make_unique(); dynamic_cast(overlay_current_.get())->openSectors(sectors); @@ -1579,8 +1584,8 @@ void MapEditContext::openQuickTextureOverlay() { overlay_current_ = std::make_unique(this); - renderer_.renderer3D().enableHilight(false); - renderer_.renderer3D().enableSelection(false); + renderer_->renderer3D().enableHilight(false); + renderer_->renderer3D().enableSelection(false); selection_.lockHilight(true); } } @@ -1613,31 +1618,31 @@ void MapEditContext::closeCurrentOverlay(bool cancel) const // ----------------------------------------------------------------------------- // Updates the current info overlay, depending on edit mode // ----------------------------------------------------------------------------- -void MapEditContext::updateInfoOverlay() +void MapEditContext::updateInfoOverlay() const { // Update info overlay depending on edit mode switch (edit_mode_) { - case Mode::Vertices: info_vertex_.update(selection_.hilightedVertex()); break; - case Mode::Lines: info_line_.update(selection_.hilightedLine()); break; - case Mode::Sectors: info_sector_.update(selection_.hilightedSector()); break; - case Mode::Things: info_thing_.update(selection_.hilightedThing()); break; - default: break; + case Mode::Vertices: info_vertex_->update(selection_.hilightedVertex()); break; + case Mode::Lines: info_line_->update(selection_.hilightedLine()); break; + case Mode::Sectors: info_sector_->update(selection_.hilightedSector()); break; + case Mode::Things: info_thing_->update(selection_.hilightedThing()); break; + default: break; } } // ----------------------------------------------------------------------------- // Draws the current info overlay // ----------------------------------------------------------------------------- -void MapEditContext::drawInfoOverlay(const Vec2i& size, float alpha) +void MapEditContext::drawInfoOverlay(const Vec2i& size, float alpha) const { switch (edit_mode_) { - case Mode::Vertices: info_vertex_.draw(size.y, size.x, alpha); return; - case Mode::Lines: info_line_.draw(size.y, size.x, alpha); return; - case Mode::Sectors: info_sector_.draw(size.y, size.x, alpha); return; - case Mode::Things: info_thing_.draw(size.y, size.x, alpha); return; - case Mode::Visual: info_3d_.draw(size.y, size.x, size.x * 0.5, alpha); return; + case Mode::Vertices: info_vertex_->draw(size.y, size.x, alpha); return; + case Mode::Lines: info_line_->draw(size.y, size.x, alpha); return; + case Mode::Sectors: info_sector_->draw(size.y, size.x, alpha); return; + case Mode::Things: info_thing_->draw(size.y, size.x, alpha); return; + case Mode::Visual: info_3d_->draw(size.y, size.x, size.x * 0.5, alpha); return; } } @@ -1648,7 +1653,7 @@ bool MapEditContext::handleAction(string_view id) { using namespace mapeditor; - auto mouse_state = input_.mouseState(); + auto mouse_state = input_->mouseState(); // Skip if canvas not shown if (!canvas_->IsShown()) @@ -1756,28 +1761,28 @@ bool MapEditContext::handleAction(string_view id) // Begin line drawing else if (id == "mapw_draw_lines" && mouse_state == Input::MouseState::Normal) { - line_draw_.begin(); + line_draw_->begin(); return true; } // Begin shape drawing else if (id == "mapw_draw_shape" && mouse_state == Input::MouseState::Normal) { - line_draw_.begin(true); + line_draw_->begin(true); return true; } // Begin object edit else if (id == "mapw_edit_objects" && mouse_state == Input::MouseState::Normal) { - object_edit_.begin(); + object_edit_->begin(); return true; } // Show full map else if (id == "mapw_show_fullmap") { - renderer_.viewFitToMap(); + renderer_->viewFitToMap(); return true; } @@ -1789,10 +1794,10 @@ bool MapEditContext::handleAction(string_view id) switch (editMode()) { case Mode::Vertices: dlg.setType(MapObject::Type::Vertex); break; - case Mode::Lines: dlg.setType(MapObject::Type::Line); break; - case Mode::Sectors: dlg.setType(MapObject::Type::Sector); break; - case Mode::Things: dlg.setType(MapObject::Type::Thing); break; - default: return true; + case Mode::Lines: dlg.setType(MapObject::Type::Line); break; + case Mode::Sectors: dlg.setType(MapObject::Type::Sector); break; + case Mode::Things: dlg.setType(MapObject::Type::Thing); break; + default: return true; } // Show dialog @@ -1808,20 +1813,20 @@ bool MapEditContext::handleAction(string_view id) switch (dlg.type()) { case MapObject::Type::Vertex: setEditMode(Mode::Vertices); break; - case MapObject::Type::Line: setEditMode(Mode::Lines); break; + case MapObject::Type::Line: setEditMode(Mode::Lines); break; case MapObject::Type::Side: setEditMode(Mode::Lines); side = true; break; case MapObject::Type::Sector: setEditMode(Mode::Sectors); break; - case MapObject::Type::Thing: setEditMode(Mode::Things); break; - default: break; + case MapObject::Type::Thing: setEditMode(Mode::Things); break; + default: break; } // If side, get its parent line if (side) { - auto s = map_.side(index); + auto s = map_->side(index); if (s && s->parentLine()) index = s->parentLine()->index(); else @@ -1840,9 +1845,9 @@ bool MapEditContext::handleAction(string_view id) else if (id == "mapw_mirror_y") { // Mirroring sectors breaks Edit Objects functionality - if (input_.mouseState() != mapeditor::Input::MouseState::ObjectEdit) + if (input_->mouseState() != Input::MouseState::ObjectEdit) { - edit_2d_.mirror(false); + edit_2d_->mirror(false); return true; } } @@ -1851,9 +1856,9 @@ bool MapEditContext::handleAction(string_view id) else if (id == "mapw_mirror_x") { // Mirroring sectors breaks Edit Objects functionality - if (input_.mouseState() != mapeditor::Input::MouseState::ObjectEdit) + if (input_->mouseState() != Input::MouseState::ObjectEdit) { - edit_2d_.mirror(true); + edit_2d_->mirror(true); return true; } } @@ -1884,23 +1889,23 @@ bool MapEditContext::handleAction(string_view id) else if (id == "mapw_camera_set") { Vec3d pos = input().mousePosMap(); - auto sector = map_.sectors().atPos(input_.mousePosMap()); + auto sector = map_->sectors().atPos(input_->mousePosMap()); if (sector) pos.z = sector->floor().plane.heightAt(pos.x, pos.y) + 40; - renderer_.renderer3D().cameraSetPosition(pos); + renderer_->renderer3D().cameraSetPosition(pos); return true; } // Edit item properties else if (id == "mapw_item_properties") - edit_2d_.editObjectProperties(); + edit_2d_->editObjectProperties(); // --- Vertex context menu --- // Create vertex else if (id == "mapw_vertex_create") { - edit_2d_.createVertex(input_.mousePosMap()); + edit_2d_->createVertex(input_->mousePosMap()); return true; } @@ -1929,7 +1934,7 @@ bool MapEditContext::handleAction(string_view id) beginUndoRecord("Change Line Special", true, false, false); dlg.applyTo(selection, true); endUndoRecord(); - renderer_.renderer2D().forceUpdate(); + renderer_->renderer2D().forceUpdate(); } } @@ -1941,7 +1946,7 @@ bool MapEditContext::handleAction(string_view id) { if (beginTagEdit() > 0) { - input_.setMouseState(Input::MouseState::TagSectors); + input_->setMouseState(Input::MouseState::TagSectors); // Setup help text auto key_accept = KeyBind::bind("map_edit_accept").keysAsString(); @@ -1958,14 +1963,14 @@ bool MapEditContext::handleAction(string_view id) // Correct sectors else if (id == "mapw_line_correctsectors") { - edit_2d_.correctLineSectors(); + edit_2d_->correctLineSectors(); return true; } // Flip else if (id == "mapw_line_flip") { - edit_2d_.flipLines(); + edit_2d_->flipLines(); return true; } @@ -1974,14 +1979,14 @@ bool MapEditContext::handleAction(string_view id) // Change thing type else if (id == "mapw_thing_changetype") { - edit_2d_.changeThingType(); + edit_2d_->changeThingType(); return true; } // Create thing else if (id == "mapw_thing_create") { - edit_2d_.createThing(input_.mouseDownPosMap()); + edit_2d_->createThing(input_->mouseDownPosMap()); return true; } @@ -1990,7 +1995,7 @@ bool MapEditContext::handleAction(string_view id) // Change sector texture else if (id == "mapw_sector_changetexture") { - edit_2d_.changeSectorTexture(); + edit_2d_->changeSectorTexture(); return true; } @@ -2020,21 +2025,21 @@ bool MapEditContext::handleAction(string_view id) // Create sector else if (id == "mapw_sector_create") { - edit_2d_.createSector(input_.mouseDownPosMap()); + edit_2d_->createSector(input_->mouseDownPosMap()); return true; } // Merge sectors else if (id == "mapw_sector_join") { - edit_2d_.joinSectors(false); + edit_2d_->joinSectors(false); return true; } // Join sectors else if (id == "mapw_sector_join_keep") { - edit_2d_.joinSectors(true); + edit_2d_->joinSectors(true); return true; } @@ -2043,358 +2048,6 @@ bool MapEditContext::handleAction(string_view id) } -// ----------------------------------------------------------------------------- -// -// MapArchClipboardItem Class Functions -// -// ----------------------------------------------------------------------------- - - -// ----------------------------------------------------------------------------- -// Copies [lines] and all related map structures -// ----------------------------------------------------------------------------- -void MapArchClipboardItem::addLines(const vector& lines) -{ - // Get sectors and sides to copy - vector copy_sectors; - vector copy_sides; - for (auto line : lines) - { - auto s1 = line->s1(); - auto s2 = line->s2(); - - // Front side - if (s1) - { - copy_sides.push_back(s1); - if (std::find(copy_sectors.begin(), copy_sectors.end(), s1->sector()) == copy_sectors.end()) - copy_sectors.push_back(s1->sector()); - } - - // Back side - if (s2) - { - copy_sides.push_back(s2); - if (std::find(copy_sectors.begin(), copy_sectors.end(), s2->sector()) == copy_sectors.end()) - copy_sectors.push_back(s2->sector()); - } - } - - // Copy sectors - for (auto& sector : copy_sectors) - { - auto copy = std::make_unique(); - copy->copy(sector); - sectors_.push_back(std::move(copy)); - } - - // Copy sides - for (auto& side : copy_sides) - { - auto copy = std::make_unique(); - copy->copy(side); - - // Set relative sector - for (unsigned b = 0; b < copy_sectors.size(); b++) - { - if (side->sector() == copy_sectors[b]) - { - copy->setSector(sectors_[b].get()); - break; - } - } - - sides_.push_back(std::move(copy)); - } - - // Get vertices to copy (and determine midpoint) - double min_x = 9999999; - double max_x = -9999999; - double min_y = 9999999; - double max_y = -9999999; - vector copy_verts; - for (auto line : lines) - { - auto v1 = line->v1(); - auto v2 = line->v2(); - - // Add vertices to copy list - if (std::find(copy_verts.begin(), copy_verts.end(), v1) == copy_verts.end()) - copy_verts.push_back(v1); - if (std::find(copy_verts.begin(), copy_verts.end(), v2) == copy_verts.end()) - copy_verts.push_back(v2); - - // Update min/max - if (v1->xPos() < min_x) - min_x = v1->xPos(); - if (v1->xPos() > max_x) - max_x = v1->xPos(); - if (v1->yPos() < min_y) - min_y = v1->yPos(); - if (v1->yPos() > max_y) - max_y = v1->yPos(); - if (v2->xPos() < min_x) - min_x = v2->xPos(); - if (v2->xPos() > max_x) - max_x = v2->xPos(); - if (v2->yPos() < min_y) - min_y = v2->yPos(); - if (v2->yPos() > max_y) - max_y = v2->yPos(); - } - - // Determine midpoint - double mid_x = min_x + ((max_x - min_x) * 0.5); - double mid_y = min_y + ((max_y - min_y) * 0.5); - midpoint_.set(mid_x, mid_y); - - // Copy vertices - for (auto& vertex : copy_verts) - { - auto copy = std::make_unique(vertex->position() - midpoint_); - copy->copy(vertex); - vertices_.push_back(std::move(copy)); - } - - // Copy lines - for (auto line : lines) - { - // Get relative sides - MapSide* s1 = nullptr; - MapSide* s2 = nullptr; - bool s1_found = false; - bool s2_found = !(line->s2()); - for (unsigned i = 0; i < copy_sides.size(); i++) - { - if (line->s1() == copy_sides[i]) - { - s1 = sides_[i].get(); - s1_found = true; - } - if (line->s2() == copy_sides[i]) - { - s2 = sides_[i].get(); - s2_found = true; - } - - if (s1_found && s2_found) - break; - } - - // Get relative vertices - MapVertex* v1 = nullptr; - MapVertex* v2 = nullptr; - for (unsigned i = 0; i < copy_verts.size(); i++) - { - if (line->v1() == copy_verts[i]) - v1 = vertices_[i].get(); - if (line->v2() == copy_verts[i]) - v2 = vertices_[i].get(); - - if (v1 && v2) - break; - } - - // Copy line - auto copy = std::make_unique(v1, v2, s1, s2); - copy->copy(line); - lines_.push_back(std::move(copy)); - } -} - -// ----------------------------------------------------------------------------- -// Returns a string with info on what items are copied -// ----------------------------------------------------------------------------- -string MapArchClipboardItem::info() const -{ - return fmt::format( - "{} Vertices, {} Lines, {} Sides and {} Sectors", - vertices_.size(), - lines_.size(), - sides_.size(), - sectors_.size()); -} - -// ----------------------------------------------------------------------------- -// Pastes copied architecture to [map] at [position] -// ----------------------------------------------------------------------------- -vector MapArchClipboardItem::pasteToMap(SLADEMap* map, Vec2d position) -{ - std::map vertMap; - std::map sectMap; - std::map sideMap; - // Not used yet... - // std::map lineMap; - - // Add vertices - vector new_verts; - for (auto& vertex : vertices_) - { - new_verts.push_back(map->createVertex(position + vertex->position())); - new_verts.back()->copy(vertex.get()); - vertMap[vertex.get()] = new_verts.back(); - } - - // Add sectors - for (auto& sector : sectors_) - { - auto new_sector = map->createSector(); - new_sector->copy(sector.get()); - sectMap[sector.get()] = new_sector; - } - - // Add sides - // int first_new_side = map->nSides(); - for (auto& side : sides_) - { - // Get relative sector - auto sector = findInMap(sectMap, side->sector()); - - auto new_side = map->createSide(sector); - new_side->copy(side.get()); - sideMap[side.get()] = new_side; - } - - // Add lines - // int first_new_line = map->nLines(); - for (auto& line : lines_) - { - // Get relative vertices - auto v1 = findInMap(vertMap, line->v1()); - auto v2 = findInMap(vertMap, line->v2()); - - if (!v1) - { - log::info(1, "no v1"); - continue; - } - if (!v2) - { - log::info(1, "no v2"); - } - - auto newline = map->createLine(v1, v2, true); - newline->copy(line.get()); - - // Set relative sides - auto newS1 = findInMap(sideMap, line->s1()); - auto newS2 = findInMap(sideMap, line->s2()); - if (newS1) - newline->setS1(newS1); - if (newS2) - newline->setS2(newS2); - - // Set important flags (needed when copying from Doom/Hexen format to UDMF) - // Won't be needed when proper map format conversion stuff is implemented - game::configuration().setLineBasicFlag("twosided", newline, map->currentFormat(), (newS1 && newS2)); - game::configuration().setLineBasicFlag("blocking", newline, map->currentFormat(), !newS2); - } - - // TODO: - // - Split lines - // - Merge lines - - //// Fix sector references - //// TODO: figure out what lines are 'outside' on copy, only fix said lines - // for (unsigned a = first_new_line; a < map->nLines(); a++) - //{ - // MapLine* line = map->getLine(a); - // MapSector* sec1 = map->getLineSideSector(line, true); - // MapSector* sec2 = map->getLineSideSector(line, false); - // int i1 = -1; - // int i2 = -2; - // if (sec1) i1 = sec1->getIndex(); - // if (sec2) i2 = sec2->getIndex(); - // map->setLineSector(a, i1, true); - // map->setLineSector(a, i2, false); - //} - - return new_verts; -} - -// ----------------------------------------------------------------------------- -// Adds all copied lines to [list] -// ----------------------------------------------------------------------------- -void MapArchClipboardItem::putLines(vector& list) -{ - for (auto& line : lines_) - list.push_back(line.get()); -} - - -// ----------------------------------------------------------------------------- -// -// MapThingsClipboardItem Class Functions -// -// ----------------------------------------------------------------------------- - - -// ----------------------------------------------------------------------------- -// Copies [things] -// ----------------------------------------------------------------------------- -void MapThingsClipboardItem::addThings(vector& things) -{ - // Copy things - double min_x = 99999999; - double min_y = 99999999; - double max_x = -99999999; - double max_y = -99999999; - for (auto& thing : things) - { - auto copy_thing = std::make_unique(); - copy_thing->copy(thing); - things_.push_back(std::move(copy_thing)); - - if (thing->xPos() < min_x) - min_x = thing->xPos(); - if (thing->yPos() < min_y) - min_y = thing->yPos(); - if (thing->xPos() > max_x) - max_x = thing->xPos(); - if (thing->yPos() > max_y) - max_y = thing->yPos(); - } - - // Get midpoint - double mid_x = min_x + ((max_x - min_x) * 0.5); - double mid_y = min_y + ((max_y - min_y) * 0.5); - midpoint_.set(mid_x, mid_y); - - // Adjust thing positions - for (auto& thing : things_) - thing->move(thing->position() - midpoint_); -} - -// ----------------------------------------------------------------------------- -// Returns a string with info on what items are copied -// ----------------------------------------------------------------------------- -string MapThingsClipboardItem::info() const -{ - return fmt::format("{} Things", things_.size()); -} - -// ----------------------------------------------------------------------------- -// Pastes copied things to [map] at [position] -// ----------------------------------------------------------------------------- -void MapThingsClipboardItem::pasteToMap(SLADEMap* map, Vec2d position) -{ - for (auto& thing : things_) - { - auto newthing = map->createThing({ 0., 0. }); - newthing->copy(thing.get()); - newthing->move(position + thing->position()); - } -} - -// ----------------------------------------------------------------------------- -// Adds all copied things to [list] -// ----------------------------------------------------------------------------- -void MapThingsClipboardItem::putThings(vector& list) -{ - for (auto& thing : things_) - list.push_back(thing.get()); -} - // ----------------------------------------------------------------------------- // @@ -2540,15 +2193,16 @@ CONSOLE_COMMAND(m_vertex_attached, 1, false) } } -CONSOLE_COMMAND(m_n_polys, 0, false) -{ - SLADEMap& map = mapeditor::editContext().map(); - int npoly = 0; - for (unsigned a = 0; a < map.nSectors(); a++) - npoly += map.sector(a)->polygon()->nSubPolys(); - - log::console(fmt::format("{} polygons total", npoly)); -} +// #include "Utility/Polygon2D.h" +// CONSOLE_COMMAND(m_n_polys, 0, false) +//{ +// SLADEMap& map = mapeditor::editContext().map(); +// int npoly = 0; +// for (unsigned a = 0; a < map.nSectors(); a++) +// npoly += map.sector(a)->polygon()->nSubPolys(); +// +// log::console(fmt::format("{} polygons total", npoly)); +// } CONSOLE_COMMAND(mobj_info, 1, false) { diff --git a/src/MapEditor/MapEditContext.h b/src/MapEditor/MapEditContext.h index a66a22bd1..8360b8dd8 100644 --- a/src/MapEditor/MapEditContext.h +++ b/src/MapEditor/MapEditContext.h @@ -1,36 +1,50 @@ #pragma once -#include "Archive/Archive.h" -#include "Edit/Edit2D.h" -#include "Edit/Edit3D.h" -#include "Edit/Input.h" -#include "Edit/LineDraw.h" -#include "Edit/MoveObjects.h" -#include "Edit/ObjectEdit.h" -#include "General/Clipboard.h" +#include "Archive/MapDesc.h" #include "General/SAction.h" -#include "General/UI.h" -#include "General/UndoRedo.h" #include "ItemSelection.h" -#include "MapEditor.h" -#include "Renderer/Overlays/InfoOverlay3d.h" -#include "Renderer/Overlays/LineInfoOverlay.h" -#include "Renderer/Overlays/MCOverlay.h" -#include "Renderer/Overlays/SectorInfoOverlay.h" -#include "Renderer/Overlays/ThingInfoOverlay.h" -#include "Renderer/Overlays/VertexInfoOverlay.h" -#include "Renderer/Renderer.h" -#include "SLADEMap/SLADEMap.h" +// Forward declarations namespace slade { +class InfoOverlay3D; +class ThingInfoOverlay; +class SectorInfoOverlay; +class LineInfoOverlay; +class VertexInfoOverlay; +class MapSide; +class UndoStep; +class MCOverlay; +class MapObject; +class UndoManager; +class MapThing; +class MapLine; +class MapSector; +class ItemSelection; +class SLADEMap; +class MapCanvas; + namespace ui { enum class MouseCursor; } +namespace mapeditor +{ + class Edit2D; + class Edit3D; + class ObjectEdit; + class LineDraw; + class MoveObjects; + class Input; + class Renderer; + enum class Mode; + enum class SectorMode; + struct Item; +} // namespace mapeditor +} // namespace slade -class MapCanvas; - +namespace slade::mapeditor +{ class MapEditContext : public SActionHandler { public: @@ -43,31 +57,31 @@ class MapEditContext : public SActionHandler }; MapEditContext(); - ~MapEditContext() = default; - - SLADEMap& map() { return map_; } - mapeditor::Mode editMode() const { return edit_mode_; } - mapeditor::SectorMode sectorEditMode() const { return sector_mode_; } - double gridSize() const; - ItemSelection& selection() { return selection_; } - mapeditor::Item hilightItem() const { return selection_.hilight(); } - vector& taggedSectors() { return tagged_sectors_; } - vector& taggedLines() { return tagged_lines_; } - vector& taggedThings() { return tagged_things_; } - vector& taggingLines() { return tagging_lines_; } - vector& taggingThings() { return tagging_things_; } - vector& pathedThings() { return pathed_things_; } - bool gridSnap() const { return grid_snap_; } - UndoManager* undoManager() const { return undo_manager_.get(); } - Archive::MapDesc& mapDesc() { return map_desc_; } - MapCanvas* canvas() const { return canvas_; } - mapeditor::Renderer& renderer() { return renderer_; } - mapeditor::Input& input() { return input_; } - bool mouseLocked() const { return mouse_locked_; } - - void setEditMode(mapeditor::Mode mode); + ~MapEditContext() override = default; + + SLADEMap& map() const { return *map_; } + Mode editMode() const { return edit_mode_; } + SectorMode sectorEditMode() const { return sector_mode_; } + double gridSize() const; + ItemSelection& selection() { return selection_; } + Item hilightItem() const { return selection_.hilight(); } + vector& taggedSectors() { return tagged_sectors_; } + vector& taggedLines() { return tagged_lines_; } + vector& taggedThings() { return tagged_things_; } + vector& taggingLines() { return tagging_lines_; } + vector& taggingThings() { return tagging_things_; } + vector& pathedThings() { return pathed_things_; } + bool gridSnap() const { return grid_snap_; } + UndoManager* undoManager() const { return undo_manager_.get(); } + MapDesc& mapDesc() { return map_desc_; } + MapCanvas* canvas() const { return canvas_; } + Renderer& renderer() const { return *renderer_; } + Input& input() const { return *input_; } + bool mouseLocked() const { return mouse_locked_; } + + void setEditMode(Mode mode); void setPrevEditMode() { setEditMode(edit_mode_prev_); } - void setSectorEditMode(mapeditor::SectorMode mode); + void setSectorEditMode(SectorMode mode); void cycleSectorEditMode(); void setCanvas(MapCanvas* canvas) { canvas_ = canvas; } void lockMouse(bool lock); @@ -76,7 +90,7 @@ class MapEditContext : public SActionHandler bool update(long frametime); // Map loading - bool openMap(Archive::MapDesc map); + bool openMap(const MapDesc& map); void clearMap(); // Selection/hilight @@ -88,24 +102,24 @@ class MapEditContext : public SActionHandler void incrementGrid(); void decrementGrid(); double snapToGrid(double position, bool force = true) const; - Vec2d relativeSnapToGrid(Vec2d origin, Vec2d mouse_pos) const; + Vec2d relativeSnapToGrid(const Vec2d& origin, const Vec2d& mouse_pos) const; // Tag edit int beginTagEdit(); - void tagSectorAt(Vec2d pos); + void tagSectorAt(const Vec2d& pos); void endTagEdit(bool accept = true); // Editing handlers - MoveObjects& moveObjects() { return move_objects_; } - LineDraw& lineDraw() { return line_draw_; } - ObjectEdit& objectEdit() { return object_edit_; } - Edit3D& edit3D() { return edit_3d_; } - Edit2D& edit2D() { return edit_2d_; } + MoveObjects& moveObjects() const { return *move_objects_; } + LineDraw& lineDraw() const { return *line_draw_; } + ObjectEdit& objectEdit() const { return *object_edit_; } + Edit3D& edit3D() const { return *edit_3d_; } + Edit2D& edit2D() const { return *edit_2d_; } // Editor messages unsigned numEditorMessages() const { return editor_messages_.size(); } const string& editorMessage(int index); - long editorMessageTime(int index); + long editorMessageTime(int index) const; void addEditorMessage(string_view message); // Feature help text @@ -125,50 +139,50 @@ class MapEditContext : public SActionHandler MCOverlay* currentOverlay() const { return overlay_current_.get(); } bool overlayActive() const; void closeCurrentOverlay(bool cancel = false) const; - void openSectorTextureOverlay(vector& sectors); + void openSectorTextureOverlay(const vector& sectors); void openQuickTextureOverlay(); void openLineTextureOverlay(); bool infoOverlayActive() const { return info_showing_; } - void updateInfoOverlay(); - void drawInfoOverlay(const Vec2i& size, float alpha); + void updateInfoOverlay() const; + void drawInfoOverlay(const Vec2i& size, float alpha) const; // Player start swapping void swapPlayerStart3d(); - void swapPlayerStart2d(Vec2d pos); + void swapPlayerStart2d(const Vec2d& pos); void resetPlayerStart() const; // Misc string modeString(bool plural = true) const; bool handleKeyBind(string_view key, Vec2d position); - void updateDisplay(); + void updateDisplay() const; void updateStatusText() const; void updateThingLists(); void setCursor(ui::MouseCursor cursor) const; - void forceRefreshRenderer(); + void forceRefreshRenderer() const; // SAction handler bool handleAction(string_view id) override; private: - SLADEMap map_; - MapCanvas* canvas_ = nullptr; - Archive::MapDesc map_desc_; - long next_frame_length_ = 0; + unique_ptr map_; + MapCanvas* canvas_ = nullptr; + MapDesc map_desc_; + long next_frame_length_ = 0; // Undo/Redo stuff - unique_ptr undo_manager_ = nullptr; - unique_ptr us_create_delete_ = nullptr; + unique_ptr undo_manager_; + unique_ptr us_create_delete_; // Editor state - mapeditor::Mode edit_mode_ = mapeditor::Mode::Lines; - mapeditor::Mode edit_mode_prev_ = mapeditor::Mode::Lines; - ItemSelection selection_ = ItemSelection(this); - int grid_size_ = 9; - mapeditor::SectorMode sector_mode_ = mapeditor::SectorMode::Both; - bool grid_snap_ = true; - int current_tag_ = 0; - bool mouse_locked_ = false; + Mode edit_mode_; + Mode edit_mode_prev_; + ItemSelection selection_ = ItemSelection(this); + int grid_size_ = 9; + SectorMode sector_mode_; + bool grid_snap_ = true; + int current_tag_ = 0; + bool mouse_locked_ = false; // Undo/Redo bool undo_modified_ = false; @@ -189,18 +203,11 @@ class MapEditContext : public SActionHandler vector pathed_things_; // Editing - MoveObjects move_objects_{ *this }; - LineDraw line_draw_{ *this }; - Edit2D edit_2d_{ *this }; - Edit3D edit_3d_{ *this }; - ObjectEdit object_edit_{ *this }; - - // Object properties and copy/paste - unique_ptr copy_thing_ = nullptr; - unique_ptr copy_sector_ = nullptr; - unique_ptr copy_side_front_ = nullptr; - unique_ptr copy_side_back_ = nullptr; - unique_ptr copy_line_ = nullptr; + unique_ptr move_objects_; + unique_ptr line_draw_; + unique_ptr edit_2d_; + unique_ptr edit_3d_; + unique_ptr object_edit_; // Editor messages vector editor_messages_; @@ -213,57 +220,20 @@ class MapEditContext : public SActionHandler int player_start_dir_ = 0; // Renderer - mapeditor::Renderer renderer_ = mapeditor::Renderer(*this); + unique_ptr renderer_; // Input - mapeditor::Input input_ = mapeditor::Input(*this); + unique_ptr input_; // Full-Screen Overlay - unique_ptr overlay_current_ = nullptr; + unique_ptr overlay_current_; // Info overlays - bool info_showing_ = false; - VertexInfoOverlay info_vertex_; - LineInfoOverlay info_line_; - SectorInfoOverlay info_sector_; - ThingInfoOverlay info_thing_; - InfoOverlay3D info_3d_; -}; - -class MapArchClipboardItem : public ClipboardItem -{ -public: - MapArchClipboardItem() : ClipboardItem(Type::MapArchitecture) {} - ~MapArchClipboardItem() = default; - - void addLines(const vector& lines); - string info() const; - vector pasteToMap(SLADEMap* map, Vec2d position); - void putLines(vector& list); - Vec2d midpoint() const { return midpoint_; } - -private: - vector> vertices_; - vector> sides_; - vector> lines_; - vector> sectors_; - Vec2d midpoint_; + bool info_showing_ = false; + unique_ptr info_vertex_; + unique_ptr info_line_; + unique_ptr info_sector_; + unique_ptr info_thing_; + unique_ptr info_3d_; }; - -class MapThingsClipboardItem : public ClipboardItem -{ -public: - MapThingsClipboardItem() : ClipboardItem(Type::MapThings) {} - ~MapThingsClipboardItem() = default; - - void addThings(vector& things); - string info() const; - void pasteToMap(SLADEMap* map, Vec2d position); - void putThings(vector& list); - Vec2d midpoint() const { return midpoint_; } - -private: - vector> things_; - Vec2d midpoint_; -}; -} // namespace slade +} // namespace slade::mapeditor diff --git a/src/MapEditor/MapEditor.cpp b/src/MapEditor/MapEditor.cpp index 3b896b4a0..5163ad16b 100644 --- a/src/MapEditor/MapEditor.cpp +++ b/src/MapEditor/MapEditor.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -32,6 +32,8 @@ // // ----------------------------------------------------------------------------- #include "Main.h" +#include "General/UI.h" +#include "ItemSelection.h" #include "MapBackupManager.h" #include "MapEditContext.h" #include "MapEditor/UI/Dialogs/MapTextureBrowser.h" @@ -47,6 +49,7 @@ #include "UI/WxUtils.h" using namespace slade; +using namespace mapeditor; // ----------------------------------------------------------------------------- @@ -58,102 +61,12 @@ namespace slade::mapeditor { unique_ptr edit_context; MapTextureManager texture_manager; -Archive::MapDesc current_map_desc; +MapDesc current_map_desc; MapEditorWindow* map_window; MapBackupManager backup_manager; } // namespace slade::mapeditor -// ----------------------------------------------------------------------------- -// -// MapEditor::Item Struct Functions -// -// ----------------------------------------------------------------------------- - - -// ----------------------------------------------------------------------------- -// Returns the vertex in [map] matching this item, or null if the item isn't a -// vertex -// ----------------------------------------------------------------------------- -MapVertex* mapeditor::Item::asVertex(const SLADEMap& map) const -{ - if (type == ItemType::Vertex) - return map.vertex(index); - - return nullptr; -} - -// ----------------------------------------------------------------------------- -// Returns the line in [map] matching this item, or null if the item isn't a -// line -// ----------------------------------------------------------------------------- -MapLine* mapeditor::Item::asLine(const SLADEMap& map) const -{ - if (type == ItemType::Line) - return map.line(index); - - return nullptr; -} - -// ----------------------------------------------------------------------------- -// Returns the side in [map] matching this item, or null if the item isn't a -// side -// ----------------------------------------------------------------------------- -MapSide* mapeditor::Item::asSide(const SLADEMap& map) const -{ - if (type == ItemType::Side || type == ItemType::WallBottom || type == ItemType::WallMiddle - || type == ItemType::WallTop) - return map.side(index); - - return nullptr; -} - -// ----------------------------------------------------------------------------- -// Returns the sector in [map] matching this item, or null if the item isn't a -// sector -// ----------------------------------------------------------------------------- -MapSector* mapeditor::Item::asSector(const SLADEMap& map) const -{ - if (type == ItemType::Sector || type == ItemType::Ceiling || type == ItemType::Floor) - return map.sector(index); - - return nullptr; -} - -// ----------------------------------------------------------------------------- -// Returns the thing in [map] matching this item, or null if the item isn't a -// thing -// ----------------------------------------------------------------------------- -MapThing* mapeditor::Item::asThing(const SLADEMap& map) const -{ - if (type == ItemType::Thing) - return map.thing(index); - - return nullptr; -} - -// ----------------------------------------------------------------------------- -// Returns the object in [map] matching this item -// ----------------------------------------------------------------------------- -MapObject* mapeditor::Item::asObject(const SLADEMap& map) const -{ - switch (type) - { - case ItemType::Vertex: return map.vertex(index); - case ItemType::Side: - case ItemType::WallTop: - case ItemType::WallMiddle: - case ItemType::WallBottom: - case ItemType::Line: return map.line(index); - case ItemType::Floor: - case ItemType::Ceiling: - case ItemType::Sector: return map.sector(index); - case ItemType::Thing: return map.thing(index); - default: return nullptr; - } -} - - // ----------------------------------------------------------------------------- // // MapEditor Namespace Functions @@ -455,16 +368,17 @@ bool mapeditor::editObjectProperties(vector& list) PropsPanelBase* panel_props = nullptr; switch (edit_context->editMode()) { - case Mode::Lines: panel_props = new LinePropsPanel(&dlg); break; + case Mode::Lines: panel_props = new LinePropsPanel(&dlg); break; case Mode::Sectors: panel_props = new SectorPropsPanel(&dlg); break; - case Mode::Things: panel_props = new ThingPropsPanel(&dlg); break; - default: panel_props = new MapObjectPropsPanel(&dlg, true); + case Mode::Things: panel_props = new ThingPropsPanel(&dlg); break; + default: panel_props = new MapObjectPropsPanel(&dlg, true); } - sizer->Add(panel_props, 1, wxEXPAND | wxLEFT | wxRIGHT | wxTOP, ui::padLarge()); + sizer->Add(panel_props, wxutil::sfWithLargeBorder(1, wxLEFT | wxRIGHT | wxTOP).Expand()); // Add dialog buttons sizer->AddSpacer(ui::pad()); - sizer->Add(dlg.CreateButtonSizer(wxOK | wxCANCEL), 0, wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, ui::padLarge()); + sizer->Add( + dlg.CreateButtonSizer(wxOK | wxCANCEL), wxutil::sfWithLargeBorder(0, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); // Open current selection panel_props->openObjects(list); @@ -488,41 +402,3 @@ void mapeditor::resetObjectPropertiesPanel() { map_window->propsPanel()->clearGrid(); } - -// ----------------------------------------------------------------------------- -// Returns the 'base' item type for [type] -// (eg. WallMiddle is technically a Side) -// ----------------------------------------------------------------------------- -mapeditor::ItemType mapeditor::baseItemType(const ItemType& type) -{ - switch (type) - { - case ItemType::Vertex: return ItemType::Vertex; - case ItemType::Line: return ItemType::Line; - case ItemType::Side: - case ItemType::WallBottom: - case ItemType::WallMiddle: - case ItemType::WallTop: return ItemType::Side; - case ItemType::Sector: - case ItemType::Ceiling: - case ItemType::Floor: return ItemType::Sector; - case ItemType::Thing: return ItemType::Thing; - default: return ItemType::Any; - } -} - -// ----------------------------------------------------------------------------- -// Returns the map editor item type of the given map [object] -// ----------------------------------------------------------------------------- -mapeditor::ItemType mapeditor::itemTypeFromObject(const MapObject* object) -{ - switch (object->objType()) - { - case MapObject::Type::Vertex: return ItemType::Vertex; - case MapObject::Type::Line: return ItemType::Line; - case MapObject::Type::Side: return ItemType::Side; - case MapObject::Type::Sector: return ItemType::Sector; - case MapObject::Type::Thing: return ItemType::Thing; - default: return ItemType::Any; - } -} diff --git a/src/MapEditor/MapEditor.h b/src/MapEditor/MapEditor.h index 712f15ecf..ef60b1bf1 100644 --- a/src/MapEditor/MapEditor.h +++ b/src/MapEditor/MapEditor.h @@ -1,10 +1,10 @@ #pragma once +// Forward declarations namespace slade { class Archive; class MapBackupManager; -class MapEditContext; class MapEditorWindow; class MapObject; class MapVertex; @@ -13,133 +13,73 @@ class MapSide; class MapSector; class MapThing; class MapTextureManager; -class ObjectEditGroup; class SLADEMap; class UndoManager; namespace mapeditor { - enum class ItemType - { - // 2d modes - Vertex, - Line, - Sector, - - // 3d mode - Side, - WallTop, - WallMiddle, - WallBottom, - Floor, - Ceiling, - Thing, // (also 2d things mode) - - Any - }; - - enum class Mode - { - Vertices, - Lines, - Sectors, - Things, - Visual - }; - - enum class SectorMode - { - Both, - Floor, - Ceiling - }; - - enum class TextureType - { - Texture, - Flat - }; - - struct Item - { - int index; - ItemType type; - int real_index; - int control_line; - - Item(int index = -1, ItemType type = ItemType::Any) : - index{ index }, type{ type }, real_index{ -1 }, control_line{ -1 } - { - } - - // Comparison operators - bool operator<(const Item& other) const - { - if (type == other.type) - { - if (index == other.index) - return real_index < other.real_index; - else - return index < other.index; - } - else - return type < other.type; - } - bool operator==(const Item& other) const - { - return index == other.index && (type == ItemType::Any || type == other.type) - && real_index == other.real_index; - } - bool operator!=(const Item& other) const { return !(*this == other); } - - // Conversion operators - explicit operator int() const { return index; } - - MapVertex* asVertex(const SLADEMap& map) const; - MapLine* asLine(const SLADEMap& map) const; - MapSide* asSide(const SLADEMap& map) const; - MapSector* asSector(const SLADEMap& map) const; - MapThing* asThing(const SLADEMap& map) const; - MapObject* asObject(const SLADEMap& map) const; - }; - - MapEditContext& editContext(); - MapTextureManager& textureManager(); - MapEditorWindow* window(); - wxWindow* windowWx(); - MapBackupManager& backupManager(); - bool windowCreated(); - - void init(); - void forceRefresh(bool renderer = false); - bool chooseMap(Archive* archive = nullptr); - void setUndoManager(UndoManager* manager); - - // UI - void setStatusText(string_view text, int column); - void lockMouse(bool lock); - void openContextMenu(); - - // Properties Panel - void openObjectProperties(MapObject* object); - void openMultiObjectProperties(vector& objects); - bool editObjectProperties(vector& list); - void resetObjectPropertiesPanel(); - - // Other Panels - void showShapeDrawPanel(bool show = true); - void showObjectEditPanel(bool show = true, ObjectEditGroup* group = nullptr); - - // Browser - string browseTexture( - string_view init_texture, - TextureType tex_type, - SLADEMap& map, - string_view title = "Browse Texture"); - int browseThingType(int init_type, SLADEMap& map); - - // Misc - ItemType baseItemType(const ItemType& type); - ItemType itemTypeFromObject(const MapObject* object); + class MapEditContext; + class ObjectEditGroup; } // namespace mapeditor } // namespace slade + +namespace slade::mapeditor +{ +enum class Mode +{ + Vertices, + Lines, + Sectors, + Things, + Visual +}; + +enum class SectorMode +{ + Both, + Floor, + Ceiling +}; + +enum class TextureType +{ + Texture, + Flat +}; + + +MapEditContext& editContext(); +MapTextureManager& textureManager(); +MapEditorWindow* window(); +wxWindow* windowWx(); +MapBackupManager& backupManager(); +bool windowCreated(); + +void init(); +void forceRefresh(bool renderer = false); +bool chooseMap(Archive* archive = nullptr); +void setUndoManager(UndoManager* manager); + +// UI +void setStatusText(string_view text, int column); +void lockMouse(bool lock); +void openContextMenu(); + +// Properties Panel +void openObjectProperties(MapObject* object); +void openMultiObjectProperties(vector& objects); +bool editObjectProperties(vector& list); +void resetObjectPropertiesPanel(); + +// Other Panels +void showShapeDrawPanel(bool show = true); +void showObjectEditPanel(bool show = true, ObjectEditGroup* group = nullptr); + +// Browser +string browseTexture( + string_view init_texture, + TextureType tex_type, + SLADEMap& map, + string_view title = "Browse Texture"); +int browseThingType(int init_type, SLADEMap& map); +} // namespace slade::mapeditor diff --git a/src/MapEditor/MapTextureManager.cpp b/src/MapEditor/MapTextureManager.cpp index 5bbadd0ba..238127082 100644 --- a/src/MapEditor/MapTextureManager.cpp +++ b/src/MapEditor/MapTextureManager.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -42,8 +42,8 @@ #include "Graphics/SImage/SImage.h" #include "MainEditor/MainEditor.h" #include "MainEditor/UI/MainWindow.h" -#include "MapEditContext.h" #include "MapEditor.h" +#include "OpenGL/GLTexture.h" #include "OpenGL/OpenGL.h" #include "UI/Controls/PaletteChooser.h" #include "Utility/StringUtils.h" @@ -65,15 +65,38 @@ CVAR(Int, map_tex_filter, 0, CVar::Flag::Save) // ----------------------------------------------------------------------------- // -// MapTextureManager Class Functions +// MapTextureManager::Texture Struct Functions // // ----------------------------------------------------------------------------- +// ----------------------------------------------------------------------------- +// Texture Struct destructor +// ----------------------------------------------------------------------------- +MapTextureManager::Texture::~Texture() +{ + gl::Texture::clear(gl_id); +} + + +// ----------------------------------------------------------------------------- +// +// MapTextureManager Class Functions +// +// ----------------------------------------------------------------------------- // ----------------------------------------------------------------------------- // MapTextureManager class constructor // ----------------------------------------------------------------------------- -MapTextureManager::MapTextureManager(shared_ptr archive) : archive_{ archive }, palette_{ new Palette() } {} +MapTextureManager::MapTextureManager(const shared_ptr& archive) : + archive_{ archive }, + palette_{ new Palette() } +{ +} + +// ----------------------------------------------------------------------------- +// MapTextureManager class destructor +// ----------------------------------------------------------------------------- +MapTextureManager::~MapTextureManager() = default; // ----------------------------------------------------------------------------- // Initialises the texture manager @@ -190,7 +213,8 @@ const MapTextureManager::Texture& MapTextureManager::texture(string_view name, b sw = imgref.width(); sh = imgref.height(); mtex.world_panning = true; - mtex.scale = { (double)sw / (double)w, (double)sh / (double)h }; + mtex.scale = { static_cast(sw) / static_cast(w), + static_cast(sh) / static_cast(h) }; } } } @@ -641,7 +665,7 @@ void MapTextureManager::buildTexInfoList() // ----------------------------------------------------------------------------- // Sets the current archive to [archive], and refreshes all resources // ----------------------------------------------------------------------------- -void MapTextureManager::setArchive(shared_ptr archive) +void MapTextureManager::setArchive(const shared_ptr& archive) { archive_ = archive; refreshResources(); diff --git a/src/MapEditor/MapTextureManager.h b/src/MapEditor/MapTextureManager.h index 7f7350c48..79d150513 100644 --- a/src/MapEditor/MapTextureManager.h +++ b/src/MapEditor/MapTextureManager.h @@ -1,7 +1,5 @@ #pragma once -#include "OpenGL/GLTexture.h" - namespace slade { class ArchiveDir; @@ -26,7 +24,10 @@ class MapTextureManager unsigned gl_id = 0; bool world_panning = false; Vec2d scale = { 1., 1. }; - ~Texture() { gl::Texture::clear(gl_id); } + + Texture() = default; + Texture(const Texture&) = default; + ~Texture(); }; typedef std::map MapTexHashMap; @@ -46,16 +47,21 @@ class MapTextureManager string_view path, unsigned index = 0, string_view long_name = "") : - short_name(short_name), category(category), archive(archive), path(path), index(index), long_name(long_name) + short_name(short_name), + category(category), + archive(archive), + path(path), + index(index), + long_name(long_name) { } }; - MapTextureManager(shared_ptr archive = nullptr); - ~MapTextureManager() = default; + MapTextureManager(const shared_ptr& archive = nullptr); + ~MapTextureManager(); void init(); - void setArchive(shared_ptr archive); + void setArchive(const shared_ptr& archive); void refreshResources(); Palette* resourcePalette() const; diff --git a/src/MapEditor/NodeBuilders.cpp b/src/MapEditor/NodeBuilders.cpp index 394e8677e..2c98cee20 100644 --- a/src/MapEditor/NodeBuilders.cpp +++ b/src/MapEditor/NodeBuilders.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -164,10 +164,10 @@ unsigned nodebuilders::nNodeBuilders() // ----------------------------------------------------------------------------- nodebuilders::Builder& nodebuilders::builder(string_view id) { - for (unsigned a = 0; a < builders.size(); a++) + for (auto& builder : builders) { - if (builders[a].id == id) - return builders[a]; + if (builder.id == id) + return builder; } return invalid; diff --git a/src/MapEditor/Renderer/MCAnimations.cpp b/src/MapEditor/Renderer/MCAnimations.cpp index 8d9f4c3e5..e1887b0b5 100644 --- a/src/MapEditor/Renderer/MCAnimations.cpp +++ b/src/MapEditor/Renderer/MCAnimations.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -33,13 +33,17 @@ #include "Main.h" #include "MCAnimations.h" #include "General/ColourConfiguration.h" +#include "MapEditor/Item.h" #include "MapEditor/MapEditor.h" #include "MapEditor/MapTextureManager.h" #include "MapRenderer2D.h" #include "MapRenderer3D.h" +#include "OpenGL/GLTexture.h" #include "OpenGL/OpenGL.h" #include "SLADEMap/MapObject/MapLine.h" +#include "SLADEMap/MapObject/MapSector.h" #include "SLADEMap/MapObject/MapVertex.h" +#include "Utility/Polygon2D.h" using namespace slade; @@ -67,7 +71,9 @@ EXTERN_CVAR(Bool, sector_selected_fill) // ----------------------------------------------------------------------------- // MCASelboxFader class constructor // ----------------------------------------------------------------------------- -MCASelboxFader::MCASelboxFader(long start, Vec2d tl, Vec2d br) : MCAnimation(start), tl_{ tl }, br_{ br } {} +MCASelboxFader::MCASelboxFader(long start, const Vec2d& tl, const Vec2d& br) : MCAnimation(start), tl_{ tl }, br_{ br } +{ +} // ----------------------------------------------------------------------------- // Updates the animation based on [time] elapsed in ms @@ -492,7 +498,7 @@ void MCA3dWallSelection::draw() // ----------------------------------------------------------------------------- // MCA3dFlatSelection class constructor // ----------------------------------------------------------------------------- -MCA3dFlatSelection::MCA3dFlatSelection(long start, MapSector* sector, Plane plane, bool select) : +MCA3dFlatSelection::MCA3dFlatSelection(long start, MapSector* sector, const Plane& plane, bool select) : MCAnimation(start, true), sector_{ sector }, plane_{ plane }, @@ -578,11 +584,11 @@ void MCAHilightFade::draw() { switch (object_->objType()) { - case MapObject::Type::Line: renderer_->renderLineHilight(object_->index(), fade_); break; + case MapObject::Type::Line: renderer_->renderLineHilight(object_->index(), fade_); break; case MapObject::Type::Sector: renderer_->renderFlatHilight(object_->index(), fade_); break; - case MapObject::Type::Thing: renderer_->renderThingHilight(object_->index(), fade_); break; + case MapObject::Type::Thing: renderer_->renderThingHilight(object_->index(), fade_); break; case MapObject::Type::Vertex: renderer_->renderVertexHilight(object_->index(), fade_); break; - default: break; + default: break; } } diff --git a/src/MapEditor/Renderer/MCAnimations.h b/src/MapEditor/Renderer/MCAnimations.h index b43540896..0d8602086 100644 --- a/src/MapEditor/Renderer/MCAnimations.h +++ b/src/MapEditor/Renderer/MCAnimations.h @@ -1,7 +1,5 @@ #pragma once -#include "MapEditor/Edit/Edit3D.h" - namespace slade { // Forward declarations @@ -12,6 +10,10 @@ class MapSector; class MapRenderer2D; class MapObject; class MapRenderer3D; +namespace mapeditor +{ + enum class ItemType; +} class MCAnimation { @@ -33,8 +35,8 @@ class MCAnimation class MCASelboxFader : public MCAnimation { public: - MCASelboxFader(long start, Vec2d tl, Vec2d br); - ~MCASelboxFader() = default; + MCASelboxFader(long start, const Vec2d& tl, const Vec2d& br); + ~MCASelboxFader() override = default; bool update(long time) override; void draw() override; @@ -50,7 +52,7 @@ class MCAThingSelection : public MCAnimation { public: MCAThingSelection(long start, double x, double y, double radius, double scale_inv, bool select = true); - ~MCAThingSelection() = default; + ~MCAThingSelection() override = default; bool update(long time) override; void draw() override; @@ -68,7 +70,7 @@ class MCALineSelection : public MCAnimation { public: MCALineSelection(long start, const vector& lines, bool select = true); - ~MCALineSelection() = default; + ~MCALineSelection() override = default; bool update(long time) override; void draw() override; @@ -85,7 +87,7 @@ class MCAVertexSelection : public MCAnimation { public: MCAVertexSelection(long start, const vector& verts, double size, bool select = true); - ~MCAVertexSelection() = default; + ~MCAVertexSelection() override = default; bool update(long time) override; void draw() override; @@ -102,7 +104,7 @@ class MCASectorSelection : public MCAnimation { public: MCASectorSelection(long start, const vector& polys, bool select = true); - ~MCASectorSelection() = default; + ~MCASectorSelection() override = default; bool update(long time) override; void draw() override; @@ -118,7 +120,7 @@ class MCA3dWallSelection : public MCAnimation { public: MCA3dWallSelection(long start, Vec3f points[4], bool select = true); - ~MCA3dWallSelection() = default; + ~MCA3dWallSelection() override = default; bool update(long time) override; void draw() override; @@ -133,8 +135,8 @@ class MCA3dWallSelection : public MCAnimation class MCA3dFlatSelection : public MCAnimation { public: - MCA3dFlatSelection(long start, MapSector* sector, Plane plane, bool select = true); - ~MCA3dFlatSelection() = default; + MCA3dFlatSelection(long start, MapSector* sector, const Plane& plane, bool select = true); + ~MCA3dFlatSelection() override = default; bool update(long time) override; void draw() override; @@ -151,7 +153,7 @@ class MCAHilightFade : public MCAnimation { public: MCAHilightFade(long start, MapObject* object, MapRenderer2D* renderer, float fade_init); - ~MCAHilightFade() = default; + ~MCAHilightFade() override = default; bool update(long time) override; void draw() override; @@ -173,7 +175,7 @@ class MCAHilightFade3D : public MCAnimation mapeditor::ItemType item_type, MapRenderer3D* renderer, float fade_init); - ~MCAHilightFade3D() = default; + ~MCAHilightFade3D() override = default; bool update(long time) override; void draw() override; diff --git a/src/MapEditor/Renderer/MapRenderer2D.cpp b/src/MapEditor/Renderer/MapRenderer2D.cpp index 63fca396d..53258169b 100644 --- a/src/MapEditor/Renderer/MapRenderer2D.cpp +++ b/src/MapEditor/Renderer/MapRenderer2D.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -42,10 +42,17 @@ #include "OpenGL/Drawing.h" #include "OpenGL/GLTexture.h" #include "OpenGL/OpenGL.h" +#include "SLADEMap/MapObject/MapLine.h" +#include "SLADEMap/MapObject/MapSector.h" +#include "SLADEMap/MapObject/MapSide.h" +#include "SLADEMap/MapObject/MapThing.h" +#include "SLADEMap/MapObject/MapVertex.h" +#include "SLADEMap/MapObjectList/ThingList.h" #include "SLADEMap/SLADEMap.h" #include "Utility/Polygon2D.h" using namespace slade; +using namespace mapeditor; // ----------------------------------------------------------------------------- @@ -483,7 +490,7 @@ void MapRenderer2D::renderLinesVBO(bool show_direction, float alpha) glBindBuffer(GL_ARRAY_BUFFER, vbo_lines_); glVertexPointer(2, GL_FLOAT, 24, nullptr); - glColorPointer(4, GL_FLOAT, 24, ((char*)nullptr + 8)); + glColorPointer(4, GL_FLOAT, 24, (static_cast(nullptr) + 8)); // Render the VBO if (show_direction) @@ -940,7 +947,7 @@ bool MapRenderer2D::renderSpriteThing( // Fit to radius if needed if (fitradius) { - double scale = ((double)type.radius() * 0.8) / max(hw, hh); + double scale = (static_cast(type.radius()) * 0.8) / max(hw, hh); hw *= scale; hh *= scale; } @@ -1049,7 +1056,7 @@ bool MapRenderer2D::renderSquareThing( tex = mapeditor::textureManager().editorImage("thing/square/normal_d1").gl_id; // Setup variables depending on angle - switch ((int)angle) + switch (static_cast(angle)) { case 0: // East: normal, texcoord 0 break; @@ -1851,7 +1858,7 @@ void MapRenderer2D::renderPathedThings(const vector& things) to->getPoint(MapObject::Point::Mid), from->getPoint(MapObject::Point::Mid), (thing_path.type == PathType::DragonBoth || thing_path.type == PathType::Dragon) ? dragoncol : - pathedcol, + pathedcol, (thing_path.type == PathType::NormalBoth || thing_path.type == PathType::DragonBoth), arrowhead_angle, arrowhead_length); @@ -2489,7 +2496,7 @@ void MapRenderer2D::renderTaggedFlats(const vector& sectors, float f // Renders the moving overlay for vertex indices in [vertices], to show movement // by [move_vec] // ----------------------------------------------------------------------------- -void MapRenderer2D::renderMovingVertices(const vector& vertices, Vec2d move_vec) const +void MapRenderer2D::renderMovingVertices(const vector& vertices, const Vec2d& move_vec) const { vector lines_drawn(map_->nLines(), 0); @@ -2563,7 +2570,7 @@ void MapRenderer2D::renderMovingVertices(const vector& vertices // Renders the moving overlay for line indices in [lines], to show movement by // [move_vec] // ----------------------------------------------------------------------------- -void MapRenderer2D::renderMovingLines(const vector& lines, Vec2d move_vec) const +void MapRenderer2D::renderMovingLines(const vector& lines, const Vec2d& move_vec) const { vector lines_drawn(map_->nLines(), 0); @@ -2649,7 +2656,7 @@ void MapRenderer2D::renderMovingLines(const vector& lines, Vec2 // Renders the moving overlay for sector indices in [sectors], to show movement // by [move_vec] // ----------------------------------------------------------------------------- -void MapRenderer2D::renderMovingSectors(const vector& sectors, Vec2d move_vec) const +void MapRenderer2D::renderMovingSectors(const vector& sectors, const Vec2d& move_vec) const { // Determine what lines are being moved vector lines_moved(map_->nLines(), 0); @@ -2665,11 +2672,11 @@ void MapRenderer2D::renderMovingSectors(const vector& sectors, } // Build list of moving lines - vector lines; + vector lines; for (unsigned a = 0; a < map_->nLines(); a++) { if (lines_moved[a] > 0) - lines.emplace_back((int)a, mapeditor::ItemType::Line); + lines.emplace_back(static_cast(a), ItemType::Line); } // Draw moving lines @@ -2680,7 +2687,7 @@ void MapRenderer2D::renderMovingSectors(const vector& sectors, // Renders the moving overlay for thing indices in [things], to show movement by // [move_vec] // ----------------------------------------------------------------------------- -void MapRenderer2D::renderMovingThings(const vector& things, Vec2d move_vec) +void MapRenderer2D::renderMovingThings(const vector& things, const Vec2d& move_vec) { // Enable textures glEnable(GL_TEXTURE_2D); @@ -2775,7 +2782,7 @@ void MapRenderer2D::renderMovingThings(const vector& things, Ve // ----------------------------------------------------------------------------- // Renders pasting overlay for [things] at [pos] // ----------------------------------------------------------------------------- -void MapRenderer2D::renderPasteThings(const vector& things, Vec2d pos) +void MapRenderer2D::renderPasteThings(const vector& things, const Vec2d& pos) { // Enable textures glEnable(GL_TEXTURE_2D); @@ -2858,7 +2865,7 @@ void MapRenderer2D::renderPasteThings(const vector& things, Vec2d pos // ----------------------------------------------------------------------------- // Renders object edit group overlay for [group] // ----------------------------------------------------------------------------- -void MapRenderer2D::renderObjectEditGroup(ObjectEditGroup* group) +void MapRenderer2D::renderObjectEditGroup(const ObjectEditGroup* group) { // Simple test vector vertex_points; @@ -3151,7 +3158,7 @@ void MapRenderer2D::updateFlatsVBO() // ----------------------------------------------------------------------------- // Updates map object visibility info depending on the current view // ----------------------------------------------------------------------------- -void MapRenderer2D::updateVisibility(Vec2d view_tl, Vec2d view_br) +void MapRenderer2D::updateVisibility(const Vec2d& view_tl, const Vec2d& view_br) { // Sector visibility if (map_->nSectors() != vis_s_.size()) diff --git a/src/MapEditor/Renderer/MapRenderer2D.h b/src/MapEditor/Renderer/MapRenderer2D.h index 3ecd26da8..6cfe7ca7f 100644 --- a/src/MapEditor/Renderer/MapRenderer2D.h +++ b/src/MapEditor/Renderer/MapRenderer2D.h @@ -1,6 +1,5 @@ #pragma once -#include "MapEditor/MapEditor.h" #include "SLADEMap/MapObject/MapObject.h" #include "Utility/Colour.h" @@ -11,12 +10,16 @@ class ItemSelection; class MapLine; class MapSector; class MapThing; -class ObjectEditGroup; class SLADEMap; namespace game { class ThingType; } +namespace mapeditor +{ + struct Item; + class ObjectEditGroup; +} // namespace mapeditor class MapRenderer2D { @@ -106,16 +109,16 @@ class MapRenderer2D void renderTaggedFlats(const vector& sectors, float fade) const; // Moving - void renderMovingVertices(const vector& vertices, Vec2d move_vec) const; - void renderMovingLines(const vector& lines, Vec2d move_vec) const; - void renderMovingSectors(const vector& sectors, Vec2d move_vec) const; - void renderMovingThings(const vector& things, Vec2d move_vec); + void renderMovingVertices(const vector& vertices, const Vec2d& move_vec) const; + void renderMovingLines(const vector& lines, const Vec2d& move_vec) const; + void renderMovingSectors(const vector& sectors, const Vec2d& move_vec) const; + void renderMovingThings(const vector& things, const Vec2d& move_vec); // Paste - void renderPasteThings(const vector& things, Vec2d pos); + void renderPasteThings(const vector& things, const Vec2d& pos); // Object Edit - void renderObjectEditGroup(ObjectEditGroup* group); + void renderObjectEditGroup(const mapeditor::ObjectEditGroup* group); // VBOs void updateVerticesVBO(); @@ -128,7 +131,7 @@ class MapRenderer2D view_scale_ = scale; view_scale_inv_ = 1.0 / scale; } - void updateVisibility(Vec2d view_tl, Vec2d view_br); + void updateVisibility(const Vec2d& view_tl, const Vec2d& view_br); void forceUpdate(float line_alpha = 1.0f); double scaledRadius(int radius) const; bool visOK() const; @@ -180,7 +183,6 @@ class MapRenderer2D bool lines_dirs_ = false; unsigned n_vertices_ = 0; unsigned n_lines_ = 0; - unsigned n_things_ = 0; double view_scale_ = 0.; double view_scale_inv_ = 0.; bool things_angles_ = false; diff --git a/src/MapEditor/Renderer/MapRenderer3D.cpp b/src/MapEditor/Renderer/MapRenderer3D.cpp index 3fe5a5b49..b8c5ab2ac 100644 --- a/src/MapEditor/Renderer/MapRenderer3D.cpp +++ b/src/MapEditor/Renderer/MapRenderer3D.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -39,12 +39,22 @@ #include "MainEditor/MainEditor.h" #include "MainEditor/UI/MainWindow.h" #include "MapEditor/MapEditContext.h" +#include "MapEditor/MapEditor.h" #include "MapEditor/MapTextureManager.h" +#include "OpenGL/GLTexture.h" #include "OpenGL/OpenGL.h" +#include "SLADEMap/MapObject/MapLine.h" +#include "SLADEMap/MapObject/MapSector.h" +#include "SLADEMap/MapObject/MapSide.h" +#include "SLADEMap/MapObject/MapThing.h" +#include "SLADEMap/MapObjectList/SectorList.h" +#include "SLADEMap/MapSpecials.h" #include "SLADEMap/SLADEMap.h" #include "UI/Controls/PaletteChooser.h" #include "Utility/MathStuff.h" +#include "Utility/Polygon2D.h" #include "Utility/StringUtils.h" +#include using namespace slade; using ExtraFloor = MapSector::ExtraFloor; @@ -444,7 +454,7 @@ void MapRenderer3D::cameraUpdateVectors() // ----------------------------------------------------------------------------- // Sets the camera position to [position], facing [direction] // ----------------------------------------------------------------------------- -void MapRenderer3D::cameraSet(Vec3d position, Vec2d direction) +void MapRenderer3D::cameraSet(const Vec3d& position, const Vec2d& direction) { // Set camera position/direction cam_position_ = position; @@ -458,7 +468,7 @@ void MapRenderer3D::cameraSet(Vec3d position, Vec2d direction) // ----------------------------------------------------------------------------- // Moves the camera to [position] // ----------------------------------------------------------------------------- -void MapRenderer3D::cameraSetPosition(Vec3d position) +void MapRenderer3D::cameraSetPosition(const Vec3d& position) { cam_position_ = position; } @@ -476,7 +486,7 @@ void MapRenderer3D::cameraApplyGravity(double mult) // Get target height from nearest floor down, including 3D floors auto view_height = game::configuration().playerEyeHeight(); Vec2d cam2d = cam_position_.get2d(); - int fheight = (int)sector->floor().plane.heightAt(cam2d) + view_height; + int fheight = static_cast(sector->floor().plane.heightAt(cam2d)) + view_height; for (const auto& extra : sector->extraFloors()) { // Only check solid floors @@ -528,7 +538,7 @@ void MapRenderer3D::cameraLook(double xrel, double yrel) void MapRenderer3D::setupView(int width, int height) const { // Calculate aspect ratio - float aspect = (1.6f / 1.333333f) * ((float)width / (float)height); + float aspect = (1.6f / 1.333333f) * (static_cast(width) / static_cast(height)); float fovy = 2 * math::radToDeg(atan(tan(math::degToRad(render_fov) / 2) / aspect)); // Setup projection @@ -575,7 +585,7 @@ void MapRenderer3D::setLight(const ColRGBA& colour, uint8_t light, float alpha) // If we have a non-coloured light, darken it a bit to // closer resemble the software renderer light level - float mult = (float)light / 255.0f; + float mult = static_cast(light) / 255.0f; mult *= (mult * 1.3f); glColor4f(colour.fr() * mult, colour.fg() * mult, colour.fb() * mult, colour.fa() * alpha); } @@ -870,7 +880,7 @@ void MapRenderer3D::renderSky() float tx = 0.125f; float ty = 2.0f; if (tex_info.size.x > 256) - tx = 0.125f / ((float)tex_info.size.x / 256.0f); + tx = 0.125f / (static_cast(tex_info.size.x) / 256.0f); if (tex_info.size.y > 128) ty = 1.0f; @@ -932,8 +942,7 @@ void MapRenderer3D::updateFlatTexCoords(unsigned index, unsigned flat_index) con return; // Get sector - auto sector = map_->sector(index); - auto control_sector = sector_flats_[index][flat_index].control_sector; + auto sector = map_->sector(index); // Get scaling/offset info double ox = 0.; @@ -1411,7 +1420,7 @@ void MapRenderer3D::renderFlatSelection(const ItemSelection& selection, float al // ----------------------------------------------------------------------------- // Sets up coordinates for a quad // ----------------------------------------------------------------------------- -void MapRenderer3D::setupQuad(Quad* quad, Seg2d seg, double top, double bottom) const +void MapRenderer3D::setupQuad(Quad* quad, const Seg2d& seg, double top, double bottom) const { // Left quad->points[0].x = quad->points[1].x = seg.x1(); @@ -1429,7 +1438,7 @@ void MapRenderer3D::setupQuad(Quad* quad, Seg2d seg, double top, double bottom) // ----------------------------------------------------------------------------- // Sets up coordinates for a quad // ----------------------------------------------------------------------------- -void MapRenderer3D::setupQuad(Quad* quad, Seg2d seg, Plane top, Plane bottom) const +void MapRenderer3D::setupQuad(Quad* quad, const Seg2d& seg, const Plane& top, const Plane& bottom) const { // Left quad->points[0].x = quad->points[1].x = seg.x1(); @@ -2997,10 +3006,9 @@ void MapRenderer3D::checkVisibleQuads() // Go through lines MapLine* line; float distfade; - n_quads_ = 0; - unsigned updates = 0; - bool update = false; - Seg2d strafe(cam_position_.get2d(), (cam_position_ + cam_strafe_).get2d()); + n_quads_ = 0; + bool update = false; + Seg2d strafe(cam_position_.get2d(), (cam_position_ + cam_strafe_).get2d()); for (unsigned a = 0; a < lines_.size(); a++) { line = map_->line(a); @@ -3108,7 +3116,7 @@ void MapRenderer3D::checkVisibleFlats() } flats_ = new Flat*[n_flats_]; - for(unsigned a = 0; a < n_flats_; a++) + for (unsigned a = 0; a < n_flats_; a++) flats_[a] = nullptr; // Go through sectors diff --git a/src/MapEditor/Renderer/MapRenderer3D.h b/src/MapEditor/Renderer/MapRenderer3D.h index 7b4559856..50a25a794 100644 --- a/src/MapEditor/Renderer/MapRenderer3D.h +++ b/src/MapEditor/Renderer/MapRenderer3D.h @@ -1,10 +1,14 @@ #pragma once -#include "MapEditor/Edit/Edit3D.h" -#include "SLADEMap/SLADEMap.h" +#include "MapEditor/Item.h" +#include "Utility/Colour.h" namespace slade { +class MapThing; +class SLADEMap; +class MapSector; +class MapLine; class ItemSelection; class Polygon2D; @@ -114,7 +118,7 @@ class MapRenderer3D Quad* getQuad(mapeditor::Item item); Flat* getFlat(mapeditor::Item item); - vector>& getSectorFlats() { return sector_flats_; }; + vector>& getSectorFlats() { return sector_flats_; } // Camera void cameraMove(double distance, bool z = true); @@ -123,8 +127,8 @@ class MapRenderer3D void cameraStrafe(double distance); void cameraPitch(double amount); void cameraUpdateVectors(); - void cameraSet(Vec3d position, Vec2d direction); - void cameraSetPosition(Vec3d position); + void cameraSet(const Vec3d& position, const Vec2d& direction); + void cameraSetPosition(const Vec3d& position); void cameraApplyGravity(double mult); void cameraLook(double xrel, double yrel); @@ -158,8 +162,8 @@ class MapRenderer3D void renderFlatSelection(const ItemSelection& selection, float alpha = 1.0f) const; // Walls - void setupQuad(Quad* quad, Seg2d seg, double top, double bottom) const; - void setupQuad(Quad* quad, Seg2d seg, Plane top, Plane bottom) const; + void setupQuad(Quad* quad, const Seg2d& seg, double top, double bottom) const; + void setupQuad(Quad* quad, const Seg2d& seg, const Plane& top, const Plane& bottom) const; void setupQuadTexCoords( Quad* quad, int length, @@ -214,10 +218,8 @@ class MapRenderer3D Vec3d cam_position_; Vec2d cam_direction_; double cam_pitch_ = 0.; - double cam_angle_ = 0.; Vec3d cam_dir3d_; Vec3d cam_strafe_; - double gravity_ = 0.5; int item_dist_ = 0; // Map Structures diff --git a/src/MapEditor/Renderer/Overlays/InfoOverlay3d.cpp b/src/MapEditor/Renderer/Overlays/InfoOverlay3d.cpp index fa0b37a55..3f516ba2a 100644 --- a/src/MapEditor/Renderer/Overlays/InfoOverlay3d.cpp +++ b/src/MapEditor/Renderer/Overlays/InfoOverlay3d.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -39,9 +39,15 @@ #include "MapEditor/MapEditContext.h" #include "MapEditor/MapEditor.h" #include "MapEditor/MapTextureManager.h" -#include "MapEditor/UI/MapEditorWindow.h" #include "OpenGL/Drawing.h" +#include "OpenGL/GLTexture.h" #include "OpenGL/OpenGL.h" +#include "SLADEMap/MapObject/MapLine.h" +#include "SLADEMap/MapObject/MapSector.h" +#include "SLADEMap/MapObject/MapSide.h" +#include "SLADEMap/MapObject/MapThing.h" +#include "SLADEMap/MapObject/MapVertex.h" +#include "SLADEMap/MapObjectList/SectorList.h" #include "SLADEMap/SLADEMap.h" #include "Utility/StringUtils.h" @@ -132,7 +138,7 @@ void InfoOverlay3D::update(mapeditor::Item item, SLADEMap* map) strutil::removeLast(flags, 2); info_.push_back(flags); - info_.push_back(fmt::format("Length: {}", (int)line->length())); + info_.push_back(fmt::format("Length: {}", static_cast(line->length()))); // Other potential info: special, sector# @@ -168,9 +174,10 @@ void InfoOverlay3D::update(mapeditor::Item item, SLADEMap* map) if (xoff_part == 0) xoff_info = fmt::format("{}", xoff); else if (xoff_part > 0) - xoff_info = fmt::format("{:1.2f} ({}+{:1.2f})", (double)xoff + xoff_part, xoff, xoff_part); + xoff_info = fmt::format("{:1.2f} ({}+{:1.2f})", static_cast(xoff) + xoff_part, xoff, xoff_part); else - xoff_info = fmt::format("{:1.2f} ({}-{:1.2f})", (double)xoff + xoff_part, xoff, -xoff_part); + xoff_info = fmt::format( + "{:1.2f} ({}-{:1.2f})", static_cast(xoff) + xoff_part, xoff, -xoff_part); // Get y offset info int yoff = side->texOffsetY(); @@ -187,9 +194,10 @@ void InfoOverlay3D::update(mapeditor::Item item, SLADEMap* map) if (yoff_part == 0) yoff_info = fmt::format("{}", yoff); else if (yoff_part > 0) - yoff_info = fmt::format("{:1.2f} ({}+{:1.2f})", (double)yoff + yoff_part, yoff, yoff_part); + yoff_info = fmt::format("{:1.2f} ({}+{:1.2f})", static_cast(yoff) + yoff_part, yoff, yoff_part); else - yoff_info = fmt::format("{:1.2f} ({}-{:1.2f})", (double)yoff + yoff_part, yoff, -yoff_part); + yoff_info = fmt::format( + "{:1.2f} ({}-{:1.2f})", static_cast(yoff) + yoff_part, yoff, -yoff_part); info2_.push_back(fmt::format("Offsets: {}, {}", xoff_info, yoff_info)); } @@ -293,9 +301,10 @@ void InfoOverlay3D::update(mapeditor::Item item, SLADEMap* map) right_height = top_plane.heightAt(right_point) - bottom_plane.heightAt(right_point); } if (fabs(left_height - right_height) < 0.001) - info2_.push_back(fmt::format("Height: {}", (int)left_height)); + info2_.push_back(fmt::format("Height: {}", static_cast(left_height))); else - info2_.push_back(fmt::format("Height: {} ~ {}", (int)left_height, (int)right_height)); + info2_.push_back( + fmt::format("Height: {} ~ {}", static_cast(left_height), static_cast(right_height))); // Texture if (item_type == mapeditor::ItemType::WallBottom) @@ -465,10 +474,14 @@ void InfoOverlay3D::update(mapeditor::Item item, SLADEMap* map) // Position if (mapeditor::editContext().mapDesc().format == MapFormat::Hexen || mapeditor::editContext().mapDesc().format == MapFormat::UDMF) - info_.push_back( - fmt::format("Position: {}, {}, {}", (int)thing->xPos(), (int)thing->yPos(), (int)thing->zPos())); + info_.push_back(fmt::format( + "Position: {}, {}, {}", + static_cast(thing->xPos()), + static_cast(thing->yPos()), + static_cast(thing->zPos()))); else - info_.push_back(fmt::format("Position: {}, {}", (int)thing->xPos(), (int)thing->yPos())); + info_.push_back( + fmt::format("Position: {}, {}", static_cast(thing->xPos()), static_cast(thing->yPos()))); // Type @@ -567,7 +580,6 @@ void InfoOverlay3D::draw(int bottom, int right, int middle, float alpha) // Slide in/out animation float alpha_inv = 1.0f - alpha; - int bottom2 = bottom; bottom += height * alpha_inv * alpha_inv; // Draw overlay background @@ -608,7 +620,6 @@ void InfoOverlay3D::drawTexture(float alpha, int x, int y) const int line_height = 16 * scale; // Get colours - ColRGBA col_bg = colourconfig::colour("map_3d_overlay_background"); ColRGBA col_fg = colourconfig::colour("map_3d_overlay_foreground"); col_fg.a = col_fg.a * alpha; diff --git a/src/MapEditor/Renderer/Overlays/InfoOverlay3d.h b/src/MapEditor/Renderer/Overlays/InfoOverlay3d.h index c55544e9d..93d3cbe59 100644 --- a/src/MapEditor/Renderer/Overlays/InfoOverlay3d.h +++ b/src/MapEditor/Renderer/Overlays/InfoOverlay3d.h @@ -1,6 +1,6 @@ #pragma once -#include "MapEditor/Edit/Edit3D.h" +#include "MapEditor/Item.h" namespace slade { diff --git a/src/MapEditor/Renderer/Overlays/LineInfoOverlay.cpp b/src/MapEditor/Renderer/Overlays/LineInfoOverlay.cpp index d9f36548d..60e2e7041 100644 --- a/src/MapEditor/Renderer/Overlays/LineInfoOverlay.cpp +++ b/src/MapEditor/Renderer/Overlays/LineInfoOverlay.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -33,6 +33,7 @@ // ----------------------------------------------------------------------------- #include "Main.h" #include "LineInfoOverlay.h" +#include "Game/ActionSpecial.h" #include "Game/Configuration.h" #include "General/ColourConfiguration.h" #include "MapEditor/MapEditContext.h" @@ -42,6 +43,7 @@ #include "OpenGL/GLTexture.h" #include "OpenGL/OpenGL.h" #include "SLADEMap/MapObject/MapLine.h" +#include "SLADEMap/MapObject/MapSector.h" #include "SLADEMap/MapObject/MapSide.h" #include "Utility/MathStuff.h" #include "Utility/StringUtils.h" @@ -61,10 +63,15 @@ using namespace slade; // ----------------------------------------------------------------------------- LineInfoOverlay::LineInfoOverlay() : scale_{ drawing::fontSize() / 12.0 }, - text_box_{ "", drawing::Font::Condensed, 100, int(16 * scale_) } + text_box_{ new TextBox("", drawing::Font::Condensed, 100, static_cast(16 * scale_)) } { } +// ----------------------------------------------------------------------------- +// LineInfoOverlay class destructor +// ----------------------------------------------------------------------------- +LineInfoOverlay::~LineInfoOverlay() = default; + // ----------------------------------------------------------------------------- // Updates the overlay with info from [line] // ----------------------------------------------------------------------------- @@ -118,7 +125,7 @@ void LineInfoOverlay::update(MapLine* line) info_text += (fmt::format("\nFlags: {}", game::configuration().lineFlagsString(line))); // Setup text box - text_box_.setText(info_text); + text_box_->setText(info_text); // Check needed textures int needed_tex = line->needsTexture(); @@ -188,9 +195,9 @@ void LineInfoOverlay::draw(int bottom, int right, float alpha) if (last_size_ != right - sides_width) { last_size_ = right - sides_width; - text_box_.setSize(right - sides_width); + text_box_->setSize(right - sides_width); } - int height = text_box_.height() + 4; + int height = text_box_->height() + 4; // Get colours ColRGBA col_bg = colourconfig::colour("map_overlay_background"); @@ -220,8 +227,8 @@ void LineInfoOverlay::draw(int bottom, int right, float alpha) drawing::drawBorderedRect(0, bottom - height - 4, main_panel_end, bottom + 2, col_bg, col_border); // Draw info text lines - text_box_.setLineHeight(16 * scale_); - text_box_.draw(2, bottom - height, col_fg); + text_box_->setLineHeight(16 * scale_); + text_box_->draw(2, bottom - height, col_fg); // Side info int x = right - sinf_size; @@ -231,7 +238,7 @@ void LineInfoOverlay::draw(int bottom, int right, float alpha) glDisable(GL_TEXTURE_2D); drawing::drawBorderedRect(x, bottom - height - 4, x + sinf_size, bottom + 2, col_bg, col_border); - drawSide(bottom - 4, right, alpha, side_front_, x); + drawSide(bottom - 4, alpha, side_front_, x); x -= (sinf_size + 2); } if (side_back_.exists) @@ -240,7 +247,7 @@ void LineInfoOverlay::draw(int bottom, int right, float alpha) glDisable(GL_TEXTURE_2D); drawing::drawBorderedRect(x, bottom - height - 4, x + sinf_size, bottom + 2, col_bg, col_border); - drawSide(bottom - 4, right, alpha, side_back_, x); + drawSide(bottom - 4, alpha, side_back_, x); } // Done @@ -250,7 +257,7 @@ void LineInfoOverlay::draw(int bottom, int right, float alpha) // ----------------------------------------------------------------------------- // Draws side/texture info for [side] // ----------------------------------------------------------------------------- -void LineInfoOverlay::drawSide(int bottom, int right, float alpha, Side& side, int xstart) +void LineInfoOverlay::drawSide(int bottom, float alpha, const Side& side, int xstart) const { // Get colours ColRGBA col_fg = colourconfig::colour("map_overlay_foreground"); diff --git a/src/MapEditor/Renderer/Overlays/LineInfoOverlay.h b/src/MapEditor/Renderer/Overlays/LineInfoOverlay.h index 388234427..843271290 100644 --- a/src/MapEditor/Renderer/Overlays/LineInfoOverlay.h +++ b/src/MapEditor/Renderer/Overlays/LineInfoOverlay.h @@ -1,24 +1,23 @@ #pragma once -#include "OpenGL/Drawing.h" - namespace slade { +class TextBox; class MapLine; class LineInfoOverlay { public: LineInfoOverlay(); - ~LineInfoOverlay() = default; + ~LineInfoOverlay(); void update(MapLine* line); void draw(int bottom, int right, float alpha = 1.0f); private: - double scale_ = 1.; - TextBox text_box_; - int last_size_ = 100; + double scale_ = 1.; + unique_ptr text_box_; + int last_size_ = 100; struct Side { @@ -35,7 +34,7 @@ class LineInfoOverlay Side side_front_{}; Side side_back_{}; - void drawSide(int bottom, int right, float alpha, Side& side, int xstart = 0); + void drawSide(int bottom, float alpha, const Side& side, int xstart = 0) const; void drawTexture(float alpha, int x, int y, string_view texture, bool needed, string_view pos = "U") const; }; } // namespace slade diff --git a/src/MapEditor/Renderer/Overlays/LineTextureOverlay.cpp b/src/MapEditor/Renderer/Overlays/LineTextureOverlay.cpp index d38d12189..07d9c6378 100644 --- a/src/MapEditor/Renderer/Overlays/LineTextureOverlay.cpp +++ b/src/MapEditor/Renderer/Overlays/LineTextureOverlay.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -39,6 +39,7 @@ #include "MapEditor/MapTextureManager.h" #include "MapEditor/UI/Dialogs/MapTextureBrowser.h" #include "OpenGL/Drawing.h" +#include "OpenGL/GLTexture.h" #include "SLADEMap/MapObject/MapLine.h" #include "SLADEMap/MapObject/MapSide.h" @@ -64,9 +65,9 @@ void LineTextureOverlay::addTexture(TexInfo& inf, string_view texture) const // Add texture if it doesn't exist already bool exists = false; - for (unsigned a = 0; a < inf.textures.size(); a++) + for (const auto& tex : inf.textures) { - if (inf.textures[a] == texture) + if (tex == texture) { exists = true; break; @@ -79,28 +80,28 @@ void LineTextureOverlay::addTexture(TexInfo& inf, string_view texture) const // ----------------------------------------------------------------------------- // 'Opens' all lines in [list], adds all textures from each // ----------------------------------------------------------------------------- -void LineTextureOverlay::openLines(vector& list) +void LineTextureOverlay::openLines(const vector& list) { // Clear current lines lines_.clear(); side1_ = false; side2_ = false; selected_side_ = 0; - for (unsigned a = 0; a < 6; a++) + for (auto& texture : textures_) { - textures_[a].textures.clear(); - textures_[a].hover = false; - textures_[a].changed = false; + texture.textures.clear(); + texture.hover = false; + texture.changed = false; } // Go through list - for (unsigned a = 0; a < list.size(); a++) + for (auto line : list) { // Add to lines list - lines_.push_back(list[a]); + lines_.push_back(line); // Process first side - auto side1 = list[a]->s1(); + auto side1 = line->s1(); if (side1) { // Add textures @@ -112,7 +113,7 @@ void LineTextureOverlay::openLines(vector& list) } // Process second side - auto side2 = list[a]->s2(); + auto side2 = line->s2(); if (side2) { // Add textures @@ -278,7 +279,6 @@ void LineTextureOverlay::draw(int width, int height, float fade) void LineTextureOverlay::drawTexture(float alpha, int size, TexInfo& tex, string_view position) const { // Get colours - ColRGBA col_bg = colourconfig::colour("map_overlay_background"); ColRGBA col_fg = colourconfig::colour("map_overlay_foreground"); ColRGBA col_sel = colourconfig::colour("map_hilight"); col_fg.a = col_fg.a * alpha; diff --git a/src/MapEditor/Renderer/Overlays/LineTextureOverlay.h b/src/MapEditor/Renderer/Overlays/LineTextureOverlay.h index 24e26e988..eac811441 100644 --- a/src/MapEditor/Renderer/Overlays/LineTextureOverlay.h +++ b/src/MapEditor/Renderer/Overlays/LineTextureOverlay.h @@ -10,10 +10,10 @@ class MapSide; class LineTextureOverlay : public MCOverlay { public: - LineTextureOverlay() = default; - ~LineTextureOverlay() = default; + LineTextureOverlay() = default; + ~LineTextureOverlay() override = default; - void openLines(vector& list); + void openLines(const vector& list); void close(bool cancel) override; void update(long frametime) override; diff --git a/src/MapEditor/Renderer/Overlays/QuickTextureOverlay3d.cpp b/src/MapEditor/Renderer/Overlays/QuickTextureOverlay3d.cpp index 6d0bacd59..1b93df0c3 100644 --- a/src/MapEditor/Renderer/Overlays/QuickTextureOverlay3d.cpp +++ b/src/MapEditor/Renderer/Overlays/QuickTextureOverlay3d.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -42,9 +42,13 @@ #include "OpenGL/Drawing.h" #include "OpenGL/GLTexture.h" #include "OpenGL/OpenGL.h" +#include "SLADEMap/MapObject/MapSector.h" +#include "SLADEMap/MapObject/MapSide.h" +#include "SLADEMap/SLADEMap.h" #include "Utility/StringUtils.h" using namespace slade; +using namespace mapeditor; // ----------------------------------------------------------------------------- @@ -76,8 +80,8 @@ QuickTextureOverlay3d::QuickTextureOverlay3d(MapEditContext* editor) : MCOverlay sel_walls_ = false; for (unsigned a = 0; a < sel.size(); a++) { - if (sel[a].type != mapeditor::ItemType::Thing && sel[a].type != mapeditor::ItemType::Ceiling - && sel[a].type != mapeditor::ItemType::Floor) + if (sel[a].type != ItemType::Thing && sel[a].type != ItemType::Ceiling + && sel[a].type != ItemType::Floor) { sel_walls_ = true; initial = a; @@ -88,15 +92,15 @@ QuickTextureOverlay3d::QuickTextureOverlay3d(MapEditContext* editor) : MCOverlay // Get initial texture string tex_init; - if (sel[initial].type == mapeditor::ItemType::Ceiling) + if (sel[initial].type == ItemType::Ceiling) tex_init = editor->map().sector(sel[initial].index)->ceiling().texture; - else if (sel[initial].type == mapeditor::ItemType::Floor) + else if (sel[initial].type == ItemType::Floor) tex_init = editor->map().sector(sel[initial].index)->floor().texture; - else if (sel[initial].type == mapeditor::ItemType::WallTop) + else if (sel[initial].type == ItemType::WallTop) tex_init = editor->map().side(sel[initial].index)->texUpper(); - else if (sel[initial].type == mapeditor::ItemType::WallMiddle) + else if (sel[initial].type == ItemType::WallMiddle) tex_init = editor->map().side(sel[initial].index)->texMiddle(); - else if (sel[initial].type == mapeditor::ItemType::WallBottom) + else if (sel[initial].type == ItemType::WallBottom) tex_init = editor->map().side(sel[initial].index)->texLower(); auto map_format = editor->map().currentFormat(); @@ -187,7 +191,7 @@ void QuickTextureOverlay3d::setTexture(string_view name) // ----------------------------------------------------------------------------- // Applies the current texture to all selected walls/flats // ----------------------------------------------------------------------------- -void QuickTextureOverlay3d::applyTexture() +void QuickTextureOverlay3d::applyTexture() const { // Check editor is associated if (!editor_) @@ -202,18 +206,18 @@ void QuickTextureOverlay3d::applyTexture() for (auto& item : selection) { // Thing (skip) - if (item.type == mapeditor::ItemType::Thing) + if (item.type == ItemType::Thing) continue; // Floor - if (item.type == mapeditor::ItemType::Floor && sel_flats_) + if (item.type == ItemType::Floor && sel_flats_) { if (auto sector = item.asSector(editor_->map())) sector->setFloorTexture(textures_[current_index_].name); } // Ceiling - else if (item.type == mapeditor::ItemType::Ceiling && sel_flats_) + else if (item.type == ItemType::Ceiling && sel_flats_) { if (auto sector = item.asSector(editor_->map())) sector->setCeilingTexture(textures_[current_index_].name); @@ -225,13 +229,13 @@ void QuickTextureOverlay3d::applyTexture() if (auto side = item.asSide(editor_->map())) { // Upper - if (item.type == mapeditor::ItemType::WallTop) + if (item.type == ItemType::WallTop) side->setTexUpper(textures_[current_index_].name); // Middle - else if (item.type == mapeditor::ItemType::WallMiddle) + else if (item.type == ItemType::WallMiddle) side->setTexMiddle(textures_[current_index_].name); // Lower - else if (item.type == mapeditor::ItemType::WallBottom) + else if (item.type == ItemType::WallBottom) side->setTexLower(textures_[current_index_].name); } } @@ -245,7 +249,7 @@ void QuickTextureOverlay3d::applyTexture() void QuickTextureOverlay3d::update(long frametime) { double target = current_index_; - float mult = (float)frametime / 10.0f; + float mult = static_cast(frametime) / 10.0f; if (anim_offset_ < target - 0.01) anim_offset_ += (target - anim_offset_) * (0.2 * mult); else if (anim_offset_ > target + 0.01) @@ -272,7 +276,7 @@ void QuickTextureOverlay3d::draw(int width, int height, float fade) glEnable(GL_TEXTURE_2D); // Draw textures - double x = ((double)width * 0.5) - (anim_offset_ * 136.0); + double x = (static_cast(width) * 0.5) - (anim_offset_ * 136.0); glColor4f(1.0f, 1.0f, 1.0f, fade); for (unsigned a = 0; a < textures_.size(); a++) { @@ -342,7 +346,7 @@ void QuickTextureOverlay3d::drawTexture(unsigned index, double x, double bottom, // ----------------------------------------------------------------------------- double QuickTextureOverlay3d::determineSize(double x, int width) const { - double mid = (double)width * 0.5; + double mid = static_cast(width) * 0.5; if (x < mid - 384 || x > mid + 384) return 1.0; @@ -428,7 +432,7 @@ bool QuickTextureOverlay3d::ok(const ItemSelection& sel) bool ok = false; for (auto item : sel) { - if (item.type != mapeditor::ItemType::Thing) + if (item.type != ItemType::Thing) { ok = true; break; diff --git a/src/MapEditor/Renderer/Overlays/QuickTextureOverlay3d.h b/src/MapEditor/Renderer/Overlays/QuickTextureOverlay3d.h index f2f4425cd..1ab3fff7f 100644 --- a/src/MapEditor/Renderer/Overlays/QuickTextureOverlay3d.h +++ b/src/MapEditor/Renderer/Overlays/QuickTextureOverlay3d.h @@ -1,21 +1,23 @@ #pragma once #include "MCOverlay.h" -#include "MapEditor/Edit/Edit3D.h" namespace slade { class ItemSelection; -class MapEditContext; +namespace mapeditor +{ + class MapEditContext; +} class QuickTextureOverlay3d : public MCOverlay { public: - QuickTextureOverlay3d(MapEditContext* editor); - ~QuickTextureOverlay3d() = default; + QuickTextureOverlay3d(mapeditor::MapEditContext* editor); + ~QuickTextureOverlay3d() override = default; void setTexture(string_view name); - void applyTexture(); + void applyTexture() const; void update(long frametime) override; @@ -38,12 +40,12 @@ class QuickTextureOverlay3d : public MCOverlay QTTex(string_view name) : texture{ 0 }, name{ name } {} }; - vector textures_; - unsigned current_index_ = 0; - string search_; - double anim_offset_ = 0.; - MapEditContext* editor_ = nullptr; - bool sel_flats_ = true; - bool sel_walls_ = true; + vector textures_; + unsigned current_index_ = 0; + string search_; + double anim_offset_ = 0.; + mapeditor::MapEditContext* editor_ = nullptr; + bool sel_flats_ = true; + bool sel_walls_ = true; }; } // namespace slade diff --git a/src/MapEditor/Renderer/Overlays/SectorInfoOverlay.cpp b/src/MapEditor/Renderer/Overlays/SectorInfoOverlay.cpp index 932448c53..544976230 100644 --- a/src/MapEditor/Renderer/Overlays/SectorInfoOverlay.cpp +++ b/src/MapEditor/Renderer/Overlays/SectorInfoOverlay.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -38,6 +38,7 @@ #include "MapEditor/MapEditor.h" #include "MapEditor/MapTextureManager.h" #include "OpenGL/Drawing.h" +#include "OpenGL/GLTexture.h" #include "OpenGL/OpenGL.h" #include "SLADEMap/MapObject/MapSector.h" @@ -59,10 +60,15 @@ SectorInfoOverlay::SectorInfoOverlay() text_box_ = std::make_unique("", drawing::Font::Condensed, 100, 16 * (drawing::fontSize() / 12.0)); } +// ----------------------------------------------------------------------------- +// SectorInfoOverlay class destructor +// ----------------------------------------------------------------------------- +SectorInfoOverlay::~SectorInfoOverlay() = default; + // ----------------------------------------------------------------------------- // Updates the overlay with info from [sector] // ----------------------------------------------------------------------------- -void SectorInfoOverlay::update(MapSector* sector) +void SectorInfoOverlay::update(const MapSector* sector) { if (!sector) return; @@ -159,7 +165,6 @@ void SectorInfoOverlay::drawTexture(float alpha, int x, int y, string_view textu int line_height = 16 * scale; // Get colours - auto col_bg = colourconfig::colour("map_overlay_background"); auto col_fg = colourconfig::colour("map_overlay_foreground"); col_fg.a = col_fg.a * alpha; diff --git a/src/MapEditor/Renderer/Overlays/SectorInfoOverlay.h b/src/MapEditor/Renderer/Overlays/SectorInfoOverlay.h index 4e2d24342..f4c3f0b34 100644 --- a/src/MapEditor/Renderer/Overlays/SectorInfoOverlay.h +++ b/src/MapEditor/Renderer/Overlays/SectorInfoOverlay.h @@ -9,9 +9,9 @@ class SectorInfoOverlay { public: SectorInfoOverlay(); - ~SectorInfoOverlay() = default; + ~SectorInfoOverlay(); - void update(MapSector* sector); + void update(const MapSector* sector); void draw(int bottom, int right, float alpha = 1.0f); private: diff --git a/src/MapEditor/Renderer/Overlays/SectorTextureOverlay.cpp b/src/MapEditor/Renderer/Overlays/SectorTextureOverlay.cpp index ea6863f6c..ba31af340 100644 --- a/src/MapEditor/Renderer/Overlays/SectorTextureOverlay.cpp +++ b/src/MapEditor/Renderer/Overlays/SectorTextureOverlay.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -40,6 +40,7 @@ #include "MapEditor/MapTextureManager.h" #include "MapEditor/UI/Dialogs/MapTextureBrowser.h" #include "OpenGL/Drawing.h" +#include "OpenGL/GLTexture.h" #include "SLADEMap/MapObject/MapSector.h" using namespace slade; @@ -58,7 +59,7 @@ using namespace slade; void SectorTextureOverlay::update(long frametime) { // Get frame time multiplier - float mult = (float)frametime / 10.0f; + float mult = static_cast(frametime) / 10.0f; // Update animations anim_floor_ += 0.1f * mult; @@ -176,10 +177,10 @@ void SectorTextureOverlay::draw(int width, int height, float fade) // ----------------------------------------------------------------------------- // Draws the texture box for [textures] // ----------------------------------------------------------------------------- -void SectorTextureOverlay::drawTexture(float alpha, int x, int y, int size, vector& textures, bool hover) const +void SectorTextureOverlay::drawTexture(float alpha, int x, int y, int size, const vector& textures, bool hover) + const { // Get colours - auto col_bg = colourconfig::colour("map_overlay_background"); auto col_fg = colourconfig::colour("map_overlay_foreground"); auto col_sel = colourconfig::colour("map_hilight"); col_fg.a = col_fg.a * alpha; @@ -223,7 +224,7 @@ void SectorTextureOverlay::drawTexture(float alpha, int x, int y, int size, vect // ----------------------------------------------------------------------------- // 'Opens' all sectors in [list], adds both textures from each // ----------------------------------------------------------------------------- -void SectorTextureOverlay::openSectors(vector& list) +void SectorTextureOverlay::openSectors(const vector& list) { // Clear current sectors list (if any) sectors_.clear(); diff --git a/src/MapEditor/Renderer/Overlays/SectorTextureOverlay.h b/src/MapEditor/Renderer/Overlays/SectorTextureOverlay.h index 95b8a4e83..3f938c593 100644 --- a/src/MapEditor/Renderer/Overlays/SectorTextureOverlay.h +++ b/src/MapEditor/Renderer/Overlays/SectorTextureOverlay.h @@ -9,16 +9,16 @@ class MapSector; class SectorTextureOverlay : public MCOverlay { public: - SectorTextureOverlay() = default; - ~SectorTextureOverlay() = default; + SectorTextureOverlay() = default; + ~SectorTextureOverlay() override = default; - void openSectors(vector& list); + void openSectors(const vector& list); void close(bool cancel) override; void update(long frametime) override; // Drawing void draw(int width, int height, float fade) override; - void drawTexture(float alpha, int x, int y, int size, vector& textures, bool hover) const; + void drawTexture(float alpha, int x, int y, int size, const vector& textures, bool hover) const; // Input void mouseMotion(int x, int y) override; diff --git a/src/MapEditor/Renderer/Overlays/ThingInfoOverlay.cpp b/src/MapEditor/Renderer/Overlays/ThingInfoOverlay.cpp index 2a19f8130..c7a1d1334 100644 --- a/src/MapEditor/Renderer/Overlays/ThingInfoOverlay.cpp +++ b/src/MapEditor/Renderer/Overlays/ThingInfoOverlay.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -32,12 +32,14 @@ // ----------------------------------------------------------------------------- #include "Main.h" #include "ThingInfoOverlay.h" +#include "Game/ActionSpecial.h" #include "Game/Configuration.h" #include "General/ColourConfiguration.h" #include "MapEditor/MapEditContext.h" #include "MapEditor/MapEditor.h" #include "MapEditor/MapTextureManager.h" #include "OpenGL/Drawing.h" +#include "OpenGL/GLTexture.h" #include "OpenGL/OpenGL.h" #include "SLADEMap/MapObject/MapThing.h" @@ -63,10 +65,15 @@ EXTERN_CVAR(Bool, use_zeth_icons) // ThingInfoOverlay class constructor // ----------------------------------------------------------------------------- ThingInfoOverlay::ThingInfoOverlay() : - text_box_{ "", drawing::Font::Condensed, 100, int(16 * (drawing::fontSize() / 12.0)) } + text_box_{ new TextBox("", drawing::Font::Condensed, 100, static_cast(16 * (drawing::fontSize() / 12.0))) } { } +// ----------------------------------------------------------------------------- +// ThingInfoOverlay class destructor +// ----------------------------------------------------------------------------- +ThingInfoOverlay::~ThingInfoOverlay() = default; + // ----------------------------------------------------------------------------- // Updates the overlay with info from [thing] // ----------------------------------------------------------------------------- @@ -93,9 +100,13 @@ void ThingInfoOverlay::update(MapThing* thing) // Position if (map_format != MapFormat::Doom) info_text += fmt::format( - "Position: {}, {}, {}\n", (int)thing->xPos(), (int)thing->yPos(), (int)(thing->zPos())); + "Position: {}, {}, {}\n", + static_cast(thing->xPos()), + static_cast(thing->yPos()), + static_cast(thing->zPos())); else - info_text += fmt::format("Position: {}, {}\n", (int)thing->xPos(), (int)thing->yPos()); + info_text += fmt::format( + "Position: {}, {}\n", static_cast(thing->xPos()), static_cast(thing->yPos())); // Direction int angle = thing->angle(); @@ -158,7 +169,7 @@ void ThingInfoOverlay::update(MapThing* thing) zeth_icon_ = tt.zethIcon(); // Setup text box - text_box_.setText(info_text); + text_box_->setText(info_text); } // ----------------------------------------------------------------------------- @@ -178,9 +189,9 @@ void ThingInfoOverlay::draw(int bottom, int right, float alpha) if (last_size_ != right) { last_size_ = right; - text_box_.setSize(right - 68); + text_box_->setSize(right - 68); } - int height = text_box_.height() + 4; + int height = text_box_->height() + 4; // Slide in/out animation float alpha_inv = 1.0f - alpha; @@ -198,8 +209,8 @@ void ThingInfoOverlay::draw(int bottom, int right, float alpha) drawing::drawBorderedRect(0, bottom - height - 4, right, bottom + 2, col_bg, col_border); // Draw info text lines - text_box_.setLineHeight(16 * (drawing::fontSize() / 12.0)); - text_box_.draw(2, bottom - height, col_fg); + text_box_->setLineHeight(16 * (drawing::fontSize() / 12.0)); + text_box_->draw(2, bottom - height, col_fg); // Draw sprite bool isicon = false; diff --git a/src/MapEditor/Renderer/Overlays/ThingInfoOverlay.h b/src/MapEditor/Renderer/Overlays/ThingInfoOverlay.h index 2ae91b858..2cd579e34 100644 --- a/src/MapEditor/Renderer/Overlays/ThingInfoOverlay.h +++ b/src/MapEditor/Renderer/Overlays/ThingInfoOverlay.h @@ -1,9 +1,8 @@ #pragma once -#include "OpenGL/Drawing.h" - namespace slade { +class TextBox; class MapThing; class GLTexture; @@ -11,18 +10,18 @@ class ThingInfoOverlay { public: ThingInfoOverlay(); - ~ThingInfoOverlay() = default; + ~ThingInfoOverlay(); void update(MapThing* thing); void draw(int bottom, int right, float alpha = 1.0f); private: - string sprite_; - string translation_; - string palette_; - string icon_; - int zeth_icon_ = -1; - TextBox text_box_; - int last_size_ = 100; + string sprite_; + string translation_; + string palette_; + string icon_; + int zeth_icon_ = -1; + unique_ptr text_box_; + int last_size_ = 100; }; } // namespace slade diff --git a/src/MapEditor/Renderer/Overlays/VertexInfoOverlay.cpp b/src/MapEditor/Renderer/Overlays/VertexInfoOverlay.cpp index 18e27bb44..8ca49788a 100644 --- a/src/MapEditor/Renderer/Overlays/VertexInfoOverlay.cpp +++ b/src/MapEditor/Renderer/Overlays/VertexInfoOverlay.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -34,6 +34,7 @@ #include "Main.h" #include "VertexInfoOverlay.h" #include "General/ColourConfiguration.h" +#include "General/Defs.h" #include "OpenGL/Drawing.h" #include "OpenGL/OpenGL.h" #include "SLADEMap/MapObject/MapVertex.h" @@ -62,7 +63,7 @@ void VertexInfoOverlay::update(MapVertex* vertex) bool udmf = vertex->parentMap()->currentFormat() == MapFormat::UDMF; // Update info string - auto pos = vertex->position(); + auto pos = vertex->position(); auto line = fmt::format("Vertex {}: (", vertex->index()); if (pos.x == static_cast(pos.x)) line += fmt::format("{}, ", static_cast(pos.x)); @@ -72,7 +73,7 @@ void VertexInfoOverlay::update(MapVertex* vertex) line += fmt::format("{})", static_cast(pos.y)); else line += fmt::format("{:1.4f})", pos.y); - + if (global::debug) line += fmt::format(" ({})", vertex->objId()); diff --git a/src/MapEditor/Renderer/Renderer.cpp b/src/MapEditor/Renderer/Renderer.cpp index 976068553..16ec67324 100644 --- a/src/MapEditor/Renderer/Renderer.cpp +++ b/src/MapEditor/Renderer/Renderer.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -36,11 +36,28 @@ #include "Game/Configuration.h" #include "General/Clipboard.h" #include "General/ColourConfiguration.h" +#include "MCAnimations.h" +#include "MapEditor/Edit/Input.h" #include "MapEditor/Edit/LineDraw.h" +#include "MapEditor/Edit/MoveObjects.h" +#include "MapEditor/Edit/ObjectEdit.h" +#include "MapEditor/MapClipboardItems.h" #include "MapEditor/MapEditContext.h" +#include "MapEditor/MapEditor.h" +#include "MapRenderer2D.h" +#include "MapRenderer3D.h" #include "OpenGL/Drawing.h" #include "OpenGL/OpenGL.h" +#include "OpenGL/View.h" #include "Overlays/MCOverlay.h" +#include "SLADEMap/MapObject/MapLine.h" +#include "SLADEMap/MapObject/MapSector.h" +#include "SLADEMap/MapObject/MapSide.h" +#include "SLADEMap/MapObject/MapThing.h" +#include "SLADEMap/MapObject/MapVertex.h" +#include "SLADEMap/MapObjectList/SectorList.h" +#include "SLADEMap/MapObjectList/VertexList.h" +#include "SLADEMap/SLADEMap.h" #include "Utility/MathStuff.h" using namespace slade; @@ -92,57 +109,65 @@ EXTERN_CVAR(Int, vertex_size) // Renderer class constructor // ----------------------------------------------------------------------------- Renderer::Renderer(MapEditContext& context) : - context_{ context }, renderer_2d_{ &context.map() }, renderer_3d_{ &context.map() }, view_{ true } + context_{ &context }, + renderer_2d_{ new MapRenderer2D(&context.map()) }, + renderer_3d_{ new MapRenderer3D(&context.map()) }, + view_{ new gl::View(true) } { } +// ----------------------------------------------------------------------------- +// Renderer class destructor +// ----------------------------------------------------------------------------- +Renderer::~Renderer() = default; + // ----------------------------------------------------------------------------- // Updates/refreshes the 2d and 3d renderers // ----------------------------------------------------------------------------- -void Renderer::forceUpdate() +void Renderer::forceUpdate() const { - renderer_2d_.forceUpdate(fade_lines_); - renderer_3d_.clearData(); + renderer_2d_->forceUpdate(fade_lines_); + renderer_3d_->clearData(); } // ----------------------------------------------------------------------------- // Scrolls the view to be centered on map coordinates [x,y] // ----------------------------------------------------------------------------- -void Renderer::setView(double map_x, double map_y) +void Renderer::setView(double map_x, double map_y) const { // Set new view - view_.setOffset(map_x, map_y); + view_->setOffset(map_x, map_y); // Update object visibility - renderer_2d_.updateVisibility(view_.visibleRegion().tl, view_.visibleRegion().br); + renderer_2d_->updateVisibility(view_->visibleRegion().tl, view_->visibleRegion().br); } // ----------------------------------------------------------------------------- // Sets the view size to [width,height] // ----------------------------------------------------------------------------- -void Renderer::setViewSize(int width, int height) +void Renderer::setViewSize(int width, int height) const { // Set new size - view_.setSize(width, height); + view_->setSize(width, height); // Update object visibility - renderer_2d_.updateVisibility(view_.visibleRegion().tl, view_.visibleRegion().br); + renderer_2d_->updateVisibility(view_->visibleRegion().tl, view_->visibleRegion().br); } // ----------------------------------------------------------------------------- // Sets the view such that the map coordinate [y] is at the top of the canvas // ----------------------------------------------------------------------------- -void Renderer::setTopY(double map_y) +void Renderer::setTopY(double map_y) const { - setView(view_.offset().x, view_.offset().y - (view_.canvasY(0) - map_y)); - view_.resetInter(false, true, false); + setView(view_->offset().x, view_->offset().y - (view_->canvasY(0) - map_y)); + view_->resetInter(false, true, false); } // ----------------------------------------------------------------------------- // Scrolls the view relatively by [x,y]. // If [scale] is true, [x,y] will be scaled by the current view scale // ----------------------------------------------------------------------------- -void Renderer::pan(double x, double y, bool scale) +void Renderer::pan(double x, double y, bool scale) const { if (scale) { @@ -150,7 +175,7 @@ void Renderer::pan(double x, double y, bool scale) y /= view().scale(); } - setView(view_.offset().x + x, view_.offset().y + y); + setView(view_->offset().x + x, view_->offset().y + y); } // ----------------------------------------------------------------------------- @@ -164,17 +189,17 @@ void Renderer::zoom(double amount, bool toward_cursor) if (toward_cursor) { cursor_zoom_disabled_ = false; - view_.zoomToward(amount, context_.input().mousePos()); + view_->zoomToward(amount, context_->input().mousePos()); } else { cursor_zoom_disabled_ = true; - view_.zoom(amount); + view_->zoom(amount); } // Update object visibility - renderer_2d_.setScale(view_.scale(true)); - renderer_2d_.updateVisibility(view_.visibleRegion().tl, view_.visibleRegion().br); + renderer_2d_->setScale(view_->scale(true)); + renderer_2d_->updateVisibility(view_->visibleRegion().tl, view_->visibleRegion().br); } // ----------------------------------------------------------------------------- @@ -187,16 +212,16 @@ void Renderer::viewFitToMap(bool snap) cursor_zoom_disabled_ = true; // Fit the view to the map bbox - view_.fitTo(context_.map().bounds()); + view_->fitTo(context_->map().bounds()); // Don't animate if specified if (snap) - view_.resetInter(true, true, true); + view_->resetInter(true, true, true); // Update object visibility - renderer_2d_.setScale(view_.scale(true)); - renderer_2d_.forceUpdate(); - renderer_2d_.updateVisibility(view_.visibleRegion().tl, view_.visibleRegion().br); + renderer_2d_->setScale(view_->scale(true)); + renderer_2d_->forceUpdate(); + renderer_2d_->updateVisibility(view_->visibleRegion().tl, view_->visibleRegion().br); } // ----------------------------------------------------------------------------- @@ -250,12 +275,12 @@ void Renderer::viewFitToObjects(const vector& objects) } // Fit the view to the bbox - view_.fitTo(bbox); + view_->fitTo(bbox); // Update object visibility - renderer_2d_.setScale(view_.scale(true)); - renderer_2d_.forceUpdate(); - renderer_2d_.updateVisibility(view_.visibleRegion().tl, view_.visibleRegion().br); + renderer_2d_->setScale(view_->scale(true)); + renderer_2d_->forceUpdate(); + renderer_2d_->updateVisibility(view_->visibleRegion().tl, view_->visibleRegion().br); } // ----------------------------------------------------------------------------- @@ -267,9 +292,10 @@ double Renderer::interpolateView(bool smooth, double view_speed, double mult) auto anim_view_speed = view_speed; if (smooth) { - auto mouse_pos = Vec2d{ (double)context_.input().mousePos().x, (double)context_.input().mousePos().y }; + auto mouse_pos = Vec2d{ static_cast(context_->input().mousePos().x), + static_cast(context_->input().mousePos().y) }; - if (!view_.interpolate(mult * view_speed, cursor_zoom_disabled_ ? nullptr : &mouse_pos)) + if (!view_->interpolate(mult * view_speed, cursor_zoom_disabled_ ? nullptr : &mouse_pos)) { cursor_zoom_disabled_ = false; anim_view_speed = 0.05; @@ -282,7 +308,7 @@ double Renderer::interpolateView(bool smooth, double view_speed, double mult) } } else - view_.resetInter(true, true, true); + view_->resetInter(true, true, true); return anim_view_speed; } @@ -293,23 +319,23 @@ double Renderer::interpolateView(bool smooth, double view_speed, double mult) bool Renderer::viewIsInterpolated() const { return ( - view_.scale(false) != view_.scale(true) || view_.offset(false).x != view_.offset(true).x - || view_.offset(false).y != view_.offset(true).y); + view_->scale(false) != view_->scale(true) || view_->offset(false).x != view_->offset(true).x + || view_->offset(false).y != view_->offset(true).y); } // ----------------------------------------------------------------------------- // Sets the 3d camera to match [thing] // ----------------------------------------------------------------------------- -void Renderer::setCameraThing(const MapThing* thing) +void Renderer::setCameraThing(const MapThing* thing) const { // Determine position Vec3d pos(thing->position(), 40); - auto sector = context_.map().sectors().atPos(thing->position()); + auto sector = context_->map().sectors().atPos(thing->position()); if (sector) pos.z += sector->floor().plane.heightAt(pos.x, pos.y); // Set camera position & direction - renderer_3d_.cameraSet(pos, math::vectorAngle(math::degToRad(thing->angle()))); + renderer_3d_->cameraSet(pos, math::vectorAngle(math::degToRad(thing->angle()))); } // ----------------------------------------------------------------------------- @@ -317,7 +343,7 @@ void Renderer::setCameraThing(const MapThing* thing) // ----------------------------------------------------------------------------- Vec2d Renderer::cameraPos2D() const { - return { renderer_3d_.camPosition().x, renderer_3d_.camPosition().y }; + return { renderer_3d_->camPosition().x, renderer_3d_->camPosition().y }; } // ----------------------------------------------------------------------------- @@ -325,7 +351,7 @@ Vec2d Renderer::cameraPos2D() const // ----------------------------------------------------------------------------- Vec2d Renderer::cameraDir2D() const { - return renderer_3d_.camDirection(); + return renderer_3d_->camDirection(); } // ----------------------------------------------------------------------------- @@ -334,7 +360,7 @@ Vec2d Renderer::cameraDir2D() const void Renderer::drawGrid() const { // Get grid size - int gridsize = context_.gridSize(); + int gridsize = context_->gridSize(); // Disable line smoothing (not needed for straight, 1.0-sized lines) glDisable(GL_LINE_SMOOTH); @@ -351,13 +377,13 @@ void Renderer::drawGrid() const glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); // Determine smallest grid size to bother drawing - int grid_hidelevel = 2.0 / view_.scale(); + int grid_hidelevel = 2.0 / view_->scale(); // Determine canvas edges in map coordinates - int start_x = view_.canvasX(0, true); - int end_x = view_.canvasX(view_.size().x, true); - int start_y = view_.canvasY(view_.size().y, true); - int end_y = view_.canvasY(0, true); + int start_x = view_->canvasX(0, true); + int end_x = view_->canvasX(view_->size().x, true); + int start_y = view_->canvasY(view_->size().y, true); + int end_y = view_->canvasY(0, true); // Draw regular grid if it's not too small if (gridsize > grid_hidelevel) @@ -473,9 +499,9 @@ void Renderer::drawGrid() const // Draw crosshair if needed if (map_crosshair > 0) { - auto mouse_pos = context_.input().mousePos(); - double x = context_.snapToGrid(view_.canvasX(mouse_pos.x), false); - double y = context_.snapToGrid(view_.canvasY(mouse_pos.y), false); + auto mouse_pos = context_->input().mousePos(); + double x = context_->snapToGrid(view_->canvasX(mouse_pos.x), false); + double y = context_->snapToGrid(view_->canvasY(mouse_pos.y), false); auto& def = colourconfig::colDef("map_64grid"); auto col = def.colour; @@ -485,8 +511,8 @@ void Renderer::drawGrid() const { col = col.ampf(1.0f, 1.0f, 1.0f, 2.0f); auto col2 = col.ampf(1.0f, 1.0f, 1.0f, 0.0f); - double size = context_.gridSize(); - double one = 1.0 / view_.scale(true); + double size = context_->gridSize(); + double one = 1.0 / view_->scale(true); gl::setBlend(def.blendMode()); @@ -519,10 +545,10 @@ void Renderer::drawGrid() const gl::setColour(col, def.blendMode()); glBegin(GL_LINES); - glVertex2d(x, view_.visibleRegion().tl.y); - glVertex2d(x, view_.visibleRegion().br.y); - glVertex2d(view_.visibleRegion().tl.x, y); - glVertex2d(view_.visibleRegion().br.x, y); + glVertex2d(x, view_->visibleRegion().tl.y); + glVertex2d(x, view_->visibleRegion().br.y); + glVertex2d(view_->visibleRegion().tl.x, y); + glVertex2d(view_->visibleRegion().br.x, y); glEnd(); } } @@ -540,10 +566,10 @@ void Renderer::drawEditorMessages() const auto col_bg = colourconfig::colour("map_editor_message_outline"); // Go through editor messages - for (unsigned a = 0; a < context_.numEditorMessages(); a++) + for (unsigned a = 0; a < context_->numEditorMessages(); a++) { // Check message time - long time = context_.editorMessageTime(a); + long time = context_->editorMessageTime(a); if (time > 2000) continue; @@ -567,7 +593,7 @@ void Renderer::drawEditorMessages() const // Draw message drawing::setTextOutline(1.0f, col_bg); - drawing::drawText(context_.editorMessage(a), 0, yoff, col, drawing::Font::Bold); + drawing::drawText(context_->editorMessage(a), 0, yoff, col, drawing::Font::Bold); yoff += 16; } @@ -580,7 +606,7 @@ void Renderer::drawEditorMessages() const void Renderer::drawFeatureHelpText() const { // Check if any text - auto& help_lines = context_.featureHelpLines(); + auto& help_lines = context_->featureHelpLines(); if (help_lines.empty() || !map_show_help) return; @@ -591,7 +617,7 @@ void Renderer::drawFeatureHelpText() const col.a = col.a * anim_help_fade_; col_bg.a = col_bg.a * anim_help_fade_; drawing::setTextOutline(1.0f, col_bg); - drawing::drawText(help_lines[0], view_.size().x - 2, 2, col, drawing::Font::Bold, drawing::Align::Right, &bounds); + drawing::drawText(help_lines[0], view_->size().x - 2, 2, col, drawing::Font::Bold, drawing::Align::Right, &bounds); // Draw underline glDisable(GL_TEXTURE_2D); @@ -609,7 +635,7 @@ void Renderer::drawFeatureHelpText() const int yoff = 22; for (unsigned a = 1; a < help_lines.size(); a++) { - drawing::drawText(help_lines[a], view_.size().x - 2, yoff, col, drawing::Font::Bold, drawing::Align::Right); + drawing::drawText(help_lines[a], view_->size().x - 2, yoff, col, drawing::Font::Bold, drawing::Align::Right); yoff += 16; } drawing::setTextOutline(0); @@ -621,7 +647,7 @@ void Renderer::drawFeatureHelpText() const void Renderer::drawSelectionNumbers() const { // Check if any selection exists - auto selection = context_.selection().selectedObjects(); + auto selection = context_->selection().selectedObjects(); if (selection.empty()) return; @@ -630,26 +656,26 @@ void Renderer::drawSelectionNumbers() const // Go through selection string text; - view_.setOverlayCoords(true); - if (context_.selection().size() <= map_max_selection_numbers * 0.5) + view_->setOverlayCoords(true); + if (context_->selection().size() <= map_max_selection_numbers * 0.5) drawing::setTextOutline(1.0, ColRGBA::BLACK); for (unsigned a = 0; a < selection.size(); a++) { - if ((int)a > map_max_selection_numbers) + if (static_cast(a) > map_max_selection_numbers) break; if (!selection[a]) continue; auto tp = selection[a]->getPoint(MapObject::Point::Text); - tp.x = view_.screenX(tp.x); - tp.y = view_.screenY(tp.y); + tp.x = view_->screenX(tp.x); + tp.y = view_->screenY(tp.y); text = fmt::format("{}", a + 1); auto ts = drawing::textExtents(text, drawing::Font::Bold); tp.x -= ts.x * 0.5; tp.y -= ts.y * 0.5; - if (context_.editMode() == Mode::Vertices) + if (context_->editMode() == Mode::Vertices) { tp.x += 8; tp.y += 8; @@ -659,7 +685,7 @@ void Renderer::drawSelectionNumbers() const drawing::drawText(fmt::format("{}", a + 1), tp.x, tp.y, col, drawing::Font::Bold); } drawing::setTextOutline(0); - view_.setOverlayCoords(false); + view_->setOverlayCoords(false); glDisable(GL_TEXTURE_2D); } @@ -670,7 +696,7 @@ void Renderer::drawSelectionNumbers() const void Renderer::drawThingQuickAngleLines() const { // Check if any selection exists - auto selection = context_.selection().selectedThings(); + auto selection = context_->selection().selectedThings(); if (selection.empty()) return; @@ -679,7 +705,7 @@ void Renderer::drawThingQuickAngleLines() const gl::setColour(col); // Draw lines - auto mouse_pos_m = view_.canvasPos(context_.input().mousePos(), true); + auto mouse_pos_m = view_->canvasPos(context_->input().mousePos(), true); glLineWidth(2.0f); glBegin(GL_LINES); for (auto& thing : selection) @@ -693,10 +719,10 @@ void Renderer::drawThingQuickAngleLines() const // ----------------------------------------------------------------------------- // Draws text showing the length from [p1] to [p2] // ----------------------------------------------------------------------------- -void Renderer::drawLineLength(Vec2d p1, Vec2d p2, ColRGBA col) const +void Renderer::drawLineLength(const Vec2d& p1, const Vec2d& p2, ColRGBA col) const { // Determine distance in screen scale - double tdist = 20 / view_.scale(true); + double tdist = 20 / view_->scale(true); // Determine line midpoint and front vector Vec2d mid(p1.x + (p2.x - p1.x) * 0.5, p1.y + (p2.y - p1.y) * 0.5); @@ -712,7 +738,7 @@ void Renderer::drawLineLength(Vec2d p1, Vec2d p2, ColRGBA col) const // Draw text drawing::drawText( - length, view_.screenX(tp.x), view_.screenY(tp.y) - hh, col, drawing::Font::Normal, drawing::Align::Center); + length, view_->screenX(tp.x), view_->screenY(tp.y) - hh, col, drawing::Font::Normal, drawing::Align::Center); glDisable(GL_TEXTURE_2D); } @@ -726,32 +752,32 @@ void Renderer::drawLineDrawLines(bool snap_nearest_vertex) const gl::setColour(col); // Determine end point - auto end = view_.canvasPos(context_.input().mousePos(), true); + auto end = view_->canvasPos(context_->input().mousePos(), true); if (snap_nearest_vertex) { // If shift is held down, snap to the nearest vertex (if any) - auto vertex = context_.map().vertices().nearest(end); + auto vertex = context_->map().vertices().nearest(end); if (vertex) { end.x = vertex->xPos(); end.y = vertex->yPos(); } - else if (context_.gridSnap()) + else if (context_->gridSnap()) { // No nearest vertex, snap to grid if needed - end.x = context_.snapToGrid(end.x); - end.y = context_.snapToGrid(end.y); + end.x = context_->snapToGrid(end.x); + end.y = context_->snapToGrid(end.y); } } - else if (context_.gridSnap()) + else if (context_->gridSnap()) { // Otherwise, snap to grid if needed - end.x = context_.snapToGrid(end.x); - end.y = context_.snapToGrid(end.y); + end.x = context_->snapToGrid(end.x); + end.y = context_->snapToGrid(end.y); } // Draw lines - auto& line_draw = context_.lineDraw(); + auto& line_draw = context_->lineDraw(); int npoints = line_draw.nPoints(); glLineWidth(2.0f); if (npoints > 1) @@ -759,19 +785,19 @@ void Renderer::drawLineDrawLines(bool snap_nearest_vertex) const for (int a = 0; a < npoints - 1; a++) drawing::drawLineTabbed(line_draw.point(a), line_draw.point(a + 1)); } - if (npoints > 0 && context_.lineDraw().state() == LineDraw::State::Line) + if (npoints > 0 && context_->lineDraw().state() == LineDraw::State::Line) drawing::drawLineTabbed(line_draw.point(npoints - 1), end); // Draw line lengths - view_.setOverlayCoords(true); + view_->setOverlayCoords(true); if (npoints > 1) { for (int a = 0; a < npoints - 1; a++) drawLineLength(line_draw.point(a), line_draw.point(a + 1), col); } - if (npoints > 0 && context_.lineDraw().state() == LineDraw::State::Line) + if (npoints > 0 && context_->lineDraw().state() == LineDraw::State::Line) drawLineLength(line_draw.point(npoints - 1), end, col); - view_.setOverlayCoords(false); + view_->setOverlayCoords(false); // Draw points glPointSize(vertex_size); @@ -780,8 +806,8 @@ void Renderer::drawLineDrawLines(bool snap_nearest_vertex) const glBegin(GL_POINTS); for (auto& point : line_draw.points()) glVertex2d(point.x, point.y); - if (context_.lineDraw().state() == LineDraw::State::Line - || context_.lineDraw().state() == LineDraw::State::ShapeOrigin) + if (context_->lineDraw().state() == LineDraw::State::Line + || context_->lineDraw().state() == LineDraw::State::ShapeOrigin) glVertex2d(end.x, end.y); glEnd(); } @@ -814,7 +840,7 @@ void Renderer::drawPasteLines() const gl::setColour(col); // Draw - auto pos = context_.relativeSnapToGrid(c->midpoint(), view_.canvasPos(context_.input().mousePos(), true)); + auto pos = context_->relativeSnapToGrid(c->midpoint(), view_->canvasPos(context_->input().mousePos(), true)); glLineWidth(2.0f); glBegin(GL_LINES); for (const auto& line : lines) @@ -828,25 +854,25 @@ void Renderer::drawPasteLines() const // ----------------------------------------------------------------------------- // Draws object edit objects, bounding box and text // ----------------------------------------------------------------------------- -void Renderer::drawObjectEdit() +void Renderer::drawObjectEdit() const { - auto& group = context_.objectEdit().group(); + auto& group = context_->objectEdit().group(); auto col = colourconfig::colour("map_object_edit"); - auto edit_state = context_.objectEdit().state(); + auto edit_state = context_->objectEdit().state(); // Map objects - renderer_2d_.renderObjectEditGroup(&group); + renderer_2d_->renderObjectEditGroup(&group); // Bounding box gl::setColour(ColRGBA::WHITE, gl::Blend::Normal); glColor4f(col.fr(), col.fg(), col.fb(), 1.0f); auto bbox = group.bbox(); - bbox.min.x -= 4 / view_.scale(true); - bbox.min.y -= 4 / view_.scale(true); - bbox.max.x += 4 / view_.scale(true); - bbox.max.y += 4 / view_.scale(true); + bbox.min.x -= 4 / view_->scale(true); + bbox.min.y -= 4 / view_->scale(true); + bbox.max.x += 4 / view_->scale(true); + bbox.max.y += 4 / view_->scale(true); - if (context_.objectEdit().rotating()) + if (context_->objectEdit().rotating()) { // Rotate @@ -863,7 +889,7 @@ void Renderer::drawObjectEdit() drawing::drawLine(tr, tl); // Top Left - double rad = 4 / view_.scale(true); + double rad = 4 / view_->scale(true); glLineWidth(1.0f); if (edit_state == ObjectEdit::State::TopLeft) drawing::drawFilledRect(tl.x - rad, tl.y - rad, tl.x + rad, tl.y + rad); @@ -927,17 +953,17 @@ void Renderer::drawObjectEdit() // Line length Vec2d nl_v1, nl_v2; - if (group.nearestLineEndpoints(view_.canvasPos(context_.input().mousePos()), 128 / view_.scale(), nl_v1, nl_v2)) + if (group.nearestLineEndpoints(view_->canvasPos(context_->input().mousePos()), 128 / view_->scale(), nl_v1, nl_v2)) { Vec2d mid(nl_v1.x + ((nl_v2.x - nl_v1.x) * 0.5), nl_v1.y + ((nl_v2.y - nl_v1.y) * 0.5)); int length = math::distance(nl_v1, nl_v2); - int x = view_.canvasX(mid.x); - int y = view_.canvasY(mid.y) - 8; - view_.setOverlayCoords(true); + int x = view_->canvasX(mid.x); + int y = view_->canvasY(mid.y) - 8; + view_->setOverlayCoords(true); drawing::setTextOutline(1.0f, ColRGBA::BLACK); drawing::drawText(fmt::format("{}", length), x, y, ColRGBA::WHITE, drawing::Font::Bold, drawing::Align::Center); drawing::setTextOutline(0); - view_.setOverlayCoords(false); + view_->setOverlayCoords(false); glDisable(GL_TEXTURE_2D); } } @@ -947,7 +973,7 @@ void Renderer::drawObjectEdit() // ----------------------------------------------------------------------------- void Renderer::drawAnimations() const { - auto mode = context_.editMode(); + auto mode = context_->editMode(); for (auto& animation : animations_) { if ((mode == Mode::Visual && animation->mode3d()) || (mode != Mode::Visual && !animation->mode3d())) @@ -958,14 +984,14 @@ void Renderer::drawAnimations() const // ----------------------------------------------------------------------------- // Draws the 2d map // ----------------------------------------------------------------------------- -void Renderer::drawMap2d() +void Renderer::drawMap2d() const { // Apply the current 2d view - view_.apply(); + view_->apply(); // Update visibility info if needed - if (!renderer_2d_.visOK()) - renderer_2d_.updateVisibility(view_.visibleRegion().tl, view_.visibleRegion().br); + if (!renderer_2d_->visOK()) + renderer_2d_->updateVisibility(view_->visibleRegion().tl, view_->visibleRegion().br); // Draw flats if needed gl::setColour(ColRGBA::WHITE, gl::Blend::Normal); @@ -977,79 +1003,79 @@ void Renderer::drawMap2d() // Adjust flat type depending on sector mode int drawtype = 0; - if (context_.editMode() == Mode::Sectors) + if (context_->editMode() == Mode::Sectors) { - if (context_.sectorEditMode() == SectorMode::Floor) + if (context_->sectorEditMode() == SectorMode::Floor) drawtype = 1; - else if (context_.sectorEditMode() == SectorMode::Ceiling) + else if (context_->sectorEditMode() == SectorMode::Ceiling) drawtype = 2; } - renderer_2d_.renderFlats(drawtype, texture, fade_flats_); + renderer_2d_->renderFlats(drawtype, texture, fade_flats_); } // Draw grid drawGrid(); // --- Draw map (depending on mode) --- - auto mouse_state = context_.input().mouseState(); + auto mouse_state = context_->input().mouseState(); gl::resetBlend(); - if (context_.editMode() == Mode::Vertices) + if (context_->editMode() == Mode::Vertices) { // Vertices mode - renderer_2d_.renderThings(fade_things_); // Things - renderer_2d_.renderLines(line_tabs_always, fade_lines_); // Lines + renderer_2d_->renderThings(fade_things_); // Things + renderer_2d_->renderLines(line_tabs_always, fade_lines_); // Lines // Vertices if (mouse_state == Input::MouseState::Move) - renderer_2d_.renderVertices(0.25f); + renderer_2d_->renderVertices(0.25f); else - renderer_2d_.renderVertices(fade_vertices_); + renderer_2d_->renderVertices(fade_vertices_); // Selection if needed - if (mouse_state != Input::MouseState::Move && !context_.overlayActive() + if (mouse_state != Input::MouseState::Move && !context_->overlayActive() && mouse_state != Input::MouseState::ObjectEdit) - renderer_2d_.renderVertexSelection(context_.selection(), anim_flash_level_); + renderer_2d_->renderVertexSelection(context_->selection(), anim_flash_level_); // Hilight if needed - if (mouse_state == Input::MouseState::Normal && !context_.overlayActive()) - renderer_2d_.renderVertexHilight(context_.hilightItem().index, anim_flash_level_); + if (mouse_state == Input::MouseState::Normal && !context_->overlayActive()) + renderer_2d_->renderVertexHilight(context_->hilightItem().index, anim_flash_level_); } - else if (context_.editMode() == Mode::Lines) + else if (context_->editMode() == Mode::Lines) { // Lines mode - renderer_2d_.renderThings(fade_things_); // Things - renderer_2d_.renderVertices(fade_vertices_); // Vertices - renderer_2d_.renderLines(true); // Lines + renderer_2d_->renderThings(fade_things_); // Things + renderer_2d_->renderVertices(fade_vertices_); // Vertices + renderer_2d_->renderLines(true); // Lines // Selection if needed - if (mouse_state != Input::MouseState::Move && !context_.overlayActive() + if (mouse_state != Input::MouseState::Move && !context_->overlayActive() && mouse_state != Input::MouseState::ObjectEdit) - renderer_2d_.renderLineSelection(context_.selection(), anim_flash_level_); + renderer_2d_->renderLineSelection(context_->selection(), anim_flash_level_); // Hilight if needed - if (mouse_state == Input::MouseState::Normal && !context_.overlayActive()) - renderer_2d_.renderLineHilight(context_.hilightItem().index, anim_flash_level_); + if (mouse_state == Input::MouseState::Normal && !context_->overlayActive()) + renderer_2d_->renderLineHilight(context_->hilightItem().index, anim_flash_level_); } - else if (context_.editMode() == Mode::Sectors) + else if (context_->editMode() == Mode::Sectors) { // Sectors mode - renderer_2d_.renderThings(fade_things_); // Things - renderer_2d_.renderVertices(fade_vertices_); // Vertices - renderer_2d_.renderLines(line_tabs_always, fade_lines_); // Lines + renderer_2d_->renderThings(fade_things_); // Things + renderer_2d_->renderVertices(fade_vertices_); // Vertices + renderer_2d_->renderLines(line_tabs_always, fade_lines_); // Lines // Selection if needed - if (mouse_state != Input::MouseState::Move && !context_.overlayActive() + if (mouse_state != Input::MouseState::Move && !context_->overlayActive() && mouse_state != Input::MouseState::ObjectEdit) - renderer_2d_.renderFlatSelection(context_.selection(), anim_flash_level_); + renderer_2d_->renderFlatSelection(context_->selection(), anim_flash_level_); // splitter.testRender(); // Testing // Hilight if needed - if (mouse_state == Input::MouseState::Normal && !context_.overlayActive()) - renderer_2d_.renderFlatHilight(context_.hilightItem().index, anim_flash_level_); + if (mouse_state == Input::MouseState::Normal && !context_->overlayActive()) + renderer_2d_->renderFlatHilight(context_->hilightItem().index, anim_flash_level_); } - else if (context_.editMode() == Mode::Things) + else if (context_->editMode() == Mode::Things) { // Check if we should force thing angles visible bool force_dir = false; @@ -1057,44 +1083,44 @@ void Renderer::drawMap2d() force_dir = true; // Things mode - auto hl_index = context_.hilightItem().index; - renderer_2d_.renderVertices(fade_vertices_); // Vertices - renderer_2d_.renderLines(line_tabs_always, fade_lines_); // Lines - renderer_2d_.renderPointLightPreviews(fade_things_, hl_index); // Point light previews - renderer_2d_.renderThings(fade_things_, force_dir); // Things + auto hl_index = context_->hilightItem().index; + renderer_2d_->renderVertices(fade_vertices_); // Vertices + renderer_2d_->renderLines(line_tabs_always, fade_lines_); // Lines + renderer_2d_->renderPointLightPreviews(fade_things_, hl_index); // Point light previews + renderer_2d_->renderThings(fade_things_, force_dir); // Things // Thing paths - renderer_2d_.renderPathedThings(context_.pathedThings()); + renderer_2d_->renderPathedThings(context_->pathedThings()); // Selection if needed - if (mouse_state != Input::MouseState::Move && !context_.overlayActive() + if (mouse_state != Input::MouseState::Move && !context_->overlayActive() && mouse_state != Input::MouseState::ObjectEdit) - renderer_2d_.renderThingSelection(context_.selection(), anim_flash_level_); + renderer_2d_->renderThingSelection(context_->selection(), anim_flash_level_); // Hilight if needed - if (mouse_state == Input::MouseState::Normal && !context_.overlayActive()) - renderer_2d_.renderThingHilight(hl_index, anim_flash_level_); + if (mouse_state == Input::MouseState::Normal && !context_->overlayActive()) + renderer_2d_->renderThingHilight(hl_index, anim_flash_level_); } // Draw tagged sectors/lines/things if needed - if (!context_.overlayActive() + if (!context_->overlayActive() && (mouse_state == Input::MouseState::Normal || mouse_state == Input::MouseState::TagSectors || mouse_state == Input::MouseState::TagThings)) { - if (!context_.taggedSectors().empty()) - renderer_2d_.renderTaggedFlats(context_.taggedSectors(), anim_flash_level_); - if (!context_.taggedLines().empty()) - renderer_2d_.renderTaggedLines(context_.taggedLines(), anim_flash_level_); - if (!context_.taggedThings().empty()) - renderer_2d_.renderTaggedThings(context_.taggedThings(), anim_flash_level_); - if (!context_.taggingLines().empty()) - renderer_2d_.renderTaggingLines(context_.taggingLines(), anim_flash_level_); - if (!context_.taggingThings().empty()) - renderer_2d_.renderTaggingThings(context_.taggingThings(), anim_flash_level_); + if (!context_->taggedSectors().empty()) + renderer_2d_->renderTaggedFlats(context_->taggedSectors(), anim_flash_level_); + if (!context_->taggedLines().empty()) + renderer_2d_->renderTaggedLines(context_->taggedLines(), anim_flash_level_); + if (!context_->taggedThings().empty()) + renderer_2d_->renderTaggedThings(context_->taggedThings(), anim_flash_level_); + if (!context_->taggingLines().empty()) + renderer_2d_->renderTaggingLines(context_->taggingLines(), anim_flash_level_); + if (!context_->taggingThings().empty()) + renderer_2d_->renderTaggingThings(context_->taggingThings(), anim_flash_level_); } // Draw selection numbers if needed - if (!context_.selection().empty() && mouse_state == Input::MouseState::Normal && map_show_selection_numbers) + if (!context_->selection().empty() && mouse_state == Input::MouseState::Normal && map_show_selection_numbers) drawSelectionNumbers(); // Draw thing quick angle lines if needed @@ -1103,7 +1129,7 @@ void Renderer::drawMap2d() // Draw line drawing lines if needed if (mouse_state == Input::MouseState::LineDraw) - drawLineDrawLines(context_.input().shiftDown()); + drawLineDrawLines(context_->input().shiftDown()); // Draw object edit objects if needed if (mouse_state == Input::MouseState::ObjectEdit) @@ -1114,10 +1140,10 @@ void Renderer::drawMap2d() // Draw selection box if active - auto mx = view_.canvasX(context_.input().mousePos().x, true); - auto my = view_.canvasY(context_.input().mousePos().y, true); - auto mdx = view_.canvasX(context_.input().mouseDownPos().x, true); - auto mdy = view_.canvasY(context_.input().mouseDownPos().y, true); + auto mx = view_->canvasX(context_->input().mousePos().x, true); + auto my = view_->canvasY(context_->input().mousePos().y, true); + auto mdx = view_->canvasX(context_->input().mouseDownPos().x, true); + auto mdy = view_->canvasY(context_->input().mouseDownPos().y, true); if (mouse_state == Input::MouseState::Selection) { // Outline @@ -1146,7 +1172,7 @@ void Renderer::drawMap2d() // Draw paste objects if needed if (mouse_state == Input::MouseState::Paste) { - if (context_.editMode() == Mode::Things) + if (context_->editMode() == Mode::Things) { // Get clipboard item for (unsigned a = 0; a < app::clipboard().size(); a++) @@ -1157,8 +1183,8 @@ void Renderer::drawMap2d() vector things; auto p = dynamic_cast(item); p->putThings(things); - auto pos(context_.relativeSnapToGrid(p->midpoint(), { mx, my })); - renderer_2d_.renderPasteThings(things, pos); + auto pos(context_->relativeSnapToGrid(p->midpoint(), { mx, my })); + renderer_2d_->renderPasteThings(things, pos); } } } @@ -1169,15 +1195,15 @@ void Renderer::drawMap2d() // Draw moving stuff if needed if (mouse_state == Input::MouseState::Move) { - auto& items = context_.moveObjects().items(); - auto offset = context_.moveObjects().offset(); - switch (context_.editMode()) + auto& items = context_->moveObjects().items(); + auto offset = context_->moveObjects().offset(); + switch (context_->editMode()) { - case Mode::Vertices: renderer_2d_.renderMovingVertices(items, offset); break; - case Mode::Lines: renderer_2d_.renderMovingLines(items, offset); break; - case Mode::Sectors: renderer_2d_.renderMovingSectors(items, offset); break; - case Mode::Things: renderer_2d_.renderMovingThings(items, offset); break; - default: break; + case Mode::Vertices: renderer_2d_->renderMovingVertices(items, offset); break; + case Mode::Lines: renderer_2d_->renderMovingLines(items, offset); break; + case Mode::Sectors: renderer_2d_->renderMovingSectors(items, offset); break; + case Mode::Things: renderer_2d_->renderMovingThings(items, offset); break; + default: break; } } } @@ -1185,23 +1211,23 @@ void Renderer::drawMap2d() // ----------------------------------------------------------------------------- // Draws the 3d map // ----------------------------------------------------------------------------- -void Renderer::drawMap3d() +void Renderer::drawMap3d() const { // Setup 3d renderer view - renderer_3d_.setupView(view_.size().x, view_.size().y); + renderer_3d_->setupView(view_->size().x, view_->size().y); // Render 3d map - renderer_3d_.renderMap(); + renderer_3d_->renderMap(); // Draw selection if any - auto selection = context_.selection(); - renderer_3d_.renderFlatSelection(selection); - renderer_3d_.renderWallSelection(selection); - renderer_3d_.renderThingSelection(selection); + auto selection = context_->selection(); + renderer_3d_->renderFlatSelection(selection); + renderer_3d_->renderWallSelection(selection); + renderer_3d_->renderThingSelection(selection); // Draw hilight if any - if (context_.selection().hasHilight()) - renderer_3d_.renderHilight(context_.selection().hilight(), anim_flash_level_); + if (context_->selection().hasHilight()) + renderer_3d_->renderHilight(context_->selection().hilight(), anim_flash_level_); // Draw animations drawAnimations(); @@ -1210,10 +1236,10 @@ void Renderer::drawMap3d() // ----------------------------------------------------------------------------- // Draws the current map editor state // ----------------------------------------------------------------------------- -void Renderer::draw() +void Renderer::draw() const { // Setup the viewport - glViewport(0, 0, view_.size().x, view_.size().y); + glViewport(0, 0, view_->size().x, view_->size().y); // Setup GL state auto col_bg = colourconfig::colour("map_background"); @@ -1225,7 +1251,7 @@ void Renderer::draw() glDisable(GL_TEXTURE_2D); // Draw 2d or 3d map depending on mode - if (context_.editMode() == Mode::Visual) + if (context_->editMode() == Mode::Visual) drawMap3d(); else drawMap2d(); @@ -1235,7 +1261,7 @@ void Renderer::draw() glDisable(GL_DEPTH_TEST); glMatrixMode(GL_PROJECTION); glLoadIdentity(); - glOrtho(0, view_.size().x, view_.size().y, 0, -1, 1); + glOrtho(0, view_->size().x, view_->size().y, 0, -1, 1); glMatrixMode(GL_MODELVIEW); glLoadIdentity(); @@ -1246,14 +1272,14 @@ void Renderer::draw() // Draw current info overlay glDisable(GL_TEXTURE_2D); - context_.drawInfoOverlay(view_.size(), anim_info_fade_); + context_->drawInfoOverlay(view_->size(), anim_info_fade_); // Draw current fullscreen overlay - if (context_.currentOverlay() && anim_overlay_fade_ > 0.01f) - context_.currentOverlay()->draw(view_.size().x, view_.size().y, anim_overlay_fade_); + if (context_->currentOverlay() && anim_overlay_fade_ > 0.01f) + context_->currentOverlay()->draw(view_->size().x, view_->size().y, anim_overlay_fade_); // Draw crosshair if 3d mode - if (context_.editMode() == Mode::Visual) + if (context_->editMode() == Mode::Visual) { // Get crosshair colour auto& def = colourconfig::colDef("map_3d_crosshair"); @@ -1264,8 +1290,8 @@ void Renderer::draw() glEnable(GL_LINE_SMOOTH); glLineWidth(1.5f); - double midx = view_.size().x * 0.5; - double midy = view_.size().y * 0.5; + double midx = view_->size().x * 0.5; + double midy = view_->size().y * 0.5; int size = camera_3d_crosshair_size; glBegin(GL_LINES); @@ -1295,12 +1321,12 @@ void Renderer::draw() glEnd(); // Draw item distance (if any) - if (context_.renderer().renderer3D().itemDistance() >= 0 && camera_3d_show_distance) + if (context_->renderer().renderer3D().itemDistance() >= 0 && camera_3d_show_distance) { glEnable(GL_TEXTURE_2D); gl::setColour(col); drawing::drawText( - fmt::format("{}", renderer_3d_.itemDistance()), + fmt::format("{}", renderer_3d_->itemDistance()), midx + 5, midy + 5, ColRGBA(255, 255, 255, 200), @@ -1378,7 +1404,7 @@ void Renderer::updateAnimations(double mult) } // 2d mode animation - if (context_.editMode() != Mode::Visual) + if (context_->editMode() != Mode::Visual) { // Update 2d mode crossfade animation if (update2dModeCrossfade(mult)) @@ -1390,7 +1416,7 @@ void Renderer::updateAnimations(double mult) animations_active_ = true; // Update renderer scale - renderer_2d_.setScale(view_.scale(true)); + renderer_2d_->setScale(view_->scale(true)); } // Flashing animation for hilight @@ -1418,7 +1444,7 @@ void Renderer::updateAnimations(double mult) } // Fader for info overlay - if (context_.infoOverlayActive() && !context_.overlayActive()) + if (context_->infoOverlayActive() && !context_->overlayActive()) { if (updateFade(anim_info_fade_, 0.1f * mult, 0.0f, 1.0f)) animations_active_ = true; @@ -1430,7 +1456,7 @@ void Renderer::updateAnimations(double mult) } // Fader for fullscreen overlay - if (context_.overlayActive()) + if (context_->overlayActive()) { if (updateFade(anim_overlay_fade_, 0.1f * mult, 0.0f, 1.0f)) animations_active_ = true; @@ -1442,7 +1468,7 @@ void Renderer::updateAnimations(double mult) } // Fader for help text - if (!context_.featureHelpLines().empty()) + if (!context_->featureHelpLines().empty()) { if (updateFade(anim_help_fade_, 0.07f * mult, 0.0f, 1.0f)) animations_active_ = true; @@ -1495,7 +1521,7 @@ bool Renderer::update2dModeCrossfade(double mult) // Interpolate bool anim_mode_crossfade = false; float mcs_speed = 0.08f; - if (context_.editMode() == Mode::Vertices) + if (context_->editMode() == Mode::Vertices) { if (fade_vertices_ < 1.0f) { @@ -1514,7 +1540,7 @@ bool Renderer::update2dModeCrossfade(double mult) anim_mode_crossfade = true; } } - else if (context_.editMode() == Mode::Lines) + else if (context_->editMode() == Mode::Lines) { if (fade_vertices_ > fa_vertices) { @@ -1533,7 +1559,7 @@ bool Renderer::update2dModeCrossfade(double mult) anim_mode_crossfade = true; } } - else if (context_.editMode() == Mode::Sectors) + else if (context_->editMode() == Mode::Sectors) { if (fade_vertices_ > fa_vertices) { @@ -1552,7 +1578,7 @@ bool Renderer::update2dModeCrossfade(double mult) anim_mode_crossfade = true; } } - else if (context_.editMode() == Mode::Things) + else if (context_->editMode() == Mode::Things) { if (fade_vertices_ > fa_vertices) { @@ -1604,7 +1630,7 @@ void Renderer::animateSelectionChange(const mapeditor::Item& item, bool selected if (mapeditor::baseItemType(item.type) == ItemType::Side) { // Get quad - auto quad = renderer_3d_.getQuad(item); + auto quad = renderer_3d_->getQuad(item); if (quad) { @@ -1622,7 +1648,7 @@ void Renderer::animateSelectionChange(const mapeditor::Item& item, bool selected else if (item.type == ItemType::Ceiling || item.type == ItemType::Floor) { // Get flat - auto flat = renderer_3d_.getFlat(item); + auto flat = renderer_3d_->getFlat(item); // Start animation if (flat) @@ -1634,7 +1660,7 @@ void Renderer::animateSelectionChange(const mapeditor::Item& item, bool selected else if (item.type == ItemType::Thing) { // Get thing - auto t = item.asThing(context_.map()); + auto t = item.asThing(context_->map()); if (!t) return; @@ -1644,16 +1670,16 @@ void Renderer::animateSelectionChange(const mapeditor::Item& item, bool selected // Start animation double radius = tt.radius(); if (tt.shrinkOnZoom()) - radius = renderer_2d_.scaledRadius(radius); + radius = renderer_2d_->scaledRadius(radius); animations_.push_back(std::make_unique( - app::runTimer(), t->xPos(), t->yPos(), radius, renderer_2d_.viewScaleInv(), selected)); + app::runTimer(), t->xPos(), t->yPos(), radius, renderer_2d_->viewScaleInv(), selected)); } // 2d mode line else if (item.type == ItemType::Line) { // Get line - auto line = item.asLine(context_.map()); + auto line = item.asLine(context_->map()); if (!line) return; @@ -1665,14 +1691,14 @@ void Renderer::animateSelectionChange(const mapeditor::Item& item, bool selected else if (item.type == ItemType::Vertex) { // Get vertex - auto vertex = item.asVertex(context_.map()); + auto vertex = item.asVertex(context_->map()); if (!vertex) return; // Determine current vertex size float vs = vertex_size; - if (view_.scale() < 1.0) - vs *= view_.scale(); + if (view_->scale() < 1.0) + vs *= view_->scale(); if (vs < 2.0) vs = 2.0; @@ -1685,7 +1711,7 @@ void Renderer::animateSelectionChange(const mapeditor::Item& item, bool selected else if (item.type == ItemType::Sector) { // Get sector polygon - auto sector = item.asSector(context_.map()); + auto sector = item.asSector(context_->map()); if (!sector) return; @@ -1713,13 +1739,13 @@ void Renderer::animateHilightChange(const mapeditor::Item& old_item, MapObject* { // 2d mode animations_.push_back( - std::make_unique(app::runTimer(), old_object, &renderer_2d_, anim_flash_level_)); + std::make_unique(app::runTimer(), old_object, renderer_2d_.get(), anim_flash_level_)); } else { // 3d mode animations_.push_back(std::make_unique( - app::runTimer(), old_item.index, old_item.type, &renderer_3d_, anim_flash_level_)); + app::runTimer(), old_item.index, old_item.type, renderer_3d_.get(), anim_flash_level_)); } // Reset hilight flash diff --git a/src/MapEditor/Renderer/Renderer.h b/src/MapEditor/Renderer/Renderer.h index 4cddb44d8..b432e152e 100644 --- a/src/MapEditor/Renderer/Renderer.h +++ b/src/MapEditor/Renderer/Renderer.h @@ -1,33 +1,42 @@ #pragma once -#include "MCAnimations.h" -#include "MapRenderer2D.h" -#include "MapRenderer3D.h" -#include "OpenGL/View.h" - namespace slade { -class MapEditContext; +struct ColRGBA; +class MCAnimation; +class ItemSelection; +class MapThing; +class MapObject; +namespace gl +{ + class View; +} +class MapRenderer3D; +class MapRenderer2D; class MCOverlay; namespace mapeditor { + struct Item; + class MapEditContext; + class Renderer { public: Renderer(MapEditContext& context); + ~Renderer(); - MapRenderer2D& renderer2D() { return renderer_2d_; } - MapRenderer3D& renderer3D() { return renderer_3d_; } - gl::View& view() { return view_; } + MapRenderer2D& renderer2D() const { return *renderer_2d_; } + MapRenderer3D& renderer3D() const { return *renderer_3d_; } + gl::View& view() const { return *view_; } - void forceUpdate(); + void forceUpdate() const; // View manipulation - void setView(double map_x, double map_y); - void setViewSize(int width, int height); - void setTopY(double map_y); - void pan(double x, double y, bool scale = false); + void setView(double map_x, double map_y) const; + void setViewSize(int width, int height) const; + void setTopY(double map_y) const; + void pan(double x, double y, bool scale = false) const; void zoom(double amount, bool toward_cursor = false); void viewFitToMap(bool snap = false); void viewFitToObjects(const vector& objects); @@ -35,26 +44,26 @@ namespace mapeditor bool viewIsInterpolated() const; // 3d Mode - void setCameraThing(const MapThing* thing); + void setCameraThing(const MapThing* thing) const; Vec2d cameraPos2D() const; Vec2d cameraDir2D() const; // Drawing - void draw(); + void draw() const; // Animation bool animationsActive() const { return !animations_.empty() || animations_active_; } void updateAnimations(double mult); - void animateSelectionChange(const mapeditor::Item& item, bool selected = true); + void animateSelectionChange(const Item& item, bool selected = true); void animateSelectionChange(const ItemSelection& selection); - void animateHilightChange(const mapeditor::Item& old_item, MapObject* old_object = nullptr); + void animateHilightChange(const Item& old_item, MapObject* old_object = nullptr); void addAnimation(unique_ptr animation); private: - MapEditContext& context_; - MapRenderer2D renderer_2d_; - MapRenderer3D renderer_3d_; - gl::View view_; + MapEditContext* context_; + unique_ptr renderer_2d_; + unique_ptr renderer_3d_; + unique_ptr view_; // MCAnimations vector> animations_; @@ -80,13 +89,13 @@ namespace mapeditor void drawFeatureHelpText() const; void drawSelectionNumbers() const; void drawThingQuickAngleLines() const; - void drawLineLength(Vec2d p1, Vec2d p2, ColRGBA col) const; + void drawLineLength(const Vec2d& p1, const Vec2d& p2, ColRGBA col) const; void drawLineDrawLines(bool snap_nearest_vertex) const; void drawPasteLines() const; - void drawObjectEdit(); + void drawObjectEdit() const; void drawAnimations() const; - void drawMap2d(); - void drawMap3d(); + void drawMap2d() const; + void drawMap3d() const; // Animation bool update2dModeCrossfade(double mult); diff --git a/src/MapEditor/SectorBuilder.cpp b/src/MapEditor/SectorBuilder.cpp index 07a00581c..fa1ef2574 100644 --- a/src/MapEditor/SectorBuilder.cpp +++ b/src/MapEditor/SectorBuilder.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -35,6 +35,9 @@ #include "Main.h" #include "SectorBuilder.h" #include "OpenGL/OpenGL.h" +#include "SLADEMap/MapObject/MapLine.h" +#include "SLADEMap/MapObject/MapSector.h" +#include "SLADEMap/MapObject/MapVertex.h" #include "SLADEMap/SLADEMap.h" #include "Utility/MathStuff.h" @@ -127,7 +130,7 @@ SectorBuilder::Edge nextEdge(SectorBuilder::Edge edge, MapLineSet& visited_lines // ----------------------------------------------------------------------------- // Returns the line for the edge at [index] // ----------------------------------------------------------------------------- -MapLine* SectorBuilder::edgeLine(unsigned index) +MapLine* SectorBuilder::edgeLine(unsigned index) const { // Check index if (index >= sector_edges_.size()) @@ -139,7 +142,7 @@ MapLine* SectorBuilder::edgeLine(unsigned index) // ----------------------------------------------------------------------------- // Returns true if the edge at [index] is on the front side of its line // ----------------------------------------------------------------------------- -bool SectorBuilder::edgeIsFront(unsigned index) +bool SectorBuilder::edgeIsFront(unsigned index) const { // Check index if (index >= sector_edges_.size()) @@ -151,7 +154,7 @@ bool SectorBuilder::edgeIsFront(unsigned index) // ----------------------------------------------------------------------------- // Returns true if the MapSide for the edge at [index] has been created // ----------------------------------------------------------------------------- -bool SectorBuilder::edgeSideCreated(unsigned index) +bool SectorBuilder::edgeSideCreated(unsigned index) const { // Check index if (index >= sector_edges_.size()) @@ -243,7 +246,7 @@ bool SectorBuilder::traceOutline(MapLine* line, bool front) // ----------------------------------------------------------------------------- // Returns the index of the edge closest to [x,y] // ----------------------------------------------------------------------------- -int SectorBuilder::nearestEdge(double x, double y) +int SectorBuilder::nearestEdge(double x, double y) const { Vec2d point(x, y); @@ -273,7 +276,7 @@ int SectorBuilder::nearestEdge(double x, double y) // ----------------------------------------------------------------------------- // Returns true if the point [x,y] is within the current outline // ----------------------------------------------------------------------------- -bool SectorBuilder::pointWithinOutline(double x, double y) +bool SectorBuilder::pointWithinOutline(double x, double y) const { Vec2d point(x, y); @@ -488,7 +491,7 @@ SectorBuilder::Edge SectorBuilder::findInnerEdge() // Finds an appropriate existing sector to copy properties from, for the new // sector being built // ----------------------------------------------------------------------------- -MapSector* SectorBuilder::findCopySector() +MapSector* SectorBuilder::findCopySector() const { // Go through new sector edges MapSector* sector_copy = nullptr; @@ -523,7 +526,7 @@ MapSector* SectorBuilder::findCopySector() // ----------------------------------------------------------------------------- // Finds any existing sector that is already part of the traced new sector // ----------------------------------------------------------------------------- -MapSector* SectorBuilder::findExistingSector(vector& sides_ignore) +MapSector* SectorBuilder::findExistingSector(vector& sides_ignore) const { // Go through new sector edges MapSector* sector = nullptr; @@ -561,7 +564,7 @@ MapSector* SectorBuilder::findExistingSector(vector& sides_ignore) // Checks if the traced sector is valid (ie. all edges are currently the same // (existing) sector) // ----------------------------------------------------------------------------- -bool SectorBuilder::isValidSector() +bool SectorBuilder::isValidSector() const { if (sector_edges_.empty()) return false; @@ -702,7 +705,7 @@ void SectorBuilder::createSector(MapSector* sector, MapSector* sector_copy) // ----------------------------------------------------------------------------- // Draws lines showing the currently traced edges // ----------------------------------------------------------------------------- -void SectorBuilder::drawResult() +void SectorBuilder::drawResult() const { glDisable(GL_TEXTURE_2D); gl::setColour(255, 255, 255, 255, gl::Blend::Normal); diff --git a/src/MapEditor/SectorBuilder.h b/src/MapEditor/SectorBuilder.h index 426a0b2b8..6709c456d 100644 --- a/src/MapEditor/SectorBuilder.h +++ b/src/MapEditor/SectorBuilder.h @@ -26,25 +26,25 @@ class SectorBuilder const string& error() const { return error_; } unsigned nEdges() const { return sector_edges_.size(); } - MapLine* edgeLine(unsigned index); - bool edgeIsFront(unsigned index); - bool edgeSideCreated(unsigned index); + MapLine* edgeLine(unsigned index) const; + bool edgeIsFront(unsigned index) const; + bool edgeSideCreated(unsigned index) const; bool traceOutline(MapLine* line, bool front = true); - int nearestEdge(double x, double y); - bool pointWithinOutline(double x, double y); + int nearestEdge(double x, double y) const; + bool pointWithinOutline(double x, double y) const; void discardOutsideVertices(); Edge findOuterEdge() const; Edge findInnerEdge(); - MapSector* findCopySector(); - MapSector* findExistingSector(vector& sides_ignore); - bool isValidSector(); + MapSector* findCopySector() const; + MapSector* findExistingSector(vector& sides_ignore) const; + bool isValidSector() const; bool traceSector(SLADEMap* map, MapLine* line, bool front = true); void createSector(MapSector* sector = nullptr, MapSector* sector_copy = nullptr); // Testing - void drawResult(); + void drawResult() const; private: vector vertex_valid_; diff --git a/src/MapEditor/UI/Dialogs/ActionSpecialDialog.cpp b/src/MapEditor/UI/Dialogs/ActionSpecialDialog.cpp index e0f9e3738..6c037f9be 100644 --- a/src/MapEditor/UI/Dialogs/ActionSpecialDialog.cpp +++ b/src/MapEditor/UI/Dialogs/ActionSpecialDialog.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: https://slade.mancubus.net @@ -32,10 +32,14 @@ // ----------------------------------------------------------------------------- #include "Main.h" #include "ActionSpecialDialog.h" +#include "Game/ActionSpecial.h" #include "Game/Configuration.h" +#include "Game/UDMFProperty.h" +#include "General/UI.h" #include "MapEditor/MapEditContext.h" #include "MapEditor/MapEditor.h" #include "MapEditor/UI/GenLineSpecialPanel.h" +#include "SLADEMap/MapObject/MapLine.h" #include "SpecialPresetDialog.h" #include "UI/Controls/NumberTextCtrl.h" #include "UI/WxUtils.h" @@ -79,10 +83,13 @@ ActionSpecialTreeView::ActionSpecialTreeView(wxWindow* parent) : wxDataViewTreeC // Bind events Bind(wxEVT_DATAVIEW_ITEM_START_EDITING, [&](wxDataViewEvent& e) { e.Veto(); }); - Bind(wxEVT_DATAVIEW_ITEM_ACTIVATED, [&](wxDataViewEvent&) { - if (parent_dialog_) - parent_dialog_->EndModal(wxID_OK); - }); + Bind( + wxEVT_DATAVIEW_ITEM_ACTIVATED, + [&](wxDataViewEvent&) + { + if (parent_dialog_) + parent_dialog_->EndModal(wxID_OK); + }); // 64 is an arbitrary fudge factor -- should be at least the width of a // scrollbar plus the expand icons plus any extra padding @@ -212,7 +219,7 @@ class ArgsControl : public wxPanel { SetSizer(new wxBoxSizer(wxVERTICAL)); } - ~ArgsControl() = default; + ~ArgsControl() override = default; virtual long getArgValue() = 0; virtual void setArgValue(long val) = 0; @@ -246,7 +253,7 @@ class ArgsTextControl : public ArgsControl wxString val = text_control_->GetValue(); // Empty string means ignore it - if (val == "") + if (val.empty()) return -1; long ret; @@ -542,7 +549,7 @@ class ArgsFlagsControl : public ArgsTextControl // ------------------------------------------------------------------------- // Do the actual work of updating the checkbox states. // ------------------------------------------------------------------------- - void updateCheckState(long val) + void updateCheckState(long val) const { for (unsigned i = 0; i < arg_.custom_flags.size(); i++) { @@ -688,13 +695,12 @@ void ArgsPanel::setup(const game::ArgSpec& args, bool udmf) } // Setup layout - int row = 0; for (unsigned a = 0; a < 5; a++) { auto& arg = args[a]; bool has_desc = false; - if ((int)a < args.count) + if (static_cast(a) < args.count) { has_desc = !arg.desc.empty(); @@ -770,7 +776,7 @@ void ArgsPanel::setup(const game::ArgSpec& args, bool udmf) // ----------------------------------------------------------------------------- // Sets the arg values // ----------------------------------------------------------------------------- -void ArgsPanel::setValues(int args[5]) +void ArgsPanel::setValues(int args[5]) const { for (unsigned a = 0; a < 5; a++) { @@ -781,7 +787,7 @@ void ArgsPanel::setValues(int args[5]) // ----------------------------------------------------------------------------- // Returns the current value for arg [index] // ----------------------------------------------------------------------------- -int ArgsPanel::argValue(int index) +int ArgsPanel::argValue(int index) const { // Check index if (index < 0 || index > 4 || !control_args_[index]) @@ -836,13 +842,13 @@ ActionSpecialPanel::ActionSpecialPanel(wxWindow* parent, bool trigger) : wxPanel { // Action Special radio button auto hbox = new wxBoxSizer(wxHORIZONTAL); - sizer->Add(hbox, 0, wxEXPAND | wxBOTTOM, ui::pad()); + sizer->Add(hbox, wxutil::sfWithBorder(0, wxBOTTOM).Expand()); rb_special_ = new wxRadioButton(this, -1, "Action Special", wxDefaultPosition, wxDefaultSize, wxRB_GROUP); - hbox->Add(rb_special_, 0, wxEXPAND | wxRIGHT, ui::pad()); + hbox->Add(rb_special_, wxutil::sfWithBorder(0, wxRIGHT).Expand()); // Generalised Special radio button rb_generalised_ = new wxRadioButton(this, -1, "Generalised Special"); - hbox->Add(rb_generalised_, 0, wxEXPAND); + hbox->Add(rb_generalised_, wxSizerFlags().Expand()); // Boom generalised line special panel panel_gen_specials_ = new GenLineSpecialPanel(this); @@ -875,13 +881,13 @@ void ActionSpecialPanel::setupSpecialPanel() // Special box text_special_ = new NumberTextCtrl(panel_action_special_); - sizer->Add(text_special_, 0, wxEXPAND | wxBOTTOM, ui::pad()); + sizer->Add(text_special_, wxutil::sfWithBorder(0, wxBOTTOM).Expand()); text_special_->Bind( wxEVT_TEXT, [&](wxCommandEvent& e) { tree_specials_->showSpecial(text_special_->number(), false); }); // Action specials tree tree_specials_ = new ActionSpecialTreeView(panel_action_special_); - sizer->Add(tree_specials_, 1, wxEXPAND); + sizer->Add(tree_specials_, wxSizerFlags(1).Expand()); if (show_trigger_) { @@ -904,20 +910,20 @@ void ActionSpecialPanel::setupSpecialPanel() { auto frame_triggers = new wxStaticBox(panel_action_special_, -1, group); auto sizer_triggers = new wxStaticBoxSizer(frame_triggers, wxVERTICAL); - sizer->Add(sizer_triggers, 0, wxEXPAND | wxTOP, ui::pad()); + sizer->Add(sizer_triggers, wxutil::sfWithBorder(0, wxTOP).Expand()); frame_sizer = new wxFlexGridSizer(3, ui::pad() / 2, ui::pad()); frame_sizer->AddGrowableCol(0, 1); frame_sizer->AddGrowableCol(1, 1); frame_sizer->AddGrowableCol(2, 1); - sizer_triggers->Add(frame_sizer, 1, wxEXPAND | wxALL, ui::pad()); + sizer_triggers->Add(frame_sizer, wxutil::sfWithBorder(1).Expand()); named_flexgrids.find(group)->second = frame_sizer; } auto cb_trigger = new wxCheckBox( panel_action_special_, -1, i.second.name(), wxDefaultPosition, wxDefaultSize, wxCHK_3STATE); - frame_sizer->Add(cb_trigger, 0, wxEXPAND); + frame_sizer->Add(cb_trigger, wxSizerFlags().Expand()); flags_.push_back({ cb_trigger, -1, i.second.propName() }); } @@ -928,26 +934,26 @@ void ActionSpecialPanel::setupSpecialPanel() { auto frame_trigger = new wxStaticBox(panel_action_special_, -1, "Special Trigger"); auto sizer_trigger = new wxStaticBoxSizer(frame_trigger, wxVERTICAL); - sizer->Add(sizer_trigger, 0, wxEXPAND | wxALL, ui::pad()); + sizer->Add(sizer_trigger, wxutil::sfWithBorder().Expand()); // Add triggers dropdown auto spac_triggers = wxutil::arrayStringStd(game::configuration().allSpacTriggers()); choice_trigger_ = new wxChoice(panel_action_special_, -1, wxDefaultPosition, wxDefaultSize, spac_triggers); - sizer_trigger->Add(choice_trigger_, 0, wxEXPAND | wxALL, ui::pad()); + sizer_trigger->Add(choice_trigger_, wxutil::sfWithBorder().Expand()); // Add activation-related flags auto fg_sizer = new wxFlexGridSizer(3, ui::pad() / 2, ui::pad()); fg_sizer->AddGrowableCol(0, 1); fg_sizer->AddGrowableCol(1, 1); fg_sizer->AddGrowableCol(2, 1); - sizer_trigger->Add(fg_sizer, 0, wxEXPAND | wxALL, ui::pad()); + sizer_trigger->Add(fg_sizer, wxutil::sfWithBorder().Expand()); for (unsigned a = 0; a < game::configuration().nLineFlags(); a++) { if (game::configuration().lineFlag(a).activation) { flags_.push_back( { new wxCheckBox(panel_action_special_, -1, game::configuration().lineFlag(a).name), - (int)a, + static_cast(a), game::configuration().lineFlag(a).udmf }); fg_sizer->Add(flags_.back().check_box, 0, wxEXPAND); } @@ -956,7 +962,7 @@ void ActionSpecialPanel::setupSpecialPanel() // Preset button btn_preset_ = new wxButton(panel_action_special_, -1, "Preset..."); - sizer->Add(btn_preset_, 0, wxALIGN_RIGHT | wxTOP, ui::pad()); + sizer->Add(btn_preset_, wxutil::sfWithBorder(0, wxTOP).Right()); btn_preset_->Bind(wxEVT_BUTTON, &ActionSpecialPanel::onSpecialPresetClicked, this); } @@ -998,7 +1004,7 @@ void ActionSpecialPanel::setSpecial(int special) // ----------------------------------------------------------------------------- // Sets the action special trigger (hexen or udmf) // ----------------------------------------------------------------------------- -void ActionSpecialPanel::setTrigger(int index) +void ActionSpecialPanel::setTrigger(int index) const { if (!show_trigger_) return; @@ -1008,14 +1014,14 @@ void ActionSpecialPanel::setTrigger(int index) choice_trigger_->SetSelection(index); // UDMF Trigger - else if (index < (int)flags_.size()) + else if (index < static_cast(flags_.size())) flags_[index].check_box->SetValue(true); } // ----------------------------------------------------------------------------- // Sets the action special trigger from a udmf trigger name (hexen or udmf) // ----------------------------------------------------------------------------- -void ActionSpecialPanel::setTrigger(const wxString& trigger) +void ActionSpecialPanel::setTrigger(const wxString& trigger) const { if (!show_trigger_) return; @@ -1043,7 +1049,7 @@ void ActionSpecialPanel::setTrigger(const wxString& trigger) // ----------------------------------------------------------------------------- // Deselects all triggers (or resets to 'player cross' in hexen format) // ----------------------------------------------------------------------------- -void ActionSpecialPanel::clearTrigger() +void ActionSpecialPanel::clearTrigger() const { // UDMF Triggers and Flags for (auto& flag : flags_) @@ -1101,7 +1107,7 @@ void ActionSpecialPanel::showGeneralised(bool show) // Applies selected special (if [apply_special] is true), trigger(s) and args // (if any) to [lines] // ----------------------------------------------------------------------------- -void ActionSpecialPanel::applyTo(vector& lines, bool apply_special) +void ActionSpecialPanel::applyTo(const vector& lines, bool apply_special) const { // Special int special = selectedSpecial(); @@ -1140,11 +1146,11 @@ void ActionSpecialPanel::applyTo(vector& lines, bool apply_special) // Trigger(s) if (show_trigger_) { - for (auto& line : lines) + for (auto line : lines) { // Hexen if (choice_trigger_) - game::configuration().setLineSpacTrigger(choice_trigger_->GetSelection(), (MapLine*)line); + game::configuration().setLineSpacTrigger(choice_trigger_->GetSelection(), dynamic_cast(line)); // UDMF / Flags for (auto& flag : flags_) @@ -1153,7 +1159,8 @@ void ActionSpecialPanel::applyTo(vector& lines, bool apply_special) continue; if (choice_trigger_) - game::configuration().setLineFlag(flag.index, (MapLine*)line, flag.check_box->GetValue()); + game::configuration().setLineFlag( + flag.index, dynamic_cast(line), flag.check_box->GetValue()); else line->setBoolProperty(flag.udmf.ToStdString(), flag.check_box->GetValue()); } @@ -1164,7 +1171,7 @@ void ActionSpecialPanel::applyTo(vector& lines, bool apply_special) // ----------------------------------------------------------------------------- // Loads special/trigger/arg values from [lines] // ----------------------------------------------------------------------------- -void ActionSpecialPanel::openLines(vector& lines) +void ActionSpecialPanel::openLines(const vector& lines) { if (lines.empty()) return; @@ -1192,10 +1199,10 @@ void ActionSpecialPanel::openLines(vector& lines) // Hexen if (choice_trigger_) { - int trigger = game::configuration().spacTriggerIndexHexen((MapLine*)lines[0]); + int trigger = game::configuration().spacTriggerIndexHexen(dynamic_cast(lines[0])); for (unsigned a = 1; a < lines.size(); a++) { - if (trigger != game::configuration().spacTriggerIndexHexen((MapLine*)lines[a])) + if (trigger != game::configuration().spacTriggerIndexHexen(dynamic_cast(lines[a]))) { trigger = -1; break; @@ -1209,13 +1216,15 @@ void ActionSpecialPanel::openLines(vector& lines) for (auto& flag : flags_) { // Set initial flag checked value - flag.check_box->SetValue(game::configuration().lineFlagSet(flag.index, (MapLine*)lines[0])); + flag.check_box->SetValue( + game::configuration().lineFlagSet(flag.index, dynamic_cast(lines[0]))); // Go through subsequent lines for (unsigned b = 1; b < lines.size(); b++) { // Check for mismatch - if (flag.check_box->GetValue() != game::configuration().lineFlagSet(flag.index, (MapLine*)lines[b])) + if (flag.check_box->GetValue() + != game::configuration().lineFlagSet(flag.index, dynamic_cast(lines[b]))) { // Set undefined flag.check_box->Set3StateValue(wxCHK_UNDETERMINED); @@ -1247,6 +1256,8 @@ void ActionSpecialPanel::openLines(vector& lines) // // ----------------------------------------------------------------------------- +// ReSharper disable CppMemberFunctionMayBeConst +// ReSharper disable CppParameterMayBeConstPtrOrRef // ----------------------------------------------------------------------------- // Called when the radio button selection is changed @@ -1351,14 +1362,14 @@ ActionSpecialDialog::ActionSpecialDialog(wxWindow* parent, bool show_args) : if (mapeditor::editContext().mapDesc().format == MapFormat::Doom || !show_args) { panel_special_ = new ActionSpecialPanel(this, false); - sizer->Add(panel_special_, 1, wxEXPAND | wxLEFT | wxRIGHT | wxTOP, ui::padLarge()); + sizer->Add(panel_special_, wxutil::sfWithLargeBorder(1, wxLEFT | wxRIGHT | wxTOP).Expand()); } // Args (use tabs) else { stc_tabs_ = STabCtrl::createControl(this); - sizer->Add(stc_tabs_, 1, wxEXPAND | wxLEFT | wxRIGHT | wxTOP, ui::padLarge()); + sizer->Add(stc_tabs_, wxutil::sfWithLargeBorder(1, wxLEFT | wxRIGHT | wxTOP).Expand()); // Special panel panel_special_ = new ActionSpecialPanel(stc_tabs_); @@ -1372,7 +1383,7 @@ ActionSpecialDialog::ActionSpecialDialog(wxWindow* parent, bool show_args) : // Add buttons sizer->AddSpacer(ui::pad()); - sizer->Add(CreateButtonSizer(wxOK | wxCANCEL), 0, wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, ui::padLarge()); + sizer->Add(CreateButtonSizer(wxOK | wxCANCEL), wxutil::sfWithLargeBorder(0, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); // Init SetSizerAndFit(sizer); @@ -1423,7 +1434,7 @@ int ActionSpecialDialog::argValue(int index) const // ----------------------------------------------------------------------------- // Applies selected trigger(s) (hexen or udmf) to [lines] // ----------------------------------------------------------------------------- -void ActionSpecialDialog::applyTo(vector& lines, bool apply_special) const +void ActionSpecialDialog::applyTo(const vector& lines, bool apply_special) const { panel_special_->applyTo(lines, apply_special); } diff --git a/src/MapEditor/UI/Dialogs/ActionSpecialDialog.h b/src/MapEditor/UI/Dialogs/ActionSpecialDialog.h index d38f347d1..b965b7cac 100644 --- a/src/MapEditor/UI/Dialogs/ActionSpecialDialog.h +++ b/src/MapEditor/UI/Dialogs/ActionSpecialDialog.h @@ -22,7 +22,7 @@ class ActionSpecialTreeView : public wxDataViewTreeCtrl { public: ActionSpecialTreeView(wxWindow* parent); - ~ActionSpecialTreeView() = default; + ~ActionSpecialTreeView() override = default; void setParentDialog(wxDialog* dlg) { parent_dialog_ = dlg; } @@ -50,11 +50,11 @@ class ArgsPanel : public wxScrolled { public: ArgsPanel(wxWindow* parent); - ~ArgsPanel() = default; + ~ArgsPanel() override = default; void setup(const game::ArgSpec& args, bool udmf); - void setValues(int args[5]); - int argValue(int index); + void setValues(int args[5]) const; + int argValue(int index) const; void onSize(wxSizeEvent& event); private: @@ -68,18 +68,18 @@ class ActionSpecialPanel : public wxPanel { public: ActionSpecialPanel(wxWindow* parent, bool trigger = true); - ~ActionSpecialPanel() = default; + ~ActionSpecialPanel() override = default; void setupSpecialPanel(); void setArgsPanel(ArgsPanel* panel) { panel_args_ = panel; } void setSpecial(int special); - void setTrigger(int index); - void setTrigger(const wxString& trigger); - void clearTrigger(); + void setTrigger(int index) const; + void setTrigger(const wxString& trigger) const; + void clearTrigger() const; int selectedSpecial() const; void showGeneralised(bool show = true); - void applyTo(vector& lines, bool apply_special); - void openLines(vector& lines); + void applyTo(const vector& lines, bool apply_special) const; + void openLines(const vector& lines); void onRadioButtonChanged(wxCommandEvent& e); void onSpecialSelectionChanged(wxDataViewEvent& e); @@ -111,13 +111,13 @@ class ActionSpecialDialog : public SDialog { public: ActionSpecialDialog(wxWindow* parent, bool show_args = false); - ~ActionSpecialDialog() = default; + ~ActionSpecialDialog() override = default; void setSpecial(int special) const; void setArgs(int args[5]) const; int selectedSpecial() const; int argValue(int index) const; - void applyTo(vector& lines, bool apply_special) const; + void applyTo(const vector& lines, bool apply_special) const; void openLines(vector& lines) const; private: diff --git a/src/MapEditor/UI/Dialogs/MapTextureBrowser.cpp b/src/MapEditor/UI/Dialogs/MapTextureBrowser.cpp index 2ddfe9119..c28c2fa7f 100644 --- a/src/MapEditor/UI/Dialogs/MapTextureBrowser.cpp +++ b/src/MapEditor/UI/Dialogs/MapTextureBrowser.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -32,12 +32,14 @@ // ----------------------------------------------------------------------------- #include "Main.h" #include "MapTextureBrowser.h" +#include "Archive/Archive.h" #include "Game/Configuration.h" -#include "General/ResourceManager.h" #include "MapEditor/MapEditor.h" #include "MapEditor/MapTextureManager.h" +#include "OpenGL/GLTexture.h" +#include "SLADEMap/MapObjectList/SectorList.h" +#include "SLADEMap/MapObjectList/SideList.h" #include "SLADEMap/SLADEMap.h" -#include "Utility/StringUtils.h" using namespace slade; using namespace mapeditor; @@ -272,7 +274,7 @@ MapTextureBrowser::MapTextureBrowser(wxWindow* parent, TextureType type, const w // Builds and returns the tree item path for [info] // ----------------------------------------------------------------------------- wxString MapTextureBrowser::determineTexturePath( - Archive* archive, + const Archive* archive, MapTextureManager::Category category, const wxString& type, const wxString& path) const @@ -289,11 +291,11 @@ wxString MapTextureBrowser::determineTexturePath( { switch (category) { - case MapTextureManager::Category::TextureX: ret += "TEXTUREx"; break; + case MapTextureManager::Category::TextureX: ret += "TEXTUREx"; break; case MapTextureManager::Category::ZDTextures: ret += "TEXTURES"; break; - case MapTextureManager::Category::HiRes: ret += "HIRESTEX"; break; - case MapTextureManager::Category::Tx: ret += "Single (TX)"; break; - default: continue; + case MapTextureManager::Category::HiRes: ret += "HIRESTEX"; break; + case MapTextureManager::Category::Tx: ret += "Single (TX)"; break; + default: continue; } } diff --git a/src/MapEditor/UI/Dialogs/MapTextureBrowser.h b/src/MapEditor/UI/Dialogs/MapTextureBrowser.h index 3c6c38aa5..ed8c89cad 100644 --- a/src/MapEditor/UI/Dialogs/MapTextureBrowser.h +++ b/src/MapEditor/UI/Dialogs/MapTextureBrowser.h @@ -2,6 +2,7 @@ #include "MapEditor/MapEditor.h" #include "MapEditor/MapTextureManager.h" +#include "UI/Browser/BrowserItem.h" #include "UI/Browser/BrowserWindow.h" namespace slade @@ -16,7 +17,7 @@ class MapTexBrowserItem : public BrowserItem static const wxString FLAT; MapTexBrowserItem(const wxString& name, const wxString& type, unsigned index = 0); - ~MapTexBrowserItem() = default; + ~MapTexBrowserItem() override = default; bool loadImage() override; wxString itemInfo() override; @@ -36,10 +37,10 @@ class MapTextureBrowser : public BrowserWindow mapeditor::TextureType type = mapeditor::TextureType::Texture, const wxString& texture = "", SLADEMap* map = nullptr); - ~MapTextureBrowser() = default; + ~MapTextureBrowser() override = default; wxString determineTexturePath( - Archive* archive, + const Archive* archive, MapTextureManager::Category category, const wxString& type, const wxString& path) const; diff --git a/src/MapEditor/UI/Dialogs/SectorSpecialDialog.cpp b/src/MapEditor/UI/Dialogs/SectorSpecialDialog.cpp index d0589f898..1042731b1 100644 --- a/src/MapEditor/UI/Dialogs/SectorSpecialDialog.cpp +++ b/src/MapEditor/UI/Dialogs/SectorSpecialDialog.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: https://slade.mancubus.net @@ -33,6 +33,8 @@ #include "Main.h" #include "SectorSpecialDialog.h" #include "Game/Configuration.h" +#include "General/UI.h" +#include "UI/Lists/ListView.h" #include "UI/WxUtils.h" using namespace slade; @@ -65,6 +67,8 @@ wxString alt_damage_types[] = { "Instantly Kill Player w/o Radsuit or Invuln", // ----------------------------------------------------------------------------- SectorSpecialPanel::SectorSpecialPanel(wxWindow* parent) : wxPanel(parent, -1) { + namespace wx = wxutil; + // Setup sizer auto sizer = new wxBoxSizer(wxVERTICAL); SetSizer(sizer); @@ -73,8 +77,8 @@ SectorSpecialPanel::SectorSpecialPanel(wxWindow* parent) : wxPanel(parent, -1) auto frame = new wxStaticBox(this, -1, "Special"); auto framesizer = new wxStaticBoxSizer(frame, wxVERTICAL); lv_specials_ = new ListView(this, -1); - framesizer->Add(lv_specials_, 1, wxEXPAND | wxALL, ui::pad()); - sizer->Add(framesizer, 1, wxEXPAND); + framesizer->Add(lv_specials_, wx::sfWithBorder(1).Expand()); + sizer->Add(framesizer, wxSizerFlags(1).Expand()); lv_specials_->enableSizeUpdate(false); lv_specials_->AppendColumn("#"); @@ -96,31 +100,31 @@ SectorSpecialPanel::SectorSpecialPanel(wxWindow* parent) : wxPanel(parent, -1) { frame = new wxStaticBox(this, -1, "Flags"); framesizer = new wxStaticBoxSizer(frame, wxVERTICAL); - sizer->Add(framesizer, 0, wxEXPAND | wxTOP, ui::pad()); + sizer->Add(framesizer, wx::sfWithBorder(0, wxTOP).Expand()); // Damage choice_damage_ = new wxChoice(this, -1, wxDefaultPosition, wxDefaultSize, 4, damage_types); choice_damage_->Select(0); - framesizer->Add(wxutil::createLabelHBox(this, "Damage:", choice_damage_), 0, wxEXPAND | wxALL, ui::pad()); + framesizer->Add(wx::createLabelHBox(this, "Damage:", choice_damage_), wx::sfWithBorder().Expand()); // Secret | Friction | Pusher/Puller cb_secret_ = new wxCheckBox(this, -1, "Secret"); cb_friction_ = new wxCheckBox(this, -1, "Friction Enabled"); cb_pushpull_ = new wxCheckBox(this, -1, "Pushers/Pullers Enabled"); - wxutil::layoutHorizontally( + wx::layoutHorizontally( framesizer, { cb_secret_, cb_friction_, cb_pushpull_ }, - wxSizerFlags(0).Expand().Border(wxLEFT | wxRIGHT | wxBOTTOM, ui::pad())); + wx::sfWithBorder(0, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); // MBF21 Flags: Alternative Damage Mode | Kill Grounded Monsters cb_alt_damage_ = new wxCheckBox(this, -1, "Alternate Damage Mode"); cb_kill_grounded_ = new wxCheckBox(this, -1, "Kill Grounded Monsters"); if (game::configuration().featureSupported(game::Feature::MBF21)) { - wxutil::layoutHorizontally( + wx::layoutHorizontally( framesizer, { cb_alt_damage_, cb_kill_grounded_ }, - wxSizerFlags(0).Expand().Border(wxLEFT | wxRIGHT | wxBOTTOM, ui::pad())); + wx::sfWithBorder(0, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); cb_alt_damage_->Bind(wxEVT_CHECKBOX, [&](wxCommandEvent&) { updateDamageDropdown(); }); } @@ -133,7 +137,7 @@ SectorSpecialPanel::SectorSpecialPanel(wxWindow* parent) : wxPanel(parent, -1) width = -1; } - wxWindowBase::SetMinSize(wxutil::scaledSize(width, 300)); + wxWindowBase::SetMinSize(wx::scaledSize(width, 300)); } // ----------------------------------------------------------------------------- @@ -199,7 +203,7 @@ int SectorSpecialPanel::selectedSpecial() const // Get selected base type int base = 0; - if (selection < (int)types.size()) + if (selection < static_cast(types.size())) { int index = 0; for (auto& i : types) @@ -258,11 +262,11 @@ SectorSpecialDialog::SectorSpecialDialog(wxWindow* parent) : SDialog(parent, "Se // Special panel panel_special_ = new SectorSpecialPanel(this); - sizer->Add(panel_special_, 1, wxEXPAND | wxLEFT | wxRIGHT | wxTOP, ui::padLarge()); + sizer->Add(panel_special_, wxutil::sfWithLargeBorder(1, wxLEFT | wxRIGHT | wxTOP).Expand()); // Dialog buttons sizer->AddSpacer(ui::pad()); - sizer->Add(CreateButtonSizer(wxOK | wxCANCEL), 0, wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, ui::padLarge()); + sizer->Add(CreateButtonSizer(wxOK | wxCANCEL), wxutil::sfWithLargeBorder(0, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); // Bind Events panel_special_->getSpecialsList()->Bind(wxEVT_LIST_ITEM_ACTIVATED, [&](wxListEvent& e) { EndModal(wxID_OK); }); diff --git a/src/MapEditor/UI/Dialogs/SectorSpecialDialog.h b/src/MapEditor/UI/Dialogs/SectorSpecialDialog.h index 5fda69f6b..1628f5640 100644 --- a/src/MapEditor/UI/Dialogs/SectorSpecialDialog.h +++ b/src/MapEditor/UI/Dialogs/SectorSpecialDialog.h @@ -1,10 +1,11 @@ #pragma once -#include "UI/Lists/ListView.h" #include "UI/SDialog.h" namespace slade { +class ListView; + class SectorSpecialPanel : public wxPanel { public: diff --git a/src/MapEditor/UI/Dialogs/ShowItemDialog.cpp b/src/MapEditor/UI/Dialogs/ShowItemDialog.cpp index 34cdd41b2..14ce8ec78 100644 --- a/src/MapEditor/UI/Dialogs/ShowItemDialog.cpp +++ b/src/MapEditor/UI/Dialogs/ShowItemDialog.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: https://slade.mancubus.net @@ -33,6 +33,7 @@ // ----------------------------------------------------------------------------- #include "Main.h" #include "ShowItemDialog.h" +#include "General/UI.h" #include "UI/WxUtils.h" using namespace slade; @@ -45,11 +46,11 @@ using namespace slade; // ----------------------------------------------------------------------------- namespace { -vector obj_types{ MapObject::Type::Vertex, - MapObject::Type::Line, - MapObject::Type::Side, - MapObject::Type::Sector, - MapObject::Type::Thing }; +vector obj_types{ MapObject::Type::Vertex, + MapObject::Type::Line, + MapObject::Type::Side, + MapObject::Type::Sector, + MapObject::Type::Thing }; } @@ -69,7 +70,7 @@ ShowItemDialog::ShowItemDialog(wxWindow* parent) : wxDialog(parent, -1, "Show It auto sizer = new wxBoxSizer(wxVERTICAL); SetSizer(sizer); auto gb_sizer = new wxGridBagSizer(ui::pad(), ui::pad()); - sizer->Add(gb_sizer, 1, wxEXPAND | wxLEFT | wxRIGHT | wxTOP, ui::padLarge()); + sizer->Add(gb_sizer, wxutil::sfWithLargeBorder(1, wxLEFT | wxRIGHT | wxTOP).Expand()); // Object type wxString types[] = { "Vertex", "Line", "Side", "Sector", "Thing" }; @@ -84,13 +85,13 @@ ShowItemDialog::ShowItemDialog(wxWindow* parent) : wxDialog(parent, -1, "Show It // Dialog buttons sizer->AddSpacer(ui::pad()); - sizer->Add(CreateButtonSizer(wxOK | wxCANCEL), 0, wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, ui::padLarge()); + sizer->Add(CreateButtonSizer(wxOK | wxCANCEL), wxutil::sfWithLargeBorder(0, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); // Init layout gb_sizer->AddGrowableCol(1, 1); SetInitialSize(wxutil::scaledSize(300, -1)); CenterOnParent(); - wxWindowBase::Layout(); + wxTopLevelWindowBase::Layout(); text_index_->SetFocus(); text_index_->SetFocusFromKbd(); } diff --git a/src/MapEditor/UI/Dialogs/ShowItemDialog.h b/src/MapEditor/UI/Dialogs/ShowItemDialog.h index 8896305eb..51e060ff9 100644 --- a/src/MapEditor/UI/Dialogs/ShowItemDialog.h +++ b/src/MapEditor/UI/Dialogs/ShowItemDialog.h @@ -11,7 +11,7 @@ class ShowItemDialog : public wxDialog { public: ShowItemDialog(wxWindow* parent); - ~ShowItemDialog() {} + ~ShowItemDialog() override = default; MapObject::Type type() const; int index() const; diff --git a/src/MapEditor/UI/Dialogs/SpecialPresetDialog.cpp b/src/MapEditor/UI/Dialogs/SpecialPresetDialog.cpp index 7b1722fb2..aa37ca280 100644 --- a/src/MapEditor/UI/Dialogs/SpecialPresetDialog.cpp +++ b/src/MapEditor/UI/Dialogs/SpecialPresetDialog.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -33,6 +33,7 @@ #include "Main.h" #include "SpecialPresetDialog.h" #include "Game/Configuration.h" +#include "General/UI.h" #include "UI/WxUtils.h" using namespace slade; @@ -48,12 +49,12 @@ namespace slade class SpecialPresetData : public wxClientData { public: - SpecialPresetData(const game::SpecialPreset& preset) : preset_{ preset } {} + SpecialPresetData(const game::SpecialPreset& preset) : preset_{ &preset } {} - const game::SpecialPreset& preset() const { return preset_; } + const game::SpecialPreset& preset() const { return *preset_; } private: - game::SpecialPreset const& preset_; + game::SpecialPreset const* preset_; }; // ----------------------------------------------------------------------------- @@ -65,10 +66,7 @@ class SpecialPresetData : public wxClientData class SpecialPresetTreeView : public wxDataViewTreeCtrl { public: - SpecialPresetTreeView(wxWindow* parent) : - wxDataViewTreeCtrl{ parent, -1 }, - root_{ wxDataViewItem(nullptr) }, - parent_dialog_{ nullptr } + SpecialPresetTreeView(wxWindow* parent) : wxDataViewTreeCtrl{ parent, -1 }, root_{ wxDataViewItem(nullptr) } { // Computing the minimum width of the tree is slightly complicated, since // wx doesn't expose it to us directly @@ -83,16 +81,19 @@ class SpecialPresetTreeView : public wxDataViewTreeCtrl // Bind events Bind(wxEVT_DATAVIEW_ITEM_START_EDITING, [&](wxDataViewEvent& e) { e.Veto(); }); - Bind(wxEVT_DATAVIEW_ITEM_ACTIVATED, [&](wxDataViewEvent& e) { - if (GetChildCount(e.GetItem()) > 0) + Bind( + wxEVT_DATAVIEW_ITEM_ACTIVATED, + [&](wxDataViewEvent& e) { - // Expand if group node - Expand(e.GetItem()); - e.Skip(); - } - else if (parent_dialog_) - parent_dialog_->EndModal(wxID_OK); - }); + if (GetChildCount(e.GetItem()) > 0) + { + // Expand if group node + Expand(e.GetItem()); + e.Skip(); + } + else if (parent_dialog_) + parent_dialog_->EndModal(wxID_OK); + }); // 64 is an arbitrary fudge factor -- should be at least the width of a // scrollbar plus the expand icons plus any extra padding @@ -166,7 +167,7 @@ class SpecialPresetTreeView : public wxDataViewTreeCtrl return current; } - void addPresets(const vector& presets, wxSize& textsize, wxClientDC& dc) + void addPresets(const vector& presets, wxSize& textsize, const wxClientDC& dc) { for (auto& preset : presets) { @@ -197,19 +198,19 @@ SpecialPresetDialog::SpecialPresetDialog(wxWindow* parent) : SDialog{ parent, "S // Presets tree tree_presets_ = new SpecialPresetTreeView(this); tree_presets_->setParentDialog(this); - sizer->Add(tree_presets_, 1, wxALL | wxEXPAND, ui::padLarge()); + sizer->Add(tree_presets_, wxutil::sfWithLargeBorder(1).Expand()); // OK button auto hbox = new wxBoxSizer(wxHORIZONTAL); - sizer->Add(hbox, 0, wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, ui::padLarge()); + sizer->Add(hbox, wxutil::sfWithLargeBorder(0, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); hbox->AddStretchSpacer(1); auto btn_ok = new wxButton(this, -1, "OK"); - hbox->Add(btn_ok, 0, wxEXPAND | wxRIGHT, ui::pad()); + hbox->Add(btn_ok, wxutil::sfWithBorder(0, wxRIGHT).Expand()); btn_ok->Bind(wxEVT_BUTTON, [&](wxCommandEvent& e) { EndModal(wxID_OK); }); // Cancel button auto btn_cancel = new wxButton(this, -1, "Cancel"); - hbox->Add(btn_cancel, 0, wxEXPAND); + hbox->Add(btn_cancel, wxSizerFlags().Expand()); btn_cancel->Bind(wxEVT_BUTTON, [&](wxCommandEvent& e) { EndModal(wxID_CANCEL); }); } diff --git a/src/MapEditor/UI/Dialogs/ThingTypeBrowser.cpp b/src/MapEditor/UI/Dialogs/ThingTypeBrowser.cpp index 85987b0e8..11e199c8c 100644 --- a/src/MapEditor/UI/Dialogs/ThingTypeBrowser.cpp +++ b/src/MapEditor/UI/Dialogs/ThingTypeBrowser.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -33,10 +33,10 @@ #include "Main.h" #include "ThingTypeBrowser.h" #include "Game/Configuration.h" +#include "General/UI.h" #include "MapEditor/MapEditor.h" #include "MapEditor/MapTextureManager.h" #include "OpenGL/Drawing.h" -#include "UI/WxUtils.h" using namespace slade; @@ -63,16 +63,20 @@ CVAR(Bool, use_zeth_icons, false, CVar::Flag::Save) bool ThingBrowserItem::loadImage() { // Get sprite - auto tex = mapeditor::textureManager().sprite(type_.sprite(), type_.translation(), type_.palette()).gl_id; - if (!tex && use_zeth_icons && type_.zethIcon() >= 0) + auto tex = mapeditor::textureManager() + .sprite(thing_type_->sprite(), thing_type_->translation(), thing_type_->palette()) + .gl_id; + if (!tex && use_zeth_icons && thing_type_->zethIcon() >= 0) { // Sprite not found, try the Zeth icon - tex = mapeditor::textureManager().editorImage(fmt::format("zethicons/zeth{:02d}", type_.zethIcon())).gl_id; + tex = mapeditor::textureManager() + .editorImage(fmt::format("zethicons/zeth{:02d}", thing_type_->zethIcon())) + .gl_id; } if (!tex) { // Sprite not found, try an icon - tex = mapeditor::textureManager().editorImage(fmt::format("thing/{}", type_.icon())).gl_id; + tex = mapeditor::textureManager().editorImage(fmt::format("thing/{}", thing_type_->icon())).gl_id; } if (!tex) { diff --git a/src/MapEditor/UI/Dialogs/ThingTypeBrowser.h b/src/MapEditor/UI/Dialogs/ThingTypeBrowser.h index baa236352..ed99834be 100644 --- a/src/MapEditor/UI/Dialogs/ThingTypeBrowser.h +++ b/src/MapEditor/UI/Dialogs/ThingTypeBrowser.h @@ -1,5 +1,6 @@ #pragma once +#include "UI/Browser/BrowserItem.h" #include "UI/Browser/BrowserWindow.h" namespace slade @@ -14,22 +15,22 @@ class ThingBrowserItem : public BrowserItem public: ThingBrowserItem(const wxString& name, const game::ThingType& type, unsigned index) : BrowserItem{ name, index }, - type_{ type } + thing_type_{ &type } { } - ~ThingBrowserItem() = default; + ~ThingBrowserItem() override = default; bool loadImage() override; private: - game::ThingType const& type_; + game::ThingType const* thing_type_; }; class ThingTypeBrowser : public BrowserWindow { public: ThingTypeBrowser(wxWindow* parent, int type = -1); - ~ThingTypeBrowser() = default; + ~ThingTypeBrowser() override = default; void setupViewOptions(); int selectedType() const; diff --git a/src/MapEditor/UI/GenLineSpecialPanel.cpp b/src/MapEditor/UI/GenLineSpecialPanel.cpp index 365f99565..e132839e8 100644 --- a/src/MapEditor/UI/GenLineSpecialPanel.cpp +++ b/src/MapEditor/UI/GenLineSpecialPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: https://slade.mancubus.net @@ -32,6 +32,7 @@ #include "Main.h" #include "MapEditor/UI/GenLineSpecialPanel.h" #include "Game/GenLineSpecial.h" +#include "General/UI.h" #include "UI/WxUtils.h" using namespace slade; @@ -57,10 +58,10 @@ GenLineSpecialPanel::GenLineSpecialPanel(wxWindow* parent) : wxPanel(parent, -1) choice_type_ = new wxChoice(this, -1); choice_type_->Set(wxutil::arrayString({ "Floor", "Ceiling", "Door", "Locked Door", "Lift", "Stairs", "Crusher" })); choice_type_->Bind(wxEVT_CHOICE, &GenLineSpecialPanel::onChoiceTypeChanged, this); - sizer->Add(wxutil::createLabelHBox(this, "Type:", choice_type_), 0, wxEXPAND | wxBOTTOM, ui::pad()); + sizer->Add(wxutil::createLabelHBox(this, "Type:", choice_type_), wxutil::sfWithBorder(0, wxBOTTOM).Expand()); gb_sizer_ = new wxGridBagSizer(ui::pad(), ui::pad()); - sizer->Add(gb_sizer_, 1, wxEXPAND); + sizer->Add(gb_sizer_, wxSizerFlags(1).Expand()); // Trigger label_props_[0] = new wxStaticText(this, -1, "Trigger:", { -1, -1 }, { -1, -1 }, wxALIGN_CENTER_VERTICAL); @@ -466,6 +467,8 @@ int GenLineSpecialPanel::special() const // // ----------------------------------------------------------------------------- +// ReSharper disable CppMemberFunctionMayBeConst +// ReSharper disable CppParameterMayBeConstPtrOrRef // ----------------------------------------------------------------------------- // Called when the special type dropdown is changed diff --git a/src/MapEditor/UI/GenLineSpecialPanel.h b/src/MapEditor/UI/GenLineSpecialPanel.h index f88a161ae..49fa08f97 100644 --- a/src/MapEditor/UI/GenLineSpecialPanel.h +++ b/src/MapEditor/UI/GenLineSpecialPanel.h @@ -10,7 +10,7 @@ class GenLineSpecialPanel : public wxPanel { public: GenLineSpecialPanel(wxWindow* parent); - ~GenLineSpecialPanel() = default; + ~GenLineSpecialPanel() override = default; void setupForType(int type); void setProp(int prop, int value); diff --git a/src/MapEditor/UI/MapBackupPanel.cpp b/src/MapEditor/UI/MapBackupPanel.cpp index 805026bf3..00a9f6de9 100644 --- a/src/MapEditor/UI/MapBackupPanel.cpp +++ b/src/MapEditor/UI/MapBackupPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: https://slade.mancubus.net @@ -58,7 +58,7 @@ MapBackupPanel::MapBackupPanel(wxWindow* parent) : wxPanel{ parent, -1 }, archiv SetSizer(sizer); // Backups list - sizer->Add(list_backups_ = new ListView(this, -1), 0, wxEXPAND | wxRIGHT, ui::pad()); + sizer->Add(list_backups_ = new ListView(this, -1), wxutil::sfWithBorder(0, wxRIGHT).Expand()); // Map preview sizer->Add(canvas_map_ = new MapPreviewCanvas(this), 1, wxEXPAND); diff --git a/src/MapEditor/UI/MapBackupPanel.h b/src/MapEditor/UI/MapBackupPanel.h index 39642e91e..e703e3e8e 100644 --- a/src/MapEditor/UI/MapBackupPanel.h +++ b/src/MapEditor/UI/MapBackupPanel.h @@ -12,7 +12,7 @@ class MapBackupPanel : public wxPanel { public: MapBackupPanel(wxWindow* parent); - ~MapBackupPanel() = default; + ~MapBackupPanel() override = default; Archive* selectedMapData() const { return archive_mapdata_.get(); } diff --git a/src/MapEditor/UI/MapCanvas.cpp b/src/MapEditor/UI/MapCanvas.cpp index affece7f5..996bf1140 100644 --- a/src/MapEditor/UI/MapCanvas.cpp +++ b/src/MapEditor/UI/MapCanvas.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: https://slade.mancubus.net @@ -33,15 +33,25 @@ #include "Main.h" #include "MapCanvas.h" #include "App.h" +#include "MapEditor/Edit/Input.h" +#include "MapEditor/MapEditContext.h" +#include "MapEditor/MapEditor.h" +#include "MapEditor/Renderer/MapRenderer3D.h" #include "MapEditor/Renderer/Overlays/MCOverlay.h" +#include "MapEditor/Renderer/Renderer.h" #include "MapEditor/SectorBuilder.h" -#include "OpenGL/Drawing.h" -#include "UI/WxUtils.h" +#include "SLADEMap/MapObject/MapLine.h" +#include "SLADEMap/MapObject/MapSector.h" +#include "SLADEMap/MapObjectList/LineList.h" +#include "SLADEMap/SLADEMap.h" #include "Utility/MathStuff.h" +#include "Utility/Polygon2D.h" +#include +#include +#include using namespace slade; - -using mapeditor::Mode; +using namespace mapeditor; // ----------------------------------------------------------------------------- @@ -64,7 +74,8 @@ CVAR(Int, map_bg_ms, 15, CVar::Flag::Save) // ----------------------------------------------------------------------------- MapCanvas::MapCanvas(wxWindow* parent, int id, MapEditContext* context) : OGLCanvas{ parent, id, false }, - context_{ context } + context_{ context }, + sf_clock_{ new sf::Clock } { // Init variables context_->setCanvas(this); @@ -118,7 +129,8 @@ void MapCanvas::mouseToCenter() { auto rect = GetScreenRect(); mouse_warp_ = true; - sf::Mouse::setPosition(sf::Vector2i(rect.x + int(rect.width * 0.5), rect.y + int(rect.height * 0.5))); + sf::Mouse::setPosition( + sf::Vector2i(rect.x + static_cast(rect.width * 0.5), rect.y + static_cast(rect.height * 0.5))); } // ----------------------------------------------------------------------------- @@ -158,9 +170,9 @@ void MapCanvas::mouseLook3d() if (!overlay_current || !overlay_current->isActive() || (overlay_current && overlay_current->allow3dMlook())) { // Get relative mouse movement (scale with dpi on macOS and Linux) - const bool useScaleFactor = (app::platform() == app::MacOS || app::platform() == app::Linux); - const double scale = useScaleFactor ? GetContentScaleFactor() : 1.; - const double threshold = scale - 1.0; + const bool useScaleFactor = (app::platform() == app::MacOS || app::platform() == app::Linux); + const double scale = useScaleFactor ? GetContentScaleFactor() : 1.; + const double threshold = scale - 1.0; wxRealPoint mouse_pos = wxGetMousePosition(); mouse_pos.x *= scale; @@ -266,7 +278,7 @@ void MapCanvas::onKeyDown(wxKeyEvent& e) if (e.GetKeyCode() == WXK_F6) { Polygon2D poly; - sf::Clock clock; + // sf::Clock clock; log::info(1, "Generating polygons..."); for (unsigned a = 0; a < context_->map().nSectors(); a++) { @@ -481,11 +493,11 @@ void MapCanvas::onIdle(wxIdleEvent& e) mouseLook3d(); // Get time since last redraw - long frametime = (sf_clock_.getElapsedTime().asMilliseconds()) - last_time_; + long frametime = (sf_clock_->getElapsedTime().asMilliseconds()) - last_time_; if (context_->update(frametime)) { - last_time_ = (sf_clock_.getElapsedTime().asMilliseconds()); + last_time_ = (sf_clock_->getElapsedTime().asMilliseconds()); Refresh(); } } @@ -499,11 +511,11 @@ void MapCanvas::onRTimer(wxTimerEvent& e) mouseLook3d(); // Get time since last redraw - long frametime = (sf_clock_.getElapsedTime().asMilliseconds()) - last_time_; + long frametime = (sf_clock_->getElapsedTime().asMilliseconds()) - last_time_; if (context_->update(frametime)) { - last_time_ = (sf_clock_.getElapsedTime().asMilliseconds()); + last_time_ = (sf_clock_->getElapsedTime().asMilliseconds()); Refresh(); } } diff --git a/src/MapEditor/UI/MapCanvas.h b/src/MapEditor/UI/MapCanvas.h index 178ede1cf..da458278c 100644 --- a/src/MapEditor/UI/MapCanvas.h +++ b/src/MapEditor/UI/MapCanvas.h @@ -1,16 +1,25 @@ #pragma once #include "General/KeyBind.h" -#include "MapEditor/MapEditContext.h" #include "UI/Canvas/OGLCanvas.h" +namespace sf +{ +class Clock; +} + namespace slade { +namespace mapeditor +{ + class MapEditContext; +} + class MapCanvas : public OGLCanvas, public KeyBindHandler { public: - MapCanvas(wxWindow* parent, int id, MapEditContext* context); - ~MapCanvas() = default; + MapCanvas(wxWindow* parent, int id, mapeditor::MapEditContext* context); + ~MapCanvas() override = default; // Drawing void draw() override; @@ -24,10 +33,10 @@ class MapCanvas : public OGLCanvas, public KeyBindHandler void onKeyBindPress(string_view name) override; private: - MapEditContext* context_ = nullptr; - bool mouse_warp_ = false; - vector fps_avg_; - sf::Clock sf_clock_; + mapeditor::MapEditContext* context_ = nullptr; + bool mouse_warp_ = false; + vector fps_avg_; + unique_ptr sf_clock_; // Events void onSize(wxSizeEvent& e); diff --git a/src/MapEditor/UI/MapChecksPanel.cpp b/src/MapEditor/UI/MapChecksPanel.cpp index 2e54da891..7be38ed94 100644 --- a/src/MapEditor/UI/MapChecksPanel.cpp +++ b/src/MapEditor/UI/MapChecksPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -33,6 +33,7 @@ // ----------------------------------------------------------------------------- #include "Main.h" #include "MapChecksPanel.h" +#include "General/UI.h" #include "MapEditor/MapChecks.h" #include "MapEditor/MapEditContext.h" #include "MapEditor/MapEditor.h" @@ -117,7 +118,10 @@ MapChecksPanel::MapChecksPanel(wxWindow* parent, SLADEMap* map) : DockPanel{ par btn_export_->Enable(false); } -MapChecksPanel::~MapChecksPanel() {} +// ----------------------------------------------------------------------------- +// MapChecksPanel class destructor +// ----------------------------------------------------------------------------- +MapChecksPanel::~MapChecksPanel() = default; // ----------------------------------------------------------------------------- // Updates the check status label text @@ -141,10 +145,10 @@ void MapChecksPanel::showCheckItem(unsigned index) switch (obj->objType()) { case MapObject::Type::Vertex: mapeditor::editContext().setEditMode(mapeditor::Mode::Vertices); break; - case MapObject::Type::Line: mapeditor::editContext().setEditMode(mapeditor::Mode::Lines); break; + case MapObject::Type::Line: mapeditor::editContext().setEditMode(mapeditor::Mode::Lines); break; case MapObject::Type::Sector: mapeditor::editContext().setEditMode(mapeditor::Mode::Sectors); break; - case MapObject::Type::Thing: mapeditor::editContext().setEditMode(mapeditor::Mode::Things); break; - default: break; + case MapObject::Type::Thing: mapeditor::editContext().setEditMode(mapeditor::Mode::Things); break; + default: break; } // Scroll to object @@ -207,12 +211,12 @@ void MapChecksPanel::refreshList() lb_errors_->Select(0); lb_errors_->EnsureVisible(0); } - else if (selected >= 0 && selected < (int)lb_errors_->GetCount()) + else if (selected >= 0 && selected < static_cast(lb_errors_->GetCount())) { lb_errors_->Select(selected); lb_errors_->EnsureVisible(selected); } - else if (selected >= (int)lb_errors_->GetCount() && lb_errors_->GetCount() > 0) + else if (selected >= static_cast(lb_errors_->GetCount()) && lb_errors_->GetCount() > 0) { lb_errors_->Select(lb_errors_->GetCount() - 1); lb_errors_->EnsureVisible(lb_errors_->GetCount()); @@ -245,29 +249,29 @@ void MapChecksPanel::reset() // ----------------------------------------------------------------------------- void MapChecksPanel::layoutVertical() { + namespace wx = wxutil; + auto sizer = new wxBoxSizer(wxVERTICAL); SetSizer(sizer); // Checks - sizer->Add(wxutil::createLabelVBox(this, "Check for:", clb_active_checks_), 0, wxEXPAND | wxALL, ui::pad()); - sizer->Add(btn_check_, 0, wxALIGN_RIGHT | wxLEFT | wxRIGHT | wxBOTTOM, ui::pad()); + sizer->Add(wx::createLabelVBox(this, "Check for:", clb_active_checks_), wx::sfWithBorder().Expand()); + sizer->Add(btn_check_, wx::sfWithBorder(0, wxLEFT | wxRIGHT | wxBOTTOM).Right()); // Results - sizer->Add(label_status_, 0, wxEXPAND | wxLEFT | wxRIGHT, ui::pad()); + sizer->Add(label_status_, wx::sfWithBorder(0, wxLEFT | wxRIGHT).Expand()); sizer->AddSpacer(ui::px(ui::Size::PadMinimum)); - sizer->Add(lb_errors_, 1, wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, ui::pad()); + sizer->Add(lb_errors_, wx::sfWithBorder(1, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); // Result actions auto hbox = new wxBoxSizer(wxHORIZONTAL); - sizer->Add(hbox, 0, wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, ui::pad()); - hbox->Add(btn_edit_object_, 0, wxEXPAND | wxRIGHT, ui::pad()); + sizer->Add(hbox, wx::sfWithBorder(0, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); + hbox->Add(btn_edit_object_, wx::sfWithBorder(0, wxRIGHT).Expand()); hbox->AddStretchSpacer(); - hbox->Add(btn_export_, 0, wxEXPAND); + hbox->Add(btn_export_, wxSizerFlags().Expand()); sizer->Add( - wxutil::layoutHorizontally(vector{ btn_fix1_, btn_fix2_ }), - 0, - wxLEFT | wxRIGHT | wxBOTTOM, - ui::pad()); + wx::layoutHorizontally(vector{ btn_fix1_, btn_fix2_ }), + wx::sfWithBorder(0, wxLEFT | wxRIGHT | wxBOTTOM)); } // ----------------------------------------------------------------------------- @@ -278,7 +282,7 @@ void MapChecksPanel::layoutHorizontal() { SetSizer(new wxBoxSizer(wxVERTICAL)); auto sizer = new wxGridBagSizer(ui::pad(), ui::pad()); - GetSizer()->Add(sizer, 1, wxEXPAND | wxALL, ui::pad()); + GetSizer()->Add(sizer, wxutil::sfWithBorder(1).Expand()); // Checks sizer->Add(new wxStaticText(this, -1, "Check for:"), { 0, 0 }, { 1, 1 }, wxEXPAND); @@ -304,6 +308,8 @@ void MapChecksPanel::layoutHorizontal() // // ----------------------------------------------------------------------------- +// ReSharper disable CppMemberFunctionMayBeConst +// ReSharper disable CppParameterMayBeConstPtrOrRef // ----------------------------------------------------------------------------- // Called when the 'check' button is clicked @@ -364,7 +370,7 @@ void MapChecksPanel::onBtnCheck(wxCommandEvent& e) void MapChecksPanel::onListBoxItem(wxCommandEvent& e) { int selected = lb_errors_->GetSelection(); - if (selected >= 0 && selected < (int)check_items_.size()) + if (selected >= 0 && selected < static_cast(check_items_.size())) showCheckItem(selected); } @@ -374,7 +380,7 @@ void MapChecksPanel::onListBoxItem(wxCommandEvent& e) void MapChecksPanel::onBtnFix1(wxCommandEvent& e) { int selected = lb_errors_->GetSelection(); - if (selected >= 0 && selected < (int)check_items_.size()) + if (selected >= 0 && selected < static_cast(check_items_.size())) { mapeditor::editContext().beginUndoRecord(wxutil::strToView(btn_fix1_->GetLabel())); mapeditor::editContext().selection().clear(); @@ -395,7 +401,7 @@ void MapChecksPanel::onBtnFix1(wxCommandEvent& e) void MapChecksPanel::onBtnFix2(wxCommandEvent& e) { int selected = lb_errors_->GetSelection(); - if (selected >= 0 && selected < (int)check_items_.size()) + if (selected >= 0 && selected < static_cast(check_items_.size())) { mapeditor::editContext().beginUndoRecord(wxutil::strToView(btn_fix2_->GetLabel())); mapeditor::editContext().selection().clear(); @@ -416,7 +422,7 @@ void MapChecksPanel::onBtnFix2(wxCommandEvent& e) void MapChecksPanel::onBtnEditObject(wxCommandEvent& e) { int selected = lb_errors_->GetSelection(); - if (selected >= 0 && selected < (int)check_items_.size()) + if (selected >= 0 && selected < static_cast(check_items_.size())) { vector list; list.push_back(check_items_[selected].check->getObject(check_items_[selected].index)); diff --git a/src/MapEditor/UI/MapChecksPanel.h b/src/MapEditor/UI/MapChecksPanel.h index 19fc22dfb..f22401b9f 100644 --- a/src/MapEditor/UI/MapChecksPanel.h +++ b/src/MapEditor/UI/MapChecksPanel.h @@ -13,7 +13,7 @@ class MapChecksPanel : public DockPanel { public: MapChecksPanel(wxWindow* parent, SLADEMap* map); - ~MapChecksPanel(); + ~MapChecksPanel() override; void updateStatusText(const wxString& text); void showCheckItem(unsigned index); diff --git a/src/MapEditor/UI/MapEditorWindow.cpp b/src/MapEditor/UI/MapEditorWindow.cpp index 11a926a6e..98c47012e 100644 --- a/src/MapEditor/UI/MapEditorWindow.cpp +++ b/src/MapEditor/UI/MapEditorWindow.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -35,26 +35,30 @@ #include "Archive/ArchiveManager.h" #include "Archive/Formats/WadArchive.h" #include "Game/Configuration.h" +#include "Game/Game.h" #include "General/Misc.h" #include "General/UI.h" #include "MainEditor/MainEditor.h" +#include "MapEditor/Edit/Input.h" #include "MapEditor/MapBackupManager.h" #include "MapEditor/MapEditContext.h" #include "MapEditor/MapEditor.h" #include "MapEditor/MapTextureManager.h" #include "MapEditor/NodeBuilders.h" +#include "MapEditor/Renderer/Renderer.h" #include "MapEditor/UI/MapCanvas.h" #include "MapEditor/UI/MapChecksPanel.h" #include "MapEditor/UI/ObjectEditPanel.h" #include "MapEditor/UI/PropsPanel/MapObjectPropsPanel.h" #include "MapEditor/UI/ScriptEditorPanel.h" #include "MapEditor/UI/ShapeDrawPanel.h" +#include "OpenGL/View.h" +#include "SLADEMap/SLADEMap.h" #include "SLADEWxApp.h" #include "Scripting/ScriptManager.h" #include "UI/Controls/ConsolePanel.h" #include "UI/Controls/UndoManagerHistoryPanel.h" #include "UI/Dialogs/MapEditorConfigDialog.h" -#include "UI/Dialogs/Preferences/BaseResourceArchivesPanel.h" #include "UI/Dialogs/Preferences/PreferencesDialog.h" #include "UI/Dialogs/RunDialog.h" #include "UI/SAuiTabArt.h" @@ -64,6 +68,7 @@ #include "Utility/Tokenizer.h" using namespace slade; +using namespace mapeditor; // ----------------------------------------------------------------------------- @@ -594,7 +599,7 @@ bool MapEditorWindow::chooseMap(Archive* archive) // ----------------------------------------------------------------------------- // Opens [map] in the editor // ----------------------------------------------------------------------------- -bool MapEditorWindow::openMap(const Archive::MapDesc& map) +bool MapEditorWindow::openMap(const MapDesc& map) { // If a map is currently open and modified, prompt to save changes if (mapeditor::editContext().map().isModified()) @@ -694,7 +699,7 @@ bool MapEditorWindow::openMap(const Archive::MapDesc& map) // ----------------------------------------------------------------------------- // Loads any scripts from [map] into the script editor // ----------------------------------------------------------------------------- -void MapEditorWindow::loadMapScripts(const Archive::MapDesc& map) +void MapEditorWindow::loadMapScripts(const MapDesc& map) { // Don't bother if no scripting language specified if (game::configuration().scriptLanguage().empty()) diff --git a/src/MapEditor/UI/MapEditorWindow.h b/src/MapEditor/UI/MapEditorWindow.h index 7e826a215..5b18dd89c 100644 --- a/src/MapEditor/UI/MapEditorWindow.h +++ b/src/MapEditor/UI/MapEditorWindow.h @@ -1,16 +1,16 @@ #pragma once -#include "Archive/Archive.h" #include "General/SAction.h" #include "UI/STopWindow.h" namespace slade { +struct MapDesc; +class Archive; class MapObject; class MapObjectPropsPanel; class ScriptEditorPanel; class ObjectEditPanel; -class ObjectEditGroup; class WadArchive; class MapCanvas; class MapChecksPanel; @@ -18,6 +18,11 @@ class UndoManagerHistoryPanel; class UndoManager; class ArchiveEntry; +namespace mapeditor +{ + class ObjectEditGroup; +} + class MapEditorWindow : public STopWindow, public SActionHandler { public: @@ -31,8 +36,8 @@ class MapEditorWindow : public STopWindow, public SActionHandler void setupMenu(); void setupLayout(); bool chooseMap(Archive* archive = nullptr); - bool openMap(const Archive::MapDesc& map); - void loadMapScripts(const Archive::MapDesc& map); + bool openMap(const MapDesc& map); + void loadMapScripts(const MapDesc& map); bool writeMap(WadArchive& wad, const wxString& name = "MAP01", bool nodes = true); bool saveMap(); bool saveMapAs(); @@ -47,7 +52,7 @@ class MapEditorWindow : public STopWindow, public SActionHandler MapObjectPropsPanel* propsPanel() const { return panel_obj_props_; } ObjectEditPanel* objectEditPanel() const { return panel_obj_edit_; } - void showObjectEditPanel(bool show, ObjectEditGroup* group); + void showObjectEditPanel(bool show, mapeditor::ObjectEditGroup* group); void showShapeDrawPanel(bool show = true); // SAction handler diff --git a/src/MapEditor/UI/ObjectEditPanel.cpp b/src/MapEditor/UI/ObjectEditPanel.cpp index 7fff92308..d055ba211 100644 --- a/src/MapEditor/UI/ObjectEditPanel.cpp +++ b/src/MapEditor/UI/ObjectEditPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -40,6 +40,7 @@ #include "UI/WxUtils.h" using namespace slade; +using namespace mapeditor; // ----------------------------------------------------------------------------- @@ -93,7 +94,7 @@ ObjectEditPanel::ObjectEditPanel(wxWindow* parent) : wxPanel(parent) // ----------------------------------------------------------------------------- // Initialises the panel with values from [group] // ----------------------------------------------------------------------------- -void ObjectEditPanel::init(ObjectEditGroup* group) +void ObjectEditPanel::init(const ObjectEditGroup* group) { // Check group was given if (!group) @@ -119,7 +120,7 @@ void ObjectEditPanel::init(ObjectEditGroup* group) // ----------------------------------------------------------------------------- // Updates the panel with values from [group] // ----------------------------------------------------------------------------- -void ObjectEditPanel::update(ObjectEditGroup* group, bool lock_rotation) const +void ObjectEditPanel::update(const ObjectEditGroup* group, bool lock_rotation) const { auto bbox = group->bbox(); int xoff = bbox.midX() - old_x_; @@ -129,8 +130,8 @@ void ObjectEditPanel::update(ObjectEditGroup* group, bool lock_rotation) const text_xoff_->SetValue(wxString::Format("%d", xoff)); text_yoff_->SetValue(wxString::Format("%d", yoff)); - text_scalex_->SetValue(wxString::Format("%d", int(100 * xscale))); - text_scaley_->SetValue(wxString::Format("%d", int(100 * yscale))); + text_scalex_->SetValue(wxString::Format("%d", static_cast(100 * xscale))); + text_scaley_->SetValue(wxString::Format("%d", static_cast(100 * yscale))); combo_rotation_->SetValue(wxString::Format("%1.2f", group->rotation())); } @@ -139,50 +140,39 @@ void ObjectEditPanel::update(ObjectEditGroup* group, bool lock_rotation) const // ----------------------------------------------------------------------------- void ObjectEditPanel::setupLayout() { + namespace wx = wxutil; + // Init sizer SetSizer(new wxBoxSizer(wxVERTICAL)); auto sizer = new wxBoxSizer(wxHORIZONTAL); - GetSizer()->Add(sizer, 1, wxEXPAND | wxALL, ui::pad()); + GetSizer()->Add(sizer, wx::sfWithBorder(1).Expand()); // X offset - sizer->Add( - wxutil::createLabelHBox(this, "X Offset:", text_xoff_), 0, wxALIGN_CENTER_VERTICAL | wxRIGHT, ui::padLarge()); + sizer->Add(wx::createLabelHBox(this, "X Offset:", text_xoff_), wx::sfWithLargeBorder(0, wxRIGHT).CenterVertical()); // Y offset - sizer->Add( - wxutil::createLabelHBox(this, "Y Offset:", text_yoff_), 0, wxALIGN_CENTER_VERTICAL | wxRIGHT, ui::padLarge()); + sizer->Add(wx::createLabelHBox(this, "Y Offset:", text_yoff_), wx::sfWithLargeBorder(0, wxRIGHT).CenterVertical()); // X scale - sizer->Add( - wxutil::createLabelHBox(this, "X Scale:", text_scalex_), - 0, - wxALIGN_CENTER_VERTICAL | wxRIGHT, - ui::px(ui::Size::PadMinimum)); - sizer->Add(new wxStaticText(this, -1, "%"), 0, wxALIGN_CENTER_VERTICAL | wxRIGHT, ui::padLarge()); + sizer->Add(wx::createLabelHBox(this, "X Scale:", text_scalex_), wx::sfWithMinBorder(0, wxRIGHT).CenterVertical()); + sizer->Add(new wxStaticText(this, -1, "%"), wx::sfWithLargeBorder(0, wxRIGHT).CenterVertical()); // Y scale - sizer->Add( - wxutil::createLabelHBox(this, "Y Scale:", text_scaley_), - 0, - wxALIGN_CENTER_VERTICAL | wxRIGHT, - ui::px(ui::Size::PadMinimum)); - sizer->Add(new wxStaticText(this, -1, "%"), 0, wxALIGN_CENTER_VERTICAL | wxRIGHT, ui::padLarge()); + sizer->Add(wx::createLabelHBox(this, "Y Scale:", text_scaley_), wx::sfWithMinBorder(0, wxRIGHT).CenterVertical()); + sizer->Add(new wxStaticText(this, -1, "%"), wx::sfWithLargeBorder(0, wxRIGHT).CenterVertical()); // Rotation sizer->Add( - wxutil::createLabelHBox(this, "Rotation:", combo_rotation_), - 0, - wxALIGN_CENTER_VERTICAL | wxRIGHT, - ui::padLarge()); + wx::createLabelHBox(this, "Rotation:", combo_rotation_), wx::sfWithLargeBorder(0, wxRIGHT).CenterVertical()); // Mirror x/y - sizer->Add(cb_mirror_x_, 0, wxALIGN_CENTER_VERTICAL | wxRIGHT, ui::padLarge()); - sizer->Add(cb_mirror_y_, 0, wxALIGN_CENTER_VERTICAL | wxRIGHT, ui::padLarge()); + sizer->Add(cb_mirror_x_, wx::sfWithLargeBorder(0, wxRIGHT).CenterVertical()); + sizer->Add(cb_mirror_y_, wx::sfWithLargeBorder(0, wxRIGHT).CenterVertical()); // Buttons - sizer->Add(btn_preview_, 0, wxALIGN_CENTER_VERTICAL | wxRIGHT, ui::pad()); - sizer->Add(btn_cancel_, 0, wxALIGN_CENTER_VERTICAL | wxRIGHT, ui::pad()); - sizer->Add(btn_apply_, 0, wxALIGN_CENTER_VERTICAL); + sizer->Add(btn_preview_, wx::sfWithBorder(0, wxRIGHT).CenterVertical()); + sizer->Add(btn_cancel_, wx::sfWithBorder(0, wxRIGHT).CenterVertical()); + sizer->Add(btn_apply_, wxSizerFlags().CenterVertical()); } diff --git a/src/MapEditor/UI/ObjectEditPanel.h b/src/MapEditor/UI/ObjectEditPanel.h index 818539055..630fcb0c2 100644 --- a/src/MapEditor/UI/ObjectEditPanel.h +++ b/src/MapEditor/UI/ObjectEditPanel.h @@ -2,16 +2,19 @@ namespace slade { -class ObjectEditGroup; +namespace mapeditor +{ + class ObjectEditGroup; +} class ObjectEditPanel : public wxPanel { public: ObjectEditPanel(wxWindow* parent); - ~ObjectEditPanel() = default; + ~ObjectEditPanel() override = default; - void init(ObjectEditGroup* group); - void update(ObjectEditGroup* group, bool lock_rotation = false) const; + void init(const mapeditor::ObjectEditGroup* group); + void update(const mapeditor::ObjectEditGroup* group, bool lock_rotation = false) const; private: wxTextCtrl* text_xoff_ = nullptr; diff --git a/src/MapEditor/UI/PropsPanel/LinePropsPanel.cpp b/src/MapEditor/UI/PropsPanel/LinePropsPanel.cpp index d361110c0..c11e08c95 100644 --- a/src/MapEditor/UI/PropsPanel/LinePropsPanel.cpp +++ b/src/MapEditor/UI/PropsPanel/LinePropsPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -33,9 +33,16 @@ #include "Main.h" #include "LinePropsPanel.h" #include "Game/Configuration.h" +#include "Game/UDMFProperty.h" +#include "General/UI.h" #include "MapEditor/MapEditContext.h" +#include "MapEditor/MapEditor.h" #include "MapEditor/UI/Dialogs/ActionSpecialDialog.h" #include "MapObjectPropsPanel.h" +#include "SLADEMap/MapObject/MapLine.h" +#include "SLADEMap/MapObjectList/LineList.h" +#include "SLADEMap/MapObjectList/SectorList.h" +#include "SLADEMap/SLADEMap.h" #include "SidePropsPanel.h" #include "UI/Controls/NumberTextCtrl.h" #include "UI/WxUtils.h" @@ -120,6 +127,8 @@ LinePropsPanel::~LinePropsPanel() // ----------------------------------------------------------------------------- wxPanel* LinePropsPanel::setupGeneralTab() { + namespace wx = wxutil; + auto panel_flags = new wxPanel(stc_tabs_, -1); auto map_format = mapeditor::editContext().mapDesc().format; @@ -129,11 +138,11 @@ wxPanel* LinePropsPanel::setupGeneralTab() // Flags auto sizer_flags = new wxStaticBoxSizer(wxVERTICAL, panel_flags, "Flags"); - sizer->Add(sizer_flags, 0, wxEXPAND | wxALL, ui::pad()); + sizer->Add(sizer_flags, wx::sfWithBorder().Expand()); // Init flags auto gb_sizer_flags = new wxGridBagSizer(ui::pad() / 2, ui::pad()); - sizer_flags->Add(gb_sizer_flags, 1, wxEXPAND | wxALL, ui::pad()); + sizer_flags->Add(gb_sizer_flags, wx::sfWithBorder(1).Expand()); unsigned row = 0; unsigned col = 0; @@ -158,7 +167,7 @@ wxPanel* LinePropsPanel::setupGeneralTab() auto cb_flag = new wxCheckBox( panel_flags, -1, flags_udmf[a].name(), wxDefaultPosition, wxDefaultSize, wxCHK_3STATE); gb_sizer_flags->Add(cb_flag, wxGBPosition(row++, col), wxDefaultSpan, wxEXPAND); - flags_.push_back({ cb_flag, (int)a, flags_udmf[a].propName() }); + flags_.push_back({ cb_flag, static_cast(a), flags_udmf[a].propName() }); if (row > flag_mid) { @@ -188,7 +197,7 @@ wxPanel* LinePropsPanel::setupGeneralTab() wxDefaultSize, wxCHK_3STATE); gb_sizer_flags->Add(cb_flag, wxGBPosition(row++, col), wxDefaultSpan, wxEXPAND); - flags_.push_back({ cb_flag, (int)a, wxEmptyString }); + flags_.push_back({ cb_flag, static_cast(a), wxEmptyString }); if (row > flag_mid) { @@ -206,34 +215,37 @@ wxPanel* LinePropsPanel::setupGeneralTab() if (map_format == MapFormat::Doom) { auto hbox = new wxBoxSizer(wxHORIZONTAL); - sizer->Add(hbox, 0, wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, ui::pad()); + sizer->Add(hbox, wx::sfWithBorder(0, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); - hbox->Add(new wxStaticText(panel_flags, -1, "Sector Tag:"), 0, wxALIGN_CENTER_VERTICAL | wxRIGHT, ui::pad()); - hbox->Add(text_tag_ = new NumberTextCtrl(panel_flags), 1, wxALIGN_CENTER_VERTICAL | wxRIGHT, ui::pad()); + hbox->Add(new wxStaticText(panel_flags, -1, "Sector Tag:"), wx::sfWithBorder(0, wxRIGHT).CenterVertical()); + hbox->Add(text_tag_ = new NumberTextCtrl(panel_flags), wx::sfWithBorder(1, wxRIGHT).CenterVertical()); btn_new_tag_ = new wxButton(panel_flags, -1, "New Tag"); - hbox->Add(btn_new_tag_, 0, wxEXPAND); + hbox->Add(btn_new_tag_, wxSizerFlags().Expand()); // Bind event - btn_new_tag_->Bind(wxEVT_COMMAND_BUTTON_CLICKED, [&](wxCommandEvent& e) { - text_tag_->setNumber(mapeditor::editContext().map().sectors().firstFreeId()); - }); + btn_new_tag_->Bind( + wxEVT_COMMAND_BUTTON_CLICKED, + [&](wxCommandEvent& e) { text_tag_->setNumber(mapeditor::editContext().map().sectors().firstFreeId()); }); } // Id if (map_format == MapFormat::UDMF) { auto hbox = new wxBoxSizer(wxHORIZONTAL); - sizer->Add(hbox, 0, wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, ui::pad()); + sizer->Add(hbox, wx::sfWithBorder(0, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); - hbox->Add(new wxStaticText(panel_flags, -1, "Line ID:"), 0, wxALIGN_CENTER_VERTICAL | wxRIGHT, ui::pad()); - hbox->Add(text_id_ = new NumberTextCtrl(panel_flags), 1, wxALIGN_CENTER_VERTICAL | wxRIGHT, ui::pad()); - hbox->Add(btn_new_id_ = new wxButton(panel_flags, -1, "New ID"), 0, wxEXPAND); + hbox->Add(new wxStaticText(panel_flags, -1, "Line ID:"), wx::sfWithBorder(0, wxRIGHT).CenterVertical()); + hbox->Add(text_id_ = new NumberTextCtrl(panel_flags), wx::sfWithBorder(1, wxRIGHT).CenterVertical()); + hbox->Add(btn_new_id_ = new wxButton(panel_flags, -1, "New ID"), wxSizerFlags().Expand()); // Bind event - btn_new_id_->Bind(wxEVT_COMMAND_BUTTON_CLICKED, [&](wxCommandEvent& e) { - auto& map = mapeditor::editContext().map(); - text_id_->setNumber(map.lines().firstFreeId(map.currentFormat())); - }); + btn_new_id_->Bind( + wxEVT_COMMAND_BUTTON_CLICKED, + [&](wxCommandEvent& e) + { + auto& map = mapeditor::editContext().map(); + text_id_->setNumber(map.lines().firstFreeId(map.currentFormat())); + }); } return panel_flags; @@ -252,13 +264,13 @@ wxPanel* LinePropsPanel::setupSpecialTab() // Action special panel panel_special_ = new ActionSpecialPanel(panel); - sizer->Add(panel_special_, 1, wxEXPAND | wxALL, ui::pad()); + sizer->Add(panel_special_, wxutil::sfWithBorder(1).Expand()); // 'Override Special' checkbox cb_override_special_ = new wxCheckBox(panel, -1, "Override Action Special"); cb_override_special_->SetToolTip( "Differing action specials detected, tick this to set the action special for all selected lines"); - sizer->Add(cb_override_special_, 0, wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, ui::pad()); + sizer->Add(cb_override_special_, wxutil::sfWithBorder(0, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); return panel; } @@ -290,13 +302,14 @@ void LinePropsPanel::openObjects(vector& lines) for (auto& flag : flags_) { // Set initial flag checked value - flag.check_box->SetValue(game::configuration().lineFlagSet(flag.index, (MapLine*)lines[0])); + flag.check_box->SetValue(game::configuration().lineFlagSet(flag.index, dynamic_cast(lines[0]))); // Go through subsequent lines for (unsigned b = 1; b < lines.size(); b++) { // Check for mismatch - if (flag.check_box->GetValue() != game::configuration().lineFlagSet(flag.index, (MapLine*)lines[b])) + if (flag.check_box->GetValue() + != game::configuration().lineFlagSet(flag.index, dynamic_cast(lines[b]))) { // Set undefined flag.check_box->Set3StateValue(wxCHK_UNDETERMINED); @@ -408,7 +421,8 @@ void LinePropsPanel::applyChanges() // Other for (auto& flag : flags_) if (flag.check_box->Get3StateValue() != wxCHK_UNDETERMINED) - game::configuration().setLineFlag(flag.index, (MapLine*)object, flag.check_box->GetValue()); + game::configuration().setLineFlag( + flag.index, dynamic_cast(object), flag.check_box->GetValue()); } // Sector tag diff --git a/src/MapEditor/UI/PropsPanel/LinePropsPanel.h b/src/MapEditor/UI/PropsPanel/LinePropsPanel.h index 882c431cb..9195cd46f 100644 --- a/src/MapEditor/UI/PropsPanel/LinePropsPanel.h +++ b/src/MapEditor/UI/PropsPanel/LinePropsPanel.h @@ -16,11 +16,11 @@ class LinePropsPanel : public PropsPanelBase { public: LinePropsPanel(wxWindow* parent); - ~LinePropsPanel(); + ~LinePropsPanel() override; wxPanel* setupGeneralTab(); wxPanel* setupSpecialTab(); - void openObjects(vector& objects) override; + void openObjects(vector& lines) override; void applyChanges() override; private: diff --git a/src/MapEditor/UI/PropsPanel/MOPGProperty.cpp b/src/MapEditor/UI/PropsPanel/MOPGProperty.cpp index 66bda8793..1fd175ea0 100644 --- a/src/MapEditor/UI/PropsPanel/MOPGProperty.cpp +++ b/src/MapEditor/UI/PropsPanel/MOPGProperty.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: https://slade.mancubus.net @@ -34,7 +34,9 @@ // ----------------------------------------------------------------------------- #include "Main.h" #include "MOPGProperty.h" +#include "Game/ActionSpecial.h" #include "Game/Configuration.h" +#include "Game/UDMFProperty.h" #include "MapEditor/MapEditContext.h" #include "MapEditor/MapEditor.h" #include "MapEditor/UI/Dialogs/ActionSpecialDialog.h" @@ -42,6 +44,11 @@ #include "MapEditor/UI/Dialogs/SectorSpecialDialog.h" #include "MapEditor/UI/Dialogs/ThingTypeBrowser.h" #include "MapObjectPropsPanel.h" +#include "SLADEMap/MapObject/MapLine.h" +#include "SLADEMap/MapObject/MapThing.h" +#include "SLADEMap/MapObjectList/LineList.h" +#include "SLADEMap/MapObjectList/SectorList.h" +#include "SLADEMap/MapObjectList/ThingList.h" #include "SLADEMap/SLADEMap.h" #include "UI/Dialogs/Preferences/EditingPrefsPanel.h" @@ -82,7 +89,8 @@ void MOPGProperty::resetValue() // MOPGBoolProperty class constructor // ----------------------------------------------------------------------------- MOPGBoolProperty::MOPGBoolProperty(const wxString& label, const wxString& name) : - MOPGProperty{ name }, wxBoolProperty(label, name, false) + MOPGProperty{ name }, + wxBoolProperty(label, name, false) { } @@ -164,7 +172,8 @@ void MOPGBoolProperty::applyValue() // MOPGIntProperty class constructor // ----------------------------------------------------------------------------- MOPGIntProperty::MOPGIntProperty(const wxString& label, const wxString& name) : - MOPGProperty{ name }, wxIntProperty(label, name, 0) + MOPGProperty{ name }, + wxIntProperty(label, name, 0) { } @@ -246,7 +255,8 @@ void MOPGIntProperty::applyValue() // MOPGFloatProperty class constructor // ----------------------------------------------------------------------------- MOPGFloatProperty::MOPGFloatProperty(const wxString& label, const wxString& name) : - MOPGProperty{ name }, wxFloatProperty(label, name, 0) + MOPGProperty{ name }, + wxFloatProperty(label, name, 0) { } @@ -328,7 +338,8 @@ void MOPGFloatProperty::applyValue() // MOPGStringProperty class constructor // ----------------------------------------------------------------------------- MOPGStringProperty::MOPGStringProperty(const wxString& label, const wxString& name) : - MOPGProperty{ name }, wxStringProperty(label, name, "") + MOPGProperty{ name }, + wxStringProperty(label, name, "") { } @@ -650,7 +661,8 @@ bool MOPGThingTypeProperty::OnEvent(wxPropertyGrid* propgrid, wxWindow* window, // MOPGLineFlagProperty class constructor // ----------------------------------------------------------------------------- MOPGLineFlagProperty::MOPGLineFlagProperty(const wxString& label, const wxString& name, int index) : - MOPGBoolProperty(label, name), index_{ index } + MOPGBoolProperty(label, name), + index_{ index } { } @@ -668,12 +680,12 @@ void MOPGLineFlagProperty::openObjects(vector& objects) } // Check flag against first object - bool first = game::configuration().lineFlagSet(index_, (MapLine*)objects[0]); + bool first = game::configuration().lineFlagSet(index_, dynamic_cast(objects[0])); // Check whether all objects share the same flag setting for (unsigned a = 1; a < objects.size(); a++) { - if (game::configuration().lineFlagSet(index_, (MapLine*)objects[a]) != first) + if (game::configuration().lineFlagSet(index_, dynamic_cast(objects[a])) != first) { // Different value found, set unspecified SetValueToUnspecified(); @@ -705,7 +717,7 @@ void MOPGLineFlagProperty::applyValue() // Go through objects and set this value auto& objects = parent_->objects(); for (auto& object : objects) - game::configuration().setLineFlag(index_, (MapLine*)object, GetValue()); + game::configuration().setLineFlag(index_, dynamic_cast(object), GetValue()); } @@ -720,7 +732,8 @@ void MOPGLineFlagProperty::applyValue() // MOPGThingFlagProperty class constructor // ----------------------------------------------------------------------------- MOPGThingFlagProperty::MOPGThingFlagProperty(const wxString& label, const wxString& name, int index) : - MOPGBoolProperty(label, name), index_{ index } + MOPGBoolProperty(label, name), + index_{ index } { } @@ -738,12 +751,12 @@ void MOPGThingFlagProperty::openObjects(vector& objects) } // Check flag against first object - bool first = game::configuration().thingFlagSet(index_, (MapThing*)objects[0]); + bool first = game::configuration().thingFlagSet(index_, dynamic_cast(objects[0])); // Check whether all objects share the same flag setting for (unsigned a = 1; a < objects.size(); a++) { - if (game::configuration().thingFlagSet(index_, (MapThing*)objects[a]) != first) + if (game::configuration().thingFlagSet(index_, dynamic_cast(objects[a])) != first) { // Different value found, set unspecified SetValueToUnspecified(); @@ -775,7 +788,7 @@ void MOPGThingFlagProperty::applyValue() // Go through objects and set this value auto& objects = parent_->objects(); for (auto& object : objects) - game::configuration().setThingFlag(index_, (MapThing*)object, GetValue()); + game::configuration().setThingFlag(index_, dynamic_cast(object), GetValue()); } @@ -790,7 +803,8 @@ void MOPGThingFlagProperty::applyValue() // MOPGAngleProperty class constructor // ----------------------------------------------------------------------------- MOPGAngleProperty::MOPGAngleProperty(const wxString& label, const wxString& name) : - MOPGProperty{ name }, wxEditEnumProperty(label, name) + MOPGProperty{ name }, + wxEditEnumProperty(label, name) { // Setup combo box choices wxArrayString labels; @@ -890,15 +904,15 @@ wxString MOPGAngleProperty::ValueToString(wxVariant& value, int arg_flags) const switch (angle) { - case 0: return "0: East"; - case 45: return "45: Northeast"; - case 90: return "90: North"; + case 0: return "0: East"; + case 45: return "45: Northeast"; + case 90: return "90: North"; case 135: return "135: Northwest"; case 180: return "180: West"; case 225: return "225: Southwest"; case 270: return "270: South"; case 315: return "315: Southeast"; - default: return wxString::Format("%d", angle); + default: return wxString::Format("%d", angle); } } @@ -914,7 +928,8 @@ wxString MOPGAngleProperty::ValueToString(wxVariant& value, int arg_flags) const // MOPGColourProperty class constructor // ----------------------------------------------------------------------------- MOPGColourProperty::MOPGColourProperty(const wxString& label, const wxString& name) : - MOPGProperty{ name }, wxColourProperty(label, name) + MOPGProperty{ name }, + wxColourProperty(label, name) { } @@ -999,7 +1014,8 @@ void MOPGColourProperty::applyValue() // MOPGTextureProperty class constructor // ----------------------------------------------------------------------------- MOPGTextureProperty::MOPGTextureProperty(TextureType textype, const wxString& label, const wxString& name) : - MOPGStringProperty(label, name), textype_{ textype } + MOPGStringProperty(label, name), + textype_{ textype } { // Set to text+button editor SetEditor(wxPGEditor_TextCtrlAndButton); @@ -1076,7 +1092,8 @@ bool MOPGTextureProperty::OnEvent(wxPropertyGrid* propgrid, wxWindow* window, wx // MOPGSPACTriggerProperty class constructor // ----------------------------------------------------------------------------- MOPGSPACTriggerProperty::MOPGSPACTriggerProperty(const wxString& label, const wxString& name) : - MOPGProperty{ name }, wxEnumProperty(label, name) + MOPGProperty{ name }, + wxEnumProperty(label, name) { // Set to combo box editor SetEditor(wxPGEditor_ComboBox); @@ -1166,7 +1183,8 @@ void MOPGSPACTriggerProperty::applyValue() // MOPGTagProperty class constructor // ----------------------------------------------------------------------------- MOPGTagProperty::MOPGTagProperty(IdType id_type, const wxString& label, const wxString& name) : - MOPGIntProperty(label, name), id_type_{ id_type } + MOPGIntProperty(label, name), + id_type_{ id_type } { // Set to text+button editor SetEditor(wxPGEditor_TextCtrlAndButton); diff --git a/src/MapEditor/UI/PropsPanel/MOPGProperty.h b/src/MapEditor/UI/PropsPanel/MOPGProperty.h index 3d0356a02..e8e2018eb 100644 --- a/src/MapEditor/UI/PropsPanel/MOPGProperty.h +++ b/src/MapEditor/UI/PropsPanel/MOPGProperty.h @@ -1,14 +1,14 @@ #pragma once -#include "Game/Args.h" #include "MapEditor/MapEditor.h" namespace slade { namespace game { + struct ArgSpec; class UDMFProperty; -} +} // namespace game class MapObject; class MapObjectPropsPanel; diff --git a/src/MapEditor/UI/PropsPanel/MapObjectPropsPanel.cpp b/src/MapEditor/UI/PropsPanel/MapObjectPropsPanel.cpp index 38b0a3bfb..502a157de 100644 --- a/src/MapEditor/UI/PropsPanel/MapObjectPropsPanel.cpp +++ b/src/MapEditor/UI/PropsPanel/MapObjectPropsPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: https://slade.mancubus.net @@ -33,6 +33,8 @@ #include "Main.h" #include "MapObjectPropsPanel.h" #include "Game/Configuration.h" +#include "Game/UDMFProperty.h" +#include "General/UI.h" #include "MOPGProperty.h" #include "MapEditor/MapEditContext.h" #include "MapEditor/UI/MapEditorWindow.h" @@ -63,8 +65,11 @@ CVAR(Bool, mobj_props_auto_apply, false, CVar::Flag::Save) // MapObjectPropsPanel class constructor // ----------------------------------------------------------------------------- MapObjectPropsPanel::MapObjectPropsPanel(wxWindow* parent, bool no_apply) : - PropsPanelBase{ parent }, no_apply_{ no_apply } + PropsPanelBase{ parent }, + no_apply_{ no_apply } { + namespace wx = wxutil; + // Setup sizer wxSizer* sizer = new wxBoxSizer(wxVERTICAL); SetSizer(sizer); @@ -72,11 +77,11 @@ MapObjectPropsPanel::MapObjectPropsPanel(wxWindow* parent, bool no_apply) : // Add item label cb_show_all_ = new wxCheckBox(this, -1, "Show All"); cb_show_all_->SetValue(mobj_props_show_all); - sizer->Add(cb_show_all_, 0, wxEXPAND | wxALL, ui::pad()); + sizer->Add(cb_show_all_, wx::sfWithBorder().Expand()); // Add tabs stc_sections_ = STabCtrl::createControl(this); - sizer->Add(stc_sections_, 1, wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, ui::pad()); + sizer->Add(stc_sections_, wx::sfWithBorder(1, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); const auto& inactiveTextColour = wxSystemSettings::GetColour(wxSYS_COLOUR_INACTIVECAPTIONTEXT); @@ -99,20 +104,20 @@ MapObjectPropsPanel::MapObjectPropsPanel(wxWindow* parent, bool no_apply) : // Add buttons auto hbox = new wxBoxSizer(wxHORIZONTAL); - sizer->Add(hbox, 0, wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, ui::pad()); + sizer->Add(hbox, wx::sfWithBorder(0, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); // Add button btn_add_ = new SIconButton(this, "plus", "Add Property"); - hbox->Add(btn_add_, 0, wxEXPAND | wxRIGHT, ui::pad()); + hbox->Add(btn_add_, wx::sfWithBorder(0, wxRIGHT).Expand()); hbox->AddStretchSpacer(1); // Reset button btn_reset_ = new SIconButton(this, "close", "Discard Changes"); - hbox->Add(btn_reset_, 0, wxEXPAND | wxRIGHT, ui::pad()); + hbox->Add(btn_reset_, wx::sfWithBorder(0, wxRIGHT).Expand()); // Apply button btn_apply_ = new SIconButton(this, "tick", "Apply Changes"); - hbox->Add(btn_apply_, 0, wxEXPAND); + hbox->Add(btn_apply_, wxSizerFlags().Expand()); wxPGCell cell; cell.SetText(""); @@ -157,7 +162,7 @@ bool MapObjectPropsPanel::showAll() const // property [propname] // ----------------------------------------------------------------------------- MOPGProperty* MapObjectPropsPanel::addBoolProperty( - wxPGProperty* group, + const wxPGProperty* group, const wxString& label, const wxString& propname, bool readonly, @@ -188,7 +193,7 @@ MOPGProperty* MapObjectPropsPanel::addBoolProperty( // property [propname] // ----------------------------------------------------------------------------- MOPGProperty* MapObjectPropsPanel::addIntProperty( - wxPGProperty* group, + const wxPGProperty* group, const wxString& label, const wxString& propname, bool readonly, @@ -219,7 +224,7 @@ MOPGProperty* MapObjectPropsPanel::addIntProperty( // [propname] // ----------------------------------------------------------------------------- MOPGProperty* MapObjectPropsPanel::addFloatProperty( - wxPGProperty* group, + const wxPGProperty* group, const wxString& label, const wxString& propname, bool readonly, @@ -250,7 +255,7 @@ MOPGProperty* MapObjectPropsPanel::addFloatProperty( // property [propname] // ----------------------------------------------------------------------------- MOPGProperty* MapObjectPropsPanel::addStringProperty( - wxPGProperty* group, + const wxPGProperty* group, const wxString& label, const wxString& propname, bool readonly, @@ -281,7 +286,7 @@ MOPGProperty* MapObjectPropsPanel::addStringProperty( // property [propname] // ----------------------------------------------------------------------------- MOPGProperty* MapObjectPropsPanel::addLineFlagProperty( - wxPGProperty* group, + const wxPGProperty* group, const wxString& label, const wxString& propname, int index, @@ -313,7 +318,7 @@ MOPGProperty* MapObjectPropsPanel::addLineFlagProperty( // property [propname] // ----------------------------------------------------------------------------- MOPGProperty* MapObjectPropsPanel::addThingFlagProperty( - wxPGProperty* group, + const wxPGProperty* group, const wxString& label, const wxString& propname, int index, @@ -345,7 +350,7 @@ MOPGProperty* MapObjectPropsPanel::addThingFlagProperty( // property [propname] // ----------------------------------------------------------------------------- MOPGProperty* MapObjectPropsPanel::addTextureProperty( - wxPGProperty* group, + const wxPGProperty* group, const wxString& label, const wxString& propname, mapeditor::TextureType textype, @@ -996,10 +1001,10 @@ void MapObjectPropsPanel::openObjects(vector& objects) // Add property switch (property::valueType(prop.value)) { - case property::ValueType::Bool: addBoolProperty(group_custom_, prop.name, prop.name); break; - case property::ValueType::Int: addIntProperty(group_custom_, prop.name, prop.name); break; + case property::ValueType::Bool: addBoolProperty(group_custom_, prop.name, prop.name); break; + case property::ValueType::Int: addIntProperty(group_custom_, prop.name, prop.name); break; case property::ValueType::Float: addFloatProperty(group_custom_, prop.name, prop.name); break; - default: addStringProperty(group_custom_, prop.name, prop.name); break; + default: addStringProperty(group_custom_, prop.name, prop.name); break; } } } @@ -1063,7 +1068,7 @@ void MapObjectPropsPanel::updateArgs(MOPGIntWithArgsProperty* source) { if (prop->type() == MOPGProperty::Type::ThingType || prop->type() == MOPGProperty::Type::ActionSpecial) { - prop_with_args = (MOPGIntWithArgsProperty*)prop; + prop_with_args = static_cast(prop); if (!prop_with_args->IsValueUnspecified() && prop_with_args->GetValue().GetInteger() != 0 && prop_with_args->hasArgs()) @@ -1128,6 +1133,8 @@ void MapObjectPropsPanel::clearGrid() // // ----------------------------------------------------------------------------- +// ReSharper disable CppMemberFunctionMayBeConst +// ReSharper disable CppParameterMayBeConstPtrOrRef // ----------------------------------------------------------------------------- // Called when the apply button is clicked @@ -1188,7 +1195,7 @@ void MapObjectPropsPanel::onBtnAdd(wxCommandEvent& e) auto msizer = new wxBoxSizer(wxVERTICAL); dlg.SetSizer(msizer); auto sizer = new wxGridBagSizer(ui::pad(), ui::pad()); - msizer->Add(sizer, 1, wxEXPAND | wxALL, ui::padLarge()); + msizer->Add(sizer, wxutil::sfWithLargeBorder(1).Expand()); // Name auto text_name = new wxTextCtrl(&dlg, -1, ""); diff --git a/src/MapEditor/UI/PropsPanel/MapObjectPropsPanel.h b/src/MapEditor/UI/PropsPanel/MapObjectPropsPanel.h index 1b95920ff..cac63dc48 100644 --- a/src/MapEditor/UI/PropsPanel/MapObjectPropsPanel.h +++ b/src/MapEditor/UI/PropsPanel/MapObjectPropsPanel.h @@ -1,6 +1,5 @@ #pragma once -#include "MOPGProperty.h" #include "PropsPanelBase.h" #include "SLADEMap/MapObject/MapObject.h" #include "UI/Controls/STabCtrl.h" @@ -10,17 +9,23 @@ class wxPGProperty; namespace slade { +class MOPGProperty; +class MOPGIntWithArgsProperty; + +namespace mapeditor +{ + enum class TextureType; +} namespace game { class UDMFProperty; } -class MOPGProperty; class MapObjectPropsPanel : public PropsPanelBase { public: MapObjectPropsPanel(wxWindow* parent, bool no_apply = false); - ~MapObjectPropsPanel() {} + ~MapObjectPropsPanel() override = default; vector& objects() { return objects_; } bool showAll() const; @@ -32,9 +37,9 @@ class MapObjectPropsPanel : public PropsPanelBase void clearGrid(); void hideFlags(bool hide) { hide_flags_ = hide; } void hideTriggers(bool hide) { hide_triggers_ = hide; } - void hideProperty(wxString property) { hide_props_.push_back(property); } + void hideProperty(const wxString& property) { hide_props_.push_back(property); } void clearHiddenProperties() { hide_props_.clear(); } - bool propHidden(wxString property) { return VECTOR_EXISTS(hide_props_, property); } + bool propHidden(const wxString& property) { return VECTOR_EXISTS(hide_props_, property); } private: TabControl* stc_sections_ = nullptr; @@ -43,7 +48,6 @@ class MapObjectPropsPanel : public PropsPanelBase wxPropertyGrid* pg_props_side2_ = nullptr; MapObject::Type last_type_ = MapObject::Type::Object; wxString last_config_; - wxStaticText* label_item_ = nullptr; vector properties_; wxPGProperty* args_[5] = {}; wxButton* btn_reset_ = nullptr; @@ -60,35 +64,35 @@ class MapObjectPropsPanel : public PropsPanelBase vector hide_props_; MOPGProperty* addBoolProperty( - wxPGProperty* group, + const wxPGProperty* group, const wxString& label, const wxString& propname, bool readonly = false, wxPropertyGrid* grid = nullptr, game::UDMFProperty* udmf_prop = nullptr); MOPGProperty* addIntProperty( - wxPGProperty* group, + const wxPGProperty* group, const wxString& label, const wxString& propname, bool readonly = false, wxPropertyGrid* grid = nullptr, game::UDMFProperty* udmf_prop = nullptr); MOPGProperty* addFloatProperty( - wxPGProperty* group, + const wxPGProperty* group, const wxString& label, const wxString& propname, bool readonly = false, wxPropertyGrid* grid = nullptr, game::UDMFProperty* udmf_prop = nullptr); MOPGProperty* addStringProperty( - wxPGProperty* group, + const wxPGProperty* group, const wxString& label, const wxString& propname, bool readonly = false, wxPropertyGrid* grid = nullptr, game::UDMFProperty* udmf_prop = nullptr); MOPGProperty* addLineFlagProperty( - wxPGProperty* group, + const wxPGProperty* group, const wxString& label, const wxString& propname, int index, @@ -96,7 +100,7 @@ class MapObjectPropsPanel : public PropsPanelBase wxPropertyGrid* grid = nullptr, game::UDMFProperty* udmf_prop = nullptr); MOPGProperty* addThingFlagProperty( - wxPGProperty* group, + const wxPGProperty* group, const wxString& label, const wxString& propname, int index, @@ -104,7 +108,7 @@ class MapObjectPropsPanel : public PropsPanelBase wxPropertyGrid* grid = nullptr, game::UDMFProperty* udmf_prop = nullptr); MOPGProperty* addTextureProperty( - wxPGProperty* group, + const wxPGProperty* group, const wxString& label, const wxString& propname, mapeditor::TextureType textype, diff --git a/src/MapEditor/UI/PropsPanel/PropsPanelBase.h b/src/MapEditor/UI/PropsPanel/PropsPanelBase.h index 4c1fbc5b0..e6855ab19 100644 --- a/src/MapEditor/UI/PropsPanel/PropsPanelBase.h +++ b/src/MapEditor/UI/PropsPanel/PropsPanelBase.h @@ -8,7 +8,7 @@ class PropsPanelBase : public wxPanel { public: PropsPanelBase(wxWindow* parent) : wxPanel(parent, -1) {} - virtual ~PropsPanelBase() = default; + ~PropsPanelBase() override = default; virtual void openObjects(vector& objects) {} virtual void applyChanges() {} diff --git a/src/MapEditor/UI/PropsPanel/SectorPropsPanel.cpp b/src/MapEditor/UI/PropsPanel/SectorPropsPanel.cpp index c0db2ac1c..9d50d0b11 100644 --- a/src/MapEditor/UI/PropsPanel/SectorPropsPanel.cpp +++ b/src/MapEditor/UI/PropsPanel/SectorPropsPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -32,6 +32,7 @@ #include "Main.h" #include "SectorPropsPanel.h" #include "Game/Configuration.h" +#include "General/UI.h" #include "MapEditor/MapEditContext.h" #include "MapEditor/MapEditor.h" #include "MapEditor/MapTextureManager.h" @@ -39,7 +40,12 @@ #include "MapEditor/UI/Dialogs/SectorSpecialDialog.h" #include "MapObjectPropsPanel.h" #include "OpenGL/Drawing.h" +#include "OpenGL/GLTexture.h" +#include "OpenGL/OpenGL.h" #include "SLADEMap/MapObject/MapObject.h" +#include "SLADEMap/MapObject/MapSector.h" +#include "SLADEMap/MapObjectList/SectorList.h" +#include "SLADEMap/SLADEMap.h" #include "UI/Controls/NumberTextCtrl.h" #include "UI/Controls/STabCtrl.h" #include "UI/WxUtils.h" @@ -49,173 +55,163 @@ using namespace slade; // ----------------------------------------------------------------------------- -// FlatTexCanvas Class Functions +// FlatTexCanvas Class // // A simple opengl canvas to display a texture // (will have more advanced functionality later) // ----------------------------------------------------------------------------- +class slade::FlatTexCanvas : public OGLCanvas +{ +public: + FlatTexCanvas(wxWindow* parent) : OGLCanvas(parent, -1) + { + // Init variables + wxWindow::SetWindowStyleFlag(wxBORDER_SIMPLE); + SetInitialSize(wxutil::scaledSize(136, 136)); + } + ~FlatTexCanvas() override = default; -// ----------------------------------------------------------------------------- -// FlatTexCanvas class constructor -// ----------------------------------------------------------------------------- -FlatTexCanvas::FlatTexCanvas(wxWindow* parent) : OGLCanvas(parent, -1) -{ - // Init variables - wxWindow::SetWindowStyleFlag(wxBORDER_SIMPLE); - SetInitialSize(wxutil::scaledSize(136, 136)); -} + wxString texName() const { return texname_; } -// ----------------------------------------------------------------------------- -// Sets the texture to display -// ----------------------------------------------------------------------------- -void FlatTexCanvas::setTexture(const wxString& tex) -{ - texname_ = tex; - if (tex.empty() || tex == "-") - texture_ = 0; - else - texture_ = mapeditor::textureManager() - .flat(tex.ToStdString(), game::configuration().featureSupported(game::Feature::MixTexFlats)) - .gl_id; + // Sets the texture to display + void setTexture(const wxString& tex) + { + texname_ = tex; + if (tex.empty() || tex == "-") + texture_ = 0; + else + texture_ = mapeditor::textureManager() + .flat(tex.ToStdString(), game::configuration().featureSupported(game::Feature::MixTexFlats)) + .gl_id; + + Refresh(); + } - Refresh(); -} + // Draws the canvas content + void draw() override + { + // Setup the viewport + const wxSize size = GetSize() * GetContentScaleFactor(); + glViewport(0, 0, size.x, size.y); -// ----------------------------------------------------------------------------- -// Draws the canvas content -// ----------------------------------------------------------------------------- -void FlatTexCanvas::draw() -{ - // Setup the viewport - const wxSize size = GetSize() * GetContentScaleFactor(); - glViewport(0, 0, size.x, size.y); + // Setup the screen projection + glMatrixMode(GL_PROJECTION); + glLoadIdentity(); + glOrtho(0, size.x, size.y, 0, -1, 1); - // Setup the screen projection - glMatrixMode(GL_PROJECTION); - glLoadIdentity(); - glOrtho(0, size.x, size.y, 0, -1, 1); + glMatrixMode(GL_MODELVIEW); + glLoadIdentity(); - glMatrixMode(GL_MODELVIEW); - glLoadIdentity(); + // Clear + glClearColor(0.0f, 0.0f, 0.0f, 1.0f); + glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); - // Clear - glClearColor(0.0f, 0.0f, 0.0f, 1.0f); - glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); + // Translate to inside of pixel (otherwise inaccuracies can occur on certain gl implementations) + if (gl::accuracyTweak()) + glTranslatef(0.375f, 0.375f, 0); - // Translate to inside of pixel (otherwise inaccuracies can occur on certain gl implementations) - if (gl::accuracyTweak()) - glTranslatef(0.375f, 0.375f, 0); + // Draw background + drawCheckeredBackground(); - // Draw background - drawCheckeredBackground(); + // Draw texture + if (texture_ && texture_ != gl::Texture::missingTexture()) + { + glEnable(GL_TEXTURE_2D); + drawing::drawTextureWithin(texture_, 0, 0, size.x, size.y, 0, 100.0); + } + else if (texture_ == gl::Texture::missingTexture()) + { + // Draw unknown icon + auto tex = mapeditor::textureManager().editorImage("thing/unknown").gl_id; + glEnable(GL_TEXTURE_2D); + gl::setColour(180, 0, 0); + drawing::drawTextureWithin(tex, 0, 0, size.x, size.y, 0, 0.25); + } - // Draw texture - if (texture_ && texture_ != gl::Texture::missingTexture()) - { - glEnable(GL_TEXTURE_2D); - drawing::drawTextureWithin(texture_, 0, 0, size.x, size.y, 0, 100.0); - } - else if (texture_ == gl::Texture::missingTexture()) - { - // Draw unknown icon - auto tex = mapeditor::textureManager().editorImage("thing/unknown").gl_id; - glEnable(GL_TEXTURE_2D); - gl::setColour(180, 0, 0); - drawing::drawTextureWithin(tex, 0, 0, size.x, size.y, 0, 0.25); + // Swap buffers (ie show what was drawn) + SwapBuffers(); } - // Swap buffers (ie show what was drawn) - SwapBuffers(); -} +private: + unsigned texture_ = 0; + wxString texname_; +}; // ----------------------------------------------------------------------------- -// FlatComboBox Class Functions +// FlatComboBox Class // // A custom combo box that will show a list of flats matching the current text // in the control (eg. 'FLAT' will list all flats beginning with FLAT) // ----------------------------------------------------------------------------- - - -// ----------------------------------------------------------------------------- -// FlatComboBox class constructor -// ----------------------------------------------------------------------------- -FlatComboBox::FlatComboBox(wxWindow* parent) : wxComboBox(parent, -1) +class slade::FlatComboBox : public wxComboBox { - // Init - wxArrayString list; - list.Add("-"); - - // Bind events - Bind(wxEVT_COMBOBOX_DROPDOWN, &FlatComboBox::onDropDown, this); - Bind(wxEVT_COMBOBOX_CLOSEUP, &FlatComboBox::onCloseUp, this); - Bind(wxEVT_KEY_DOWN, &FlatComboBox::onKeyDown, this); +public: + FlatComboBox(wxWindow* parent) : wxComboBox(parent, -1) + { + // Init + wxArrayString list; + list.Add("-"); - Set(list); -} + // Bind events + Bind(wxEVT_COMBOBOX_DROPDOWN, &FlatComboBox::onDropDown, this); + Bind(wxEVT_COMBOBOX_CLOSEUP, &FlatComboBox::onCloseUp, this); + Bind(wxEVT_KEY_DOWN, &FlatComboBox::onKeyDown, this); + Set(list); + } -// ----------------------------------------------------------------------------- -// -// FlatComboBox Class Events -// -// ----------------------------------------------------------------------------- + ~FlatComboBox() override = default; +private: + bool list_down_ = false; -// ----------------------------------------------------------------------------- -// Called when the dropdown list is expanded -// ----------------------------------------------------------------------------- -void FlatComboBox::onDropDown(wxCommandEvent& e) -{ - // Get current value - wxString text = GetValue().Upper(); - - // Populate dropdown with matching flat names - auto& textures = mapeditor::textureManager().allFlatsInfo(); - wxArrayString list; - list.Add("-"); - for (auto& texture : textures) + // Called when the dropdown list is expanded + void onDropDown(wxCommandEvent& e) { - if (strutil::startsWith(texture.short_name, text.ToStdString())) - { - list.Add(texture.short_name); - } - if (game::configuration().featureSupported(game::Feature::LongNames)) + // Get current value + wxString text = GetValue().Upper(); + + // Populate dropdown with matching flat names + auto& textures = mapeditor::textureManager().allFlatsInfo(); + wxArrayString list; + list.Add("-"); + for (auto& texture : textures) { - if (strutil::startsWith(texture.long_name, text.ToStdString())) + if (strutil::startsWith(texture.short_name, text.ToStdString())) { - list.Add(texture.long_name); + list.Add(texture.short_name); + } + if (game::configuration().featureSupported(game::Feature::LongNames)) + { + if (strutil::startsWith(texture.long_name, text.ToStdString())) + { + list.Add(texture.long_name); + } } } - } - Set(list); // Why does this clear the text box also? - SetValue(text); + Set(list); // Why does this clear the text box also? + SetValue(text); - e.Skip(); -} + e.Skip(); + } -// ----------------------------------------------------------------------------- -// Called when the dropdown list is closed -// ----------------------------------------------------------------------------- -void FlatComboBox::onCloseUp(wxCommandEvent& e) -{ - list_down_ = false; -} + // Called when the dropdown list is closed + void onCloseUp(wxCommandEvent& e) { list_down_ = false; } -// ----------------------------------------------------------------------------- -// Called when a key is pressed within the control -// ----------------------------------------------------------------------------- -void FlatComboBox::onKeyDown(wxKeyEvent& e) -{ - if (e.GetKeyCode() == WXK_DOWN && !list_down_) + // Called when a key is pressed within the control + void onKeyDown(wxKeyEvent& e) { - list_down_ = true; - Popup(); + if (e.GetKeyCode() == WXK_DOWN && !list_down_) + { + list_down_ = true; + Popup(); + } + else + e.Skip(); } - else - e.Skip(); -} +}; // ----------------------------------------------------------------------------- @@ -236,7 +232,7 @@ SectorPropsPanel::SectorPropsPanel(wxWindow* parent) : PropsPanelBase(parent) // Tabs stc_tabs_ = STabCtrl::createControl(this); - sizer->Add(stc_tabs_, 1, wxEXPAND); + sizer->Add(stc_tabs_, wxSizerFlags(1).Expand()); // General tab stc_tabs_->AddPage(setupGeneralPanel(), "General"); @@ -274,6 +270,8 @@ SectorPropsPanel::SectorPropsPanel(wxWindow* parent) : PropsPanelBase(parent) // ----------------------------------------------------------------------------- wxPanel* SectorPropsPanel::setupGeneralPanel() { + namespace wx = wxutil; + // Create panel auto panel = new wxPanel(stc_tabs_); @@ -283,14 +281,14 @@ wxPanel* SectorPropsPanel::setupGeneralPanel() // --- Floor --- auto m_hbox = new wxBoxSizer(wxHORIZONTAL); - sizer->Add(m_hbox, 0, wxEXPAND | wxALL, ui::pad()); + sizer->Add(m_hbox, wx::sfWithBorder().Expand()); auto frame = new wxStaticBox(panel, -1, "Floor"); auto framesizer = new wxStaticBoxSizer(frame, wxVERTICAL); - m_hbox->Add(framesizer, 1, wxALIGN_CENTER | wxRIGHT, ui::pad()); + m_hbox->Add(framesizer, wx::sfWithBorder(1, wxRIGHT).Center()); // Texture auto gb_sizer = new wxGridBagSizer(ui::pad(), ui::pad()); - framesizer->Add(gb_sizer, 1, wxEXPAND | wxALL, ui::pad()); + framesizer->Add(gb_sizer, wx::sfWithBorder(1).Expand()); gb_sizer->Add(gfx_floor_ = new FlatTexCanvas(panel), { 0, 0 }, { 1, 2 }, wxALIGN_CENTER); gb_sizer->Add(new wxStaticText(panel, -1, "Texture:"), { 1, 0 }, { 1, 1 }, wxALIGN_CENTER_VERTICAL); gb_sizer->Add(fcb_floor_ = new FlatComboBox(panel), { 1, 1 }, { 1, 1 }, wxEXPAND); @@ -305,11 +303,11 @@ wxPanel* SectorPropsPanel::setupGeneralPanel() // --- Ceiling --- frame = new wxStaticBox(panel, -1, "Ceiling"); framesizer = new wxStaticBoxSizer(frame, wxVERTICAL); - m_hbox->Add(framesizer, 1, wxALIGN_CENTER); + m_hbox->Add(framesizer, wxSizerFlags(1).Center()); // Texture gb_sizer = new wxGridBagSizer(ui::pad(), ui::pad()); - framesizer->Add(gb_sizer, 1, wxEXPAND | wxALL, ui::pad()); + framesizer->Add(gb_sizer, wx::sfWithBorder(1).Expand()); gb_sizer->Add(gfx_ceiling_ = new FlatTexCanvas(panel), { 0, 0 }, { 1, 2 }, wxALIGN_CENTER); gb_sizer->Add(new wxStaticText(panel, -1, "Texture:"), { 1, 0 }, { 1, 1 }, wxALIGN_CENTER_VERTICAL); gb_sizer->Add(fcb_ceiling_ = new FlatComboBox(panel), { 1, 1 }, { 1, 1 }, wxEXPAND); @@ -324,9 +322,9 @@ wxPanel* SectorPropsPanel::setupGeneralPanel() // -- General --- frame = new wxStaticBox(panel, -1, "General"); framesizer = new wxStaticBoxSizer(frame, wxVERTICAL); - sizer->Add(framesizer, 0, wxEXPAND | wxALL, ui::pad()); + sizer->Add(framesizer, wx::sfWithBorder().Expand()); gb_sizer = new wxGridBagSizer(ui::pad(), ui::pad()); - framesizer->Add(gb_sizer, 1, wxEXPAND | wxALL, ui::pad()); + framesizer->Add(gb_sizer, wx::sfWithBorder(1).Expand()); // Light level gb_sizer->Add(new wxStaticText(panel, -1, "Light Level:"), { 0, 0 }, { 1, 1 }, wxALIGN_CENTER_VERTICAL); @@ -355,14 +353,12 @@ wxPanel* SectorPropsPanel::setupSpecialPanel() panel->SetSizer(sizer); // Add special panel - sizer->Add(panel_special_ = new SectorSpecialPanel(panel), 1, wxEXPAND | wxALL, ui::pad()); + sizer->Add(panel_special_ = new SectorSpecialPanel(panel), wxutil::sfWithBorder(1).Expand()); // Add override checkbox sizer->Add( cb_override_special_ = new wxCheckBox(panel, -1, "Override Special"), - 0, - wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, - ui::pad()); + wxutil::sfWithBorder(0, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); cb_override_special_->SetToolTip( "Differing specials detected, tick this to set the special for all selected sectors"); @@ -483,6 +479,8 @@ void SectorPropsPanel::applyChanges() // // ----------------------------------------------------------------------------- +// ReSharper disable CppMemberFunctionMayBeConst +// ReSharper disable CppParameterMayBeConstPtrOrRef // ----------------------------------------------------------------------------- // Called when a texture name is changed diff --git a/src/MapEditor/UI/PropsPanel/SectorPropsPanel.h b/src/MapEditor/UI/PropsPanel/SectorPropsPanel.h index f83474adb..4c1dc881e 100644 --- a/src/MapEditor/UI/PropsPanel/SectorPropsPanel.h +++ b/src/MapEditor/UI/PropsPanel/SectorPropsPanel.h @@ -1,7 +1,6 @@ #pragma once #include "PropsPanelBase.h" -#include "UI/Canvas/OGLCanvas.h" #include "UI/Controls/STabCtrl.h" namespace slade @@ -10,42 +9,14 @@ class SectorSpecialPanel; class MapObject; class MapObjectPropsPanel; class NumberTextCtrl; - -class FlatTexCanvas : public OGLCanvas -{ -public: - FlatTexCanvas(wxWindow* parent); - ~FlatTexCanvas() = default; - - wxString texName() const { return texname_; } - void setTexture(const wxString& texture); - void draw() override; - -private: - unsigned texture_ = 0; - wxString texname_; -}; - -class FlatComboBox : public wxComboBox -{ -public: - FlatComboBox(wxWindow* parent); - ~FlatComboBox() = default; - -private: - bool list_down_ = false; - - void onDropDown(wxCommandEvent& e); - void onCloseUp(wxCommandEvent& e); - void onKeyDown(wxKeyEvent& e); -}; - +class FlatTexCanvas; +class FlatComboBox; class SectorPropsPanel : public PropsPanelBase { public: SectorPropsPanel(wxWindow* parent); - ~SectorPropsPanel() = default; + ~SectorPropsPanel() override = default; void openObjects(vector& objects) override; void applyChanges() override; diff --git a/src/MapEditor/UI/PropsPanel/SidePropsPanel.cpp b/src/MapEditor/UI/PropsPanel/SidePropsPanel.cpp index 84131f3fd..13be8dfb1 100644 --- a/src/MapEditor/UI/PropsPanel/SidePropsPanel.cpp +++ b/src/MapEditor/UI/PropsPanel/SidePropsPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -32,13 +32,15 @@ #include "Main.h" #include "SidePropsPanel.h" #include "Game/Configuration.h" +#include "General/UI.h" #include "MapEditor/MapEditContext.h" #include "MapEditor/MapEditor.h" #include "MapEditor/MapTextureManager.h" #include "MapEditor/UI/Dialogs/MapTextureBrowser.h" #include "OpenGL/Drawing.h" #include "OpenGL/GLTexture.h" -#include "SLADEMap/SLADEMap.h" +#include "OpenGL/OpenGL.h" +#include "SLADEMap/MapObject/MapSide.h" #include "UI/Controls/NumberTextCtrl.h" #include "UI/WxUtils.h" #include "Utility/StringUtils.h" @@ -47,175 +49,169 @@ using namespace slade; // ----------------------------------------------------------------------------- -// SideTexCanvas Class Functions +// SideTexCanvas Class // // A simple opengl canvas to display a texture // (will have more advanced functionality later) // ----------------------------------------------------------------------------- - -// ----------------------------------------------------------------------------- -// SideTexCanvas class constructor -// ----------------------------------------------------------------------------- -SideTexCanvas::SideTexCanvas(wxWindow* parent) : OGLCanvas(parent, -1) +class slade::SideTexCanvas : public OGLCanvas { - wxWindow::SetWindowStyleFlag(wxBORDER_SIMPLE); - SetInitialSize(wxutil::scaledSize(136, 136)); -} +public: + SideTexCanvas(wxWindow* parent) : OGLCanvas(parent, -1) + { + wxWindow::SetWindowStyleFlag(wxBORDER_SIMPLE); + SetInitialSize(wxutil::scaledSize(136, 136)); + } -// ----------------------------------------------------------------------------- -// Sets the texture to display -// ----------------------------------------------------------------------------- -void SideTexCanvas::setTexture(const wxString& tex) -{ - texname_ = tex; - if (tex.empty() || tex == "-") - texture_ = 0; - else - texture_ = mapeditor::textureManager() - .texture(tex.ToStdString(), game::configuration().featureSupported(game::Feature::MixTexFlats)) - .gl_id; - - Refresh(); -} + ~SideTexCanvas() override = default; -// ----------------------------------------------------------------------------- -// Draws the canvas content -// ----------------------------------------------------------------------------- -void SideTexCanvas::draw() -{ - // Setup the viewport - const wxSize size = GetSize() * GetContentScaleFactor(); - glViewport(0, 0, size.x, size.y); + wxString texName() const { return texname_; } + + // Sets the texture to display + void setTexture(const wxString& tex) + { + texname_ = tex; + if (tex.empty() || tex == "-") + texture_ = 0; + else + { + auto texture = mapeditor::textureManager().texture( + tex.ToStdString(), game::configuration().featureSupported(game::Feature::MixTexFlats)); + + texture_ = texture.gl_id; + } - // Setup the screen projection - glMatrixMode(GL_PROJECTION); - glLoadIdentity(); - glOrtho(0, size.x, size.y, 0, -1, 1); + Refresh(); + } - glMatrixMode(GL_MODELVIEW); - glLoadIdentity(); + // Draws the canvas content + void draw() override + { + // Setup the viewport + const wxSize size = GetSize() * GetContentScaleFactor(); + glViewport(0, 0, size.x, size.y); - // Clear - glClearColor(0.0f, 0.0f, 0.0f, 1.0f); - glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); + // Setup the screen projection + glMatrixMode(GL_PROJECTION); + glLoadIdentity(); + glOrtho(0, size.x, size.y, 0, -1, 1); - // Translate to inside of pixel (otherwise inaccuracies can occur on certain gl implementations) - if (gl::accuracyTweak()) - glTranslatef(0.375f, 0.375f, 0); + glMatrixMode(GL_MODELVIEW); + glLoadIdentity(); - // Draw background - drawCheckeredBackground(); + // Clear + glClearColor(0.0f, 0.0f, 0.0f, 1.0f); + glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); - // Draw texture - if (texture_ && texture_ != gl::Texture::missingTexture()) - { - glEnable(GL_TEXTURE_2D); - drawing::drawTextureWithin(texture_, 0, 0, size.x, size.y, 0); - } - else if (texture_ == gl::Texture::missingTexture()) - { - // Draw unknown icon - auto tex = mapeditor::textureManager().editorImage("thing/unknown").gl_id; - glEnable(GL_TEXTURE_2D); - gl::setColour(180, 0, 0); - drawing::drawTextureWithin(tex, 0, 0, size.x, size.y, 0, 0.25); + // Translate to inside of pixel (otherwise inaccuracies can occur on certain gl implementations) + if (gl::accuracyTweak()) + glTranslatef(0.375f, 0.375f, 0); + + // Draw background + drawCheckeredBackground(); + + // Draw texture + if (texture_ && texture_ != gl::Texture::missingTexture()) + { + glEnable(GL_TEXTURE_2D); + drawing::drawTextureWithin(texture_, 0, 0, size.x, size.y, 0); + } + else if (texture_ == gl::Texture::missingTexture()) + { + // Draw unknown icon + auto tex = mapeditor::textureManager().editorImage("thing/unknown").gl_id; + glEnable(GL_TEXTURE_2D); + gl::setColour(180, 0, 0); + drawing::drawTextureWithin(tex, 0, 0, size.x, size.y, 0, 0.25); + } + + // Swap buffers (ie show what was drawn) + SwapBuffers(); } - // Swap buffers (ie show what was drawn) - SwapBuffers(); -} +private: + unsigned texture_ = 0; + wxString texname_; +}; // ----------------------------------------------------------------------------- -// TextureComboBox Class Functions +// TextureComboBox Class // // A custom combo box that will show a list of textures matching the current // text in the control (eg. 'BIG' will list all textures beginning with BIG). // ----------------------------------------------------------------------------- - - -// ----------------------------------------------------------------------------- -// TextureComboBox class constructor -// ----------------------------------------------------------------------------- -TextureComboBox::TextureComboBox(wxWindow* parent) : wxComboBox(parent, -1) +class slade::TextureComboBox : public wxComboBox { - // Init - SetInitialSize(wxutil::scaledSize(136, -1)); - wxArrayString list; - list.Add("-"); +public: + TextureComboBox(wxWindow* parent) : wxComboBox(parent, -1) + { + // Init + SetInitialSize(wxutil::scaledSize(136, -1)); + wxArrayString list; + list.Add("-"); - // Bind events - Bind(wxEVT_COMBOBOX_DROPDOWN, &TextureComboBox::onDropDown, this); - Bind(wxEVT_COMBOBOX_CLOSEUP, &TextureComboBox::onCloseUp, this); - Bind(wxEVT_KEY_DOWN, &TextureComboBox::onKeyDown, this); + // Bind events + Bind(wxEVT_COMBOBOX_DROPDOWN, &TextureComboBox::onDropDown, this); + Bind(wxEVT_COMBOBOX_CLOSEUP, &TextureComboBox::onCloseUp, this); + Bind(wxEVT_KEY_DOWN, &TextureComboBox::onKeyDown, this); - Set(list); -} + Set(list); + } + ~TextureComboBox() override = default; -// ----------------------------------------------------------------------------- -// -// TextureComboBox Class Events -// -// ----------------------------------------------------------------------------- +private: + bool list_down_ = false; - -// ----------------------------------------------------------------------------- -// Called when the dropdown list is expanded -// ----------------------------------------------------------------------------- -void TextureComboBox::onDropDown(wxCommandEvent& e) -{ - // Get current value - wxString text = GetValue().Upper(); - if (text == "-") - text = ""; - - // Populate dropdown with matching texture names - auto& textures = mapeditor::textureManager().allTexturesInfo(); - wxArrayString list; - list.Add("-"); - for (auto& texture : textures) + // Called when the dropdown list is expanded + void onDropDown(wxCommandEvent& e) { - if (strutil::startsWith(texture.short_name, text.ToStdString())) + // Get current value + wxString text = GetValue().Upper(); + if (text == "-") + text = ""; + + // Populate dropdown with matching texture names + auto& textures = mapeditor::textureManager().allTexturesInfo(); + wxArrayString list; + list.Add("-"); + for (auto& texture : textures) { - list.Add(texture.short_name); - } - if (game::configuration().featureSupported(game::Feature::LongNames)) - { - if (strutil::startsWith(texture.long_name, text.ToStdString())) + if (strutil::startsWith(texture.short_name, text.ToStdString())) + { + list.Add(texture.short_name); + } + if (game::configuration().featureSupported(game::Feature::LongNames)) { - list.Add(texture.long_name); + if (strutil::startsWith(texture.long_name, text.ToStdString())) + { + list.Add(texture.long_name); + } } } - } - Set(list); // Why does this clear the text box also? - SetValue(text); + Set(list); // Why does this clear the text box also? + SetValue(text); - e.Skip(); -} + e.Skip(); + } -// ----------------------------------------------------------------------------- -// Called when the dropdown list is closed -// ----------------------------------------------------------------------------- -void TextureComboBox::onCloseUp(wxCommandEvent& e) -{ - list_down_ = false; -} + // Called when the dropdown list is closed + void onCloseUp(wxCommandEvent& e) { list_down_ = false; } -// ----------------------------------------------------------------------------- -// Called when a key is pressed within the control -// ----------------------------------------------------------------------------- -void TextureComboBox::onKeyDown(wxKeyEvent& e) -{ - if (e.GetKeyCode() == WXK_DOWN && !list_down_) + // Called when a key is pressed within the control + void onKeyDown(wxKeyEvent& e) { - list_down_ = true; - Popup(); + if (e.GetKeyCode() == WXK_DOWN && !list_down_) + { + list_down_ = true; + Popup(); + } + else + e.Skip(); } - else - e.Skip(); -} +}; // ----------------------------------------------------------------------------- @@ -230,6 +226,8 @@ void TextureComboBox::onKeyDown(wxKeyEvent& e) // ----------------------------------------------------------------------------- SidePropsPanel::SidePropsPanel(wxWindow* parent) : wxPanel(parent, -1) { + namespace wx = wxutil; + wxBoxSizer* vbox; // Setup sizer @@ -238,27 +236,26 @@ SidePropsPanel::SidePropsPanel(wxWindow* parent) : wxPanel(parent, -1) // --- Textures --- auto sizer_tex = new wxStaticBoxSizer(wxVERTICAL, this, "Textures"); - sizer->Add(sizer_tex, 0, wxEXPAND); + sizer->Add(sizer_tex, wxSizerFlags().Expand()); auto gb_sizer = new wxGridBagSizer(ui::pad(), ui::pad()); - sizer_tex->Add(gb_sizer, 1, wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, ui::pad()); + sizer_tex->Add(gb_sizer, wx::sfWithBorder(1, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); // Upper - auto pad_min = ui::px(ui::Size::PadMinimum); gb_sizer->Add(vbox = new wxBoxSizer(wxVERTICAL), { 0, 0 }, { 1, 1 }, wxALIGN_CENTER); - vbox->Add(new wxStaticText(this, -1, "Upper:"), 0, wxALIGN_CENTER | wxBOTTOM, pad_min); + vbox->Add(new wxStaticText(this, -1, "Upper:"), wx::sfWithMinBorder(0, wxBOTTOM).Center()); vbox->Add(gfx_upper_ = new SideTexCanvas(this), 1, wxEXPAND); gb_sizer->Add(tcb_upper_ = new TextureComboBox(this), { 1, 0 }, { 1, 1 }, wxALIGN_CENTER); // Middle gb_sizer->Add(vbox = new wxBoxSizer(wxVERTICAL), { 0, 1 }, { 1, 1 }, wxALIGN_CENTER); - vbox->Add(new wxStaticText(this, -1, "Middle:"), 0, wxALIGN_CENTER | wxBOTTOM, pad_min); + vbox->Add(new wxStaticText(this, -1, "Middle:"), wx::sfWithMinBorder(0, wxBOTTOM).Center()); vbox->Add(gfx_middle_ = new SideTexCanvas(this), 1, wxEXPAND); gb_sizer->Add(tcb_middle_ = new TextureComboBox(this), { 1, 1 }, { 1, 1 }, wxALIGN_CENTER); // Lower gb_sizer->Add(vbox = new wxBoxSizer(wxVERTICAL), { 0, 2 }, { 1, 1 }, wxALIGN_CENTER); - vbox->Add(new wxStaticText(this, -1, "Lower:"), 0, wxALIGN_CENTER | wxBOTTOM, pad_min); + vbox->Add(new wxStaticText(this, -1, "Lower:"), wx::sfWithMinBorder(0, wxBOTTOM).Center()); vbox->Add(gfx_lower_ = new SideTexCanvas(this), 1, wxEXPAND); gb_sizer->Add(tcb_lower_ = new TextureComboBox(this), { 1, 2 }, { 1, 1 }, wxALIGN_CENTER); @@ -269,10 +266,10 @@ SidePropsPanel::SidePropsPanel(wxWindow* parent) : wxPanel(parent, -1) // --- Offsets --- - auto layout_offsets = wxutil::layoutVertically( - vector{ wxutil::createLabelHBox(this, "X Offset:", text_offsetx_ = new NumberTextCtrl(this)), - wxutil::createLabelHBox(this, "Y Offset:", text_offsety_ = new NumberTextCtrl(this)) }); - sizer->Add(layout_offsets, 0, wxEXPAND | wxTOP, ui::pad()); + auto layout_offsets = wx::layoutVertically( + vector{ wx::createLabelHBox(this, "X Offset:", text_offsetx_ = new NumberTextCtrl(this)), + wx::createLabelHBox(this, "Y Offset:", text_offsety_ = new NumberTextCtrl(this)) }); + sizer->Add(layout_offsets, wx::sfWithBorder(0, wxTOP).Expand()); // Bind events tcb_upper_->Bind(wxEVT_TEXT, &SidePropsPanel::onTextureChanged, this); @@ -291,7 +288,7 @@ SidePropsPanel::SidePropsPanel(wxWindow* parent) : wxPanel(parent, -1) // ----------------------------------------------------------------------------- // Loads textures and offsets from [sides] // ----------------------------------------------------------------------------- -void SidePropsPanel::openSides(vector& sides) const +void SidePropsPanel::openSides(const vector& sides) const { if (sides.empty()) return; @@ -372,7 +369,7 @@ void SidePropsPanel::openSides(vector& sides) const // ----------------------------------------------------------------------------- // Applies current values to [sides] // ----------------------------------------------------------------------------- -void SidePropsPanel::applyTo(vector& sides) const +void SidePropsPanel::applyTo(const vector& sides) const { // Get values auto tex_upper = tcb_upper_->GetValue().ToStdString(); @@ -410,6 +407,8 @@ void SidePropsPanel::applyTo(vector& sides) const // // ----------------------------------------------------------------------------- +// ReSharper disable CppMemberFunctionMayBeConst +// ReSharper disable CppParameterMayBeConstPtrOrRef // ----------------------------------------------------------------------------- // Called when a texture name is changed diff --git a/src/MapEditor/UI/PropsPanel/SidePropsPanel.h b/src/MapEditor/UI/PropsPanel/SidePropsPanel.h index 654a108d0..ab68cb9cc 100644 --- a/src/MapEditor/UI/PropsPanel/SidePropsPanel.h +++ b/src/MapEditor/UI/PropsPanel/SidePropsPanel.h @@ -1,49 +1,20 @@ #pragma once -#include "UI/Canvas/OGLCanvas.h" - namespace slade { class MapSide; class NumberTextCtrl; - -class SideTexCanvas : public OGLCanvas -{ -public: - SideTexCanvas(wxWindow* parent); - ~SideTexCanvas() = default; - - wxString texName() const { return texname_; } - void setTexture(const wxString& texture); - void draw() override; - -private: - unsigned texture_ = 0; - wxString texname_; -}; - -class TextureComboBox : public wxComboBox -{ -public: - TextureComboBox(wxWindow* parent); - ~TextureComboBox() = default; - -private: - bool list_down_ = false; - - void onDropDown(wxCommandEvent& e); - void onCloseUp(wxCommandEvent& e); - void onKeyDown(wxKeyEvent& e); -}; +class SideTexCanvas; +class TextureComboBox; class SidePropsPanel : public wxPanel { public: SidePropsPanel(wxWindow* parent); - ~SidePropsPanel() = default; + ~SidePropsPanel() override = default; - void openSides(vector& sides) const; - void applyTo(vector& sides) const; + void openSides(const vector& sides) const; + void applyTo(const vector& sides) const; private: SideTexCanvas* gfx_lower_ = nullptr; diff --git a/src/MapEditor/UI/PropsPanel/ThingPropsPanel.cpp b/src/MapEditor/UI/PropsPanel/ThingPropsPanel.cpp index 4529f9476..75aeb4d1e 100644 --- a/src/MapEditor/UI/PropsPanel/ThingPropsPanel.cpp +++ b/src/MapEditor/UI/PropsPanel/ThingPropsPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: https://slade.mancubus.net @@ -32,7 +32,10 @@ #include "Main.h" #include "ThingPropsPanel.h" #include "App.h" +#include "Game/ActionSpecial.h" #include "Game/Configuration.h" +#include "Game/UDMFProperty.h" +#include "General/UI.h" #include "MapEditor/MapEditContext.h" #include "MapEditor/MapEditor.h" #include "MapEditor/MapTextureManager.h" @@ -40,6 +43,10 @@ #include "MapEditor/UI/Dialogs/ThingTypeBrowser.h" #include "MapObjectPropsPanel.h" #include "OpenGL/Drawing.h" +#include "OpenGL/OpenGL.h" +#include "SLADEMap/MapObject/MapThing.h" +#include "SLADEMap/MapObjectList/ThingList.h" +#include "SLADEMap/SLADEMap.h" #include "UI/Controls/NumberTextCtrl.h" #include "UI/Controls/STabCtrl.h" #include "UI/WxUtils.h" @@ -49,318 +56,319 @@ using namespace slade; // ----------------------------------------------------------------------------- -// SpriteTexCanvas Class Functions +// SpriteTexCanvas Class // // A simple opengl canvas to display a thing sprite // ----------------------------------------------------------------------------- - - -// ----------------------------------------------------------------------------- -// SpriteTexCanvas class constructor -// ----------------------------------------------------------------------------- -SpriteTexCanvas::SpriteTexCanvas(wxWindow* parent) : OGLCanvas(parent, -1) +class slade::SpriteTexCanvas : public OGLCanvas { - wxWindow::SetWindowStyleFlag(wxBORDER_SIMPLE); - SetInitialSize(wxutil::scaledSize(128, 128)); -} +public: + SpriteTexCanvas(wxWindow* parent) : OGLCanvas(parent, -1) + { + wxWindow::SetWindowStyleFlag(wxBORDER_SIMPLE); + SetInitialSize(wxutil::scaledSize(128, 128)); + } -// ----------------------------------------------------------------------------- -// Sets the texture to display -// ----------------------------------------------------------------------------- -void SpriteTexCanvas::setSprite(const game::ThingType& type) -{ - texname_ = type.sprite(); - icon_ = false; - colour_ = ColRGBA::WHITE; + ~SpriteTexCanvas() override = default; - // Sprite - texture_ = mapeditor::textureManager().sprite(texname_.ToStdString(), type.translation(), type.palette()).gl_id; + wxString texName() const { return texname_; } - // Icon - if (!texture_) + // Sets the texture to display + void setSprite(const game::ThingType& type) { - texture_ = mapeditor::textureManager().editorImage(fmt::format("thing/{}", type.icon())).gl_id; - colour_ = type.colour(); - icon_ = true; + texname_ = type.sprite(); + icon_ = false; + colour_ = ColRGBA::WHITE; + + // Sprite + texture_ = mapeditor::textureManager().sprite(texname_.ToStdString(), type.translation(), type.palette()).gl_id; + + // Icon + if (!texture_) + { + texture_ = mapeditor::textureManager().editorImage(fmt::format("thing/{}", type.icon())).gl_id; + colour_ = type.colour(); + icon_ = true; + } + + // Unknown + if (!texture_) + { + texture_ = mapeditor::textureManager().editorImage("thing/unknown").gl_id; + icon_ = true; + } + + Refresh(); } - // Unknown - if (!texture_) + // Draws the canvas content + void draw() override { - texture_ = mapeditor::textureManager().editorImage("thing/unknown").gl_id; - icon_ = true; - } + // Setup the viewport + const wxSize size = GetSize() * GetContentScaleFactor(); + glViewport(0, 0, size.x, size.y); - Refresh(); -} + // Setup the screen projection + glMatrixMode(GL_PROJECTION); + glLoadIdentity(); + glOrtho(0, size.x, size.y, 0, -1, 1); -// ----------------------------------------------------------------------------- -// Draws the canvas content -// ----------------------------------------------------------------------------- -void SpriteTexCanvas::draw() -{ - // Setup the viewport - const wxSize size = GetSize() * GetContentScaleFactor(); - glViewport(0, 0, size.x, size.y); - - // Setup the screen projection - glMatrixMode(GL_PROJECTION); - glLoadIdentity(); - glOrtho(0, size.x, size.y, 0, -1, 1); + glMatrixMode(GL_MODELVIEW); + glLoadIdentity(); - glMatrixMode(GL_MODELVIEW); - glLoadIdentity(); + // Clear + glClearColor(0.0f, 0.0f, 0.0f, 1.0f); + glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); - // Clear - glClearColor(0.0f, 0.0f, 0.0f, 1.0f); - glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); + // Translate to inside of pixel (otherwise inaccuracies can occur on certain gl implementations) + if (gl::accuracyTweak()) + glTranslatef(0.375f, 0.375f, 0); - // Translate to inside of pixel (otherwise inaccuracies can occur on certain gl implementations) - if (gl::accuracyTweak()) - glTranslatef(0.375f, 0.375f, 0); + // Draw background + drawCheckeredBackground(); - // Draw background - drawCheckeredBackground(); + // Draw texture + gl::setColour(colour_); + if (texture_ && !icon_) + { + // Sprite + glEnable(GL_TEXTURE_2D); + drawing::drawTextureWithin(texture_, 0, 0, size.x, size.y, 4, 2); + } + else if (texture_ && icon_) + { + // Icon + glEnable(GL_TEXTURE_2D); + drawing::drawTextureWithin(texture_, 0, 0, size.x, size.y, 0, 0.25); + } - // Draw texture - gl::setColour(colour_); - if (texture_ && !icon_) - { - // Sprite - glEnable(GL_TEXTURE_2D); - drawing::drawTextureWithin(texture_, 0, 0, size.x, size.y, 4, 2); - } - else if (texture_ && icon_) - { - // Icon - glEnable(GL_TEXTURE_2D); - drawing::drawTextureWithin(texture_, 0, 0, size.x, size.y, 0, 0.25); + // Swap buffers (ie show what was drawn) + SwapBuffers(); } - // Swap buffers (ie show what was drawn) - SwapBuffers(); -} +private: + unsigned texture_ = 0; + wxString texname_; + ColRGBA colour_ = ColRGBA::WHITE; + bool icon_ = false; +}; // ----------------------------------------------------------------------------- -// ThingDirCanvas Class Functions +// ThingDirCanvas Class // // An OpenGL canvas that shows a direction and circles for each of the 8 // 'standard' directions, clicking within one of the circles will set the // direction // ----------------------------------------------------------------------------- - - -// ----------------------------------------------------------------------------- -// ThingDirCanvas class constructor -// ----------------------------------------------------------------------------- -ThingDirCanvas::ThingDirCanvas(AngleControl* parent) : OGLCanvas(parent, -1, true, 15), parent_{ parent } +class slade::ThingDirCanvas : public OGLCanvas { - // Get system panel background colour - auto bgcolwx = drawing::systemPanelBGColour(); - col_bg_.set(bgcolwx); - - // Get system text colour - auto textcol = wxSystemSettings::GetColour(wxSYS_COLOUR_WINDOWTEXT); - col_fg_.set(textcol); - - // Setup dir points - double rot = 0; - for (int a = 0; a < 8; a++) +public: + ThingDirCanvas(AngleControl* parent) : OGLCanvas(parent, -1, true, 15), parent_{ parent } { - dir_points_.emplace_back(sin(rot), 0 - cos(rot)); - rot -= (3.1415926535897932384626433832795 * 2) / 8.0; - } + // Get system panel background colour + auto bgcolwx = drawing::systemPanelBGColour(); + col_bg_.set(bgcolwx); - // Bind Events - Bind(wxEVT_MOTION, &ThingDirCanvas::onMouseEvent, this); - Bind(wxEVT_LEAVE_WINDOW, &ThingDirCanvas::onMouseEvent, this); - Bind(wxEVT_LEFT_DOWN, &ThingDirCanvas::onMouseEvent, this); + // Get system text colour + auto textcol = wxSystemSettings::GetColour(wxSYS_COLOUR_WINDOWTEXT); + col_fg_.set(textcol); - // Fixed size - auto size = ui::scalePx(128); - SetInitialSize(wxSize(size, size)); - wxWindowBase::SetMaxSize(wxSize(size, size)); -} - -// ----------------------------------------------------------------------------- -// Sets the selected angle point based on [angle] -// ----------------------------------------------------------------------------- -void ThingDirCanvas::setAngle(int angle) -{ - // Clamp angle - while (angle >= 360) - angle -= 360; - while (angle < 0) - angle += 360; - - // Set selected dir point (if any) - if (!dir_points_.empty()) - { - switch (angle) + // Setup dir points + double rot = 0; + for (int a = 0; a < 8; a++) { - case 0: point_sel_ = 6; break; - case 45: point_sel_ = 7; break; - case 90: point_sel_ = 0; break; - case 135: point_sel_ = 1; break; - case 180: point_sel_ = 2; break; - case 225: point_sel_ = 3; break; - case 270: point_sel_ = 4; break; - case 315: point_sel_ = 5; break; - default: point_sel_ = -1; break; + dir_points_.emplace_back(sin(rot), 0 - cos(rot)); + rot -= (3.1415926535897932384626433832795 * 2) / 8.0; } - } - Refresh(); -} + // Bind Events + Bind(wxEVT_MOTION, &ThingDirCanvas::onMouseEvent, this); + Bind(wxEVT_LEAVE_WINDOW, &ThingDirCanvas::onMouseEvent, this); + Bind(wxEVT_LEFT_DOWN, &ThingDirCanvas::onMouseEvent, this); -// ----------------------------------------------------------------------------- -// Draws the control -// ----------------------------------------------------------------------------- -void ThingDirCanvas::draw() -{ - // Setup the viewport - const wxSize size = GetSize() * GetContentScaleFactor(); - glViewport(0, 0, size.x, size.y); - - // Setup the screen projection - glMatrixMode(GL_PROJECTION); - glLoadIdentity(); - glOrtho(-1.2, 1.2, 1.2, -1.2, -1, 1); - - glMatrixMode(GL_MODELVIEW); - glLoadIdentity(); - - // Clear - glClearColor(col_bg_.fr(), col_bg_.fg(), col_bg_.fb(), 1.0f); - glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); - - // Draw angle ring - glDisable(GL_TEXTURE_2D); - glLineWidth(1.5f); - glEnable(GL_LINE_SMOOTH); - ColRGBA col_faded( - col_bg_.r * 0.6 + col_fg_.r * 0.4, col_bg_.g * 0.6 + col_fg_.g * 0.4, col_bg_.b * 0.6 + col_fg_.b * 0.4); - drawing::drawEllipse(Vec2d(0, 0), 1, 1, 48, col_faded); - - // Draw dir points - for (auto dir_point : dir_points_) - { - drawing::drawFilledEllipse(dir_point, 0.12, 0.12, 8, col_bg_); - drawing::drawEllipse(dir_point, 0.12, 0.12, 16, col_fg_); + // Fixed size + auto size = ui::scalePx(128); + SetInitialSize(wxSize(size, size)); + wxWindowBase::SetMaxSize(wxSize(size, size)); } - // Draw angle arrow - glLineWidth(2.0f); - if (parent_->angleSet()) - { - auto tip = math::rotatePoint(Vec2d(0, 0), Vec2d(0.8, 0), -parent_->angle()); - drawing::drawArrow(tip, Vec2d(0, 0), col_fg_, false, 1.2, 0.2); - } + ~ThingDirCanvas() override = default; - // Draw hover point - glPointSize(8.0f); - glEnable(GL_POINT_SMOOTH); - if (point_hl_ >= 0 && point_hl_ < (int)dir_points_.size()) + // Sets the selected angle point based on [angle] + void setAngle(int angle) { - gl::setColour(col_faded); - glBegin(GL_POINTS); - glVertex2d(dir_points_[point_hl_].x, dir_points_[point_hl_].y); - glEnd(); + // Clamp angle + while (angle >= 360) + angle -= 360; + while (angle < 0) + angle += 360; + + // Set selected dir point (if any) + if (!dir_points_.empty()) + { + switch (angle) + { + case 0: point_sel_ = 6; break; + case 45: point_sel_ = 7; break; + case 90: point_sel_ = 0; break; + case 135: point_sel_ = 1; break; + case 180: point_sel_ = 2; break; + case 225: point_sel_ = 3; break; + case 270: point_sel_ = 4; break; + case 315: point_sel_ = 5; break; + default: point_sel_ = -1; break; + } + } + + Refresh(); } - // Draw selected point - if (parent_->angleSet() && point_sel_ >= 0 && point_sel_ < (int)dir_points_.size()) + // Draws the control + void draw() override { - gl::setColour(col_fg_); - glBegin(GL_POINTS); - glVertex2d(dir_points_[point_sel_].x, dir_points_[point_sel_].y); - glEnd(); - } + // Setup the viewport + const wxSize size = GetSize() * GetContentScaleFactor(); + glViewport(0, 0, size.x, size.y); + + // Setup the screen projection + glMatrixMode(GL_PROJECTION); + glLoadIdentity(); + glOrtho(-1.2, 1.2, 1.2, -1.2, -1, 1); + + glMatrixMode(GL_MODELVIEW); + glLoadIdentity(); + + // Clear + glClearColor(col_bg_.fr(), col_bg_.fg(), col_bg_.fb(), 1.0f); + glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); + + // Draw angle ring + glDisable(GL_TEXTURE_2D); + glLineWidth(1.5f); + glEnable(GL_LINE_SMOOTH); + ColRGBA col_faded( + col_bg_.r * 0.6 + col_fg_.r * 0.4, col_bg_.g * 0.6 + col_fg_.g * 0.4, col_bg_.b * 0.6 + col_fg_.b * 0.4); + drawing::drawEllipse(Vec2d(0, 0), 1, 1, 48, col_faded); + + // Draw dir points + for (auto dir_point : dir_points_) + { + drawing::drawFilledEllipse(dir_point, 0.12, 0.12, 8, col_bg_); + drawing::drawEllipse(dir_point, 0.12, 0.12, 16, col_fg_); + } - // Swap buffers (ie show what was drawn) - SwapBuffers(); -} + // Draw angle arrow + glLineWidth(2.0f); + if (parent_->angleSet()) + { + auto tip = math::rotatePoint(Vec2d(0, 0), Vec2d(0.8, 0), -parent_->angle()); + drawing::drawArrow(tip, Vec2d(0, 0), col_fg_, false, 1.2, 0.2); + } + // Draw hover point + glPointSize(8.0f); + glEnable(GL_POINT_SMOOTH); + if (point_hl_ >= 0 && point_hl_ < static_cast(dir_points_.size())) + { + gl::setColour(col_faded); + glBegin(GL_POINTS); + glVertex2d(dir_points_[point_hl_].x, dir_points_[point_hl_].y); + glEnd(); + } -// ----------------------------------------------------------------------------- -// -// ThingDirCanvas Class Events -// -// ----------------------------------------------------------------------------- + // Draw selected point + if (parent_->angleSet() && point_sel_ >= 0 && point_sel_ < static_cast(dir_points_.size())) + { + gl::setColour(col_fg_); + glBegin(GL_POINTS); + glVertex2d(dir_points_[point_sel_].x, dir_points_[point_sel_].y); + glEnd(); + } + // Swap buffers (ie show what was drawn) + SwapBuffers(); + } -// ----------------------------------------------------------------------------- -// Called when a mouse event happens in the canvas -// ----------------------------------------------------------------------------- -void ThingDirCanvas::onMouseEvent(wxMouseEvent& e) -{ - // Motion - if (e.Moving()) + // Called when a mouse event happens in the canvas + void onMouseEvent(wxMouseEvent& e) { - auto last_point = point_hl_; - if (app::runTimer() > last_check_ + 15) + // Motion + if (e.Moving()) { - // Get cursor position in canvas coordinates - const wxSize size = GetSize(); - double x = -1.2 + ((double)e.GetX() / (double)size.x) * 2.4; - double y = -1.2 + ((double)e.GetY() / (double)size.y) * 2.4; - Vec2d cursor_pos(x, y); - - // Find closest dir point to cursor - point_hl_ = -1; - double min_dist = 0.3; - for (unsigned a = 0; a < dir_points_.size(); a++) + auto last_point = point_hl_; + if (app::runTimer() > last_check_ + 15) { - double dist = math::distance(cursor_pos, dir_points_[a]); - if (dist < min_dist) + // Get cursor position in canvas coordinates + const wxSize size = GetSize(); + double x = -1.2 + (static_cast(e.GetX()) / static_cast(size.x)) * 2.4; + double y = -1.2 + (static_cast(e.GetY()) / static_cast(size.y)) * 2.4; + Vec2d cursor_pos(x, y); + + // Find closest dir point to cursor + point_hl_ = -1; + double min_dist = 0.3; + for (unsigned a = 0; a < dir_points_.size(); a++) { - point_hl_ = a; - min_dist = dist; + double dist = math::distance(cursor_pos, dir_points_[a]); + if (dist < min_dist) + { + point_hl_ = a; + min_dist = dist; + } } + + last_check_ = app::runTimer(); } - last_check_ = app::runTimer(); + if (last_point != point_hl_) + Refresh(); } - if (last_point != point_hl_) + // Leaving + else if (e.Leaving()) + { + point_hl_ = -1; Refresh(); - } - - // Leaving - else if (e.Leaving()) - { - point_hl_ = -1; - Refresh(); - } + } - // Left click - else if (e.LeftDown()) - { - if (point_hl_ >= 0) + // Left click + else if (e.LeftDown()) { - point_sel_ = point_hl_; - int angle = 0; - switch (point_sel_) + if (point_hl_ >= 0) { - case 6: angle = 0; break; - case 7: angle = 45; break; - case 0: angle = 90; break; - case 1: angle = 135; break; - case 2: angle = 180; break; - case 3: angle = 225; break; - case 4: angle = 270; break; - case 5: angle = 315; break; - default: angle = 0; break; - } + point_sel_ = point_hl_; + int angle = 0; + switch (point_sel_) + { + case 6: angle = 0; break; + case 7: angle = 45; break; + case 0: angle = 90; break; + case 1: angle = 135; break; + case 2: angle = 180; break; + case 3: angle = 225; break; + case 4: angle = 270; break; + case 5: angle = 315; break; + default: angle = 0; break; + } - parent_->setAngle(angle, false); - Refresh(); + parent_->setAngle(angle, false); + Refresh(); + } } + + e.Skip(); } - e.Skip(); -} +private: + AngleControl* parent_ = nullptr; + vector dir_points_; + ColRGBA col_bg_; + ColRGBA col_fg_; + int point_hl_ = -1; + int point_sel_ = -1; + long last_check_ = 0; +}; // ----------------------------------------------------------------------------- @@ -379,11 +387,10 @@ AngleControl::AngleControl(wxWindow* parent) : wxControl(parent, -1, wxDefaultPo SetSizer(sizer); // Angle visual control - sizer->Add(dc_angle_ = new ThingDirCanvas(this), 1, wxEXPAND | wxALL, ui::pad()); + sizer->Add(dc_angle_ = new ThingDirCanvas(this), wxutil::sfWithBorder(1).Expand()); // Angle text box - text_angle_ = new NumberTextCtrl(this); - sizer->Add(text_angle_, 0, wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, ui::pad()); + sizer->Add(text_angle_ = new NumberTextCtrl(this), wxutil::sfWithBorder(0, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); // Bind events text_angle_->Bind(wxEVT_TEXT, &AngleControl::onAngleTextChanged, this); @@ -462,7 +469,7 @@ ThingPropsPanel::ThingPropsPanel(wxWindow* parent) : PropsPanelBase(parent) // Tabs stc_tabs_ = STabCtrl::createControl(this); - sizer->Add(stc_tabs_, 1, wxEXPAND | wxALL, ui::pad()); + sizer->Add(stc_tabs_, wxutil::sfWithBorder(1).Expand()); // General tab stc_tabs_->AddPage(setupGeneralTab(), "General"); @@ -512,6 +519,8 @@ ThingPropsPanel::ThingPropsPanel(wxWindow* parent) : PropsPanelBase(parent) // ----------------------------------------------------------------------------- wxPanel* ThingPropsPanel::setupGeneralTab() { + namespace wx = wxutil; + auto map_format = mapeditor::editContext().mapDesc().format; // Create panel @@ -524,11 +533,11 @@ wxPanel* ThingPropsPanel::setupGeneralTab() // --- Flags --- auto frame = new wxStaticBox(panel, -1, "Flags"); auto framesizer = new wxStaticBoxSizer(frame, wxVERTICAL); - sizer->Add(framesizer, 0, wxEXPAND | wxALL, ui::pad()); + sizer->Add(framesizer, wx::sfWithBorder().Expand()); // Init flags auto gb_sizer = new wxGridBagSizer(ui::pad() / 2, ui::pad()); - framesizer->Add(gb_sizer, 1, wxEXPAND | wxALL, ui::pad()); + framesizer->Add(gb_sizer, wx::sfWithBorder(1).Expand()); int row = 0; int col = 0; @@ -546,11 +555,11 @@ wxPanel* ThingPropsPanel::setupGeneralTab() { if (i.second.showAlways()) { - flags.push_back(i.second.name()); - udmf_flags_.push_back(i.second.propName()); + flags.emplace_back(i.second.name()); + udmf_flags_.emplace_back(i.second.propName()); } else - udmf_flags_extra_.push_back(i.second.propName()); + udmf_flags_extra_.emplace_back(i.second.propName()); } } @@ -600,29 +609,25 @@ wxPanel* ThingPropsPanel::setupGeneralTab() // Type auto hbox = new wxBoxSizer(wxHORIZONTAL); - sizer->Add(hbox, 0, wxEXPAND | wxALL, ui::pad()); + sizer->Add(hbox, wx::sfWithBorder().Expand()); frame = new wxStaticBox(panel, -1, "Type"); framesizer = new wxStaticBoxSizer(frame, wxVERTICAL); - hbox->Add(framesizer, 1, wxEXPAND | wxRIGHT, ui::pad()); - framesizer->Add(gfx_sprite_ = new SpriteTexCanvas(panel), 1, wxEXPAND | wxALL, ui::pad()); + hbox->Add(framesizer, wx::sfWithBorder(1, wxRIGHT).Expand()); + framesizer->Add(gfx_sprite_ = new SpriteTexCanvas(panel), wx::sfWithBorder(1).Expand()); framesizer->Add( - label_type_ = new wxStaticText(panel, -1, ""), 0, wxEXPAND | wxLEFT | wxRIGHT | wxBOTTOM, ui::pad()); + label_type_ = new wxStaticText(panel, -1, ""), wx::sfWithBorder(0, wxLEFT | wxRIGHT | wxBOTTOM).Expand()); // Direction frame = new wxStaticBox(panel, -1, "Direction"); framesizer = new wxStaticBoxSizer(frame, wxVERTICAL); hbox->Add(framesizer, 0, wxEXPAND); - framesizer->Add(ac_direction_ = new AngleControl(panel), 1, wxEXPAND); - -#ifdef __WXMSW__ - // ac_direction->SetBackgroundColour(stc_tabs->GetThemeBackgroundColour()); -#endif + framesizer->Add(ac_direction_ = new AngleControl(panel), wxSizerFlags(1).Expand()); if (map_format != MapFormat::Doom) { // Id gb_sizer = new wxGridBagSizer(ui::pad(), ui::pad()); - sizer->Add(gb_sizer, 0, wxEXPAND | wxALL, ui::pad()); + sizer->Add(gb_sizer, wx::sfWithBorder().Expand()); gb_sizer->Add(new wxStaticText(panel, -1, "TID:"), { 0, 0 }, { 1, 1 }, wxALIGN_CENTER_VERTICAL); gb_sizer->Add(text_id_ = new NumberTextCtrl(panel), { 0, 1 }, { 1, 1 }, wxEXPAND | wxALIGN_CENTER_VERTICAL); gb_sizer->Add(btn_new_id_ = new wxButton(panel, -1, "New TID"), { 0, 2 }, { 1, 1 }); @@ -636,9 +641,9 @@ wxPanel* ThingPropsPanel::setupGeneralTab() gb_sizer->AddGrowableCol(1, 1); // 'New TID' button event - btn_new_id_->Bind(wxEVT_BUTTON, [&](wxCommandEvent&) { - text_id_->setNumber(mapeditor::editContext().map().things().firstFreeId()); - }); + btn_new_id_->Bind( + wxEVT_BUTTON, + [&](wxCommandEvent&) { text_id_->setNumber(mapeditor::editContext().map().things().firstFreeId()); }); } return panel; @@ -658,7 +663,7 @@ wxPanel* ThingPropsPanel::setupExtraFlagsTab() // Init flags auto gb_sizer_flags = new wxGridBagSizer(ui::pad() / 2, ui::pad()); - sizer->Add(gb_sizer_flags, 1, wxEXPAND | wxALL, ui::pad()); + sizer->Add(gb_sizer_flags, wxutil::sfWithBorder(1).Expand()); int row = 0; int col = 0; @@ -667,7 +672,7 @@ wxPanel* ThingPropsPanel::setupExtraFlagsTab() for (const auto& a : udmf_flags_extra_) { auto prop = game::configuration().getUDMFProperty(a.ToStdString(), MapObject::Type::Thing); - flags.push_back(prop->name()); + flags.emplace_back(prop->name()); } // Add flag checkboxes @@ -723,13 +728,14 @@ void ThingPropsPanel::openObjects(vector& objects) for (int a = 0; a < game::configuration().nThingFlags(); a++) { // Set initial flag checked value - cb_flags_[a]->SetValue(game::configuration().thingFlagSet(a, (MapThing*)objects[0])); + cb_flags_[a]->SetValue(game::configuration().thingFlagSet(a, dynamic_cast(objects[0]))); // Go through subsequent things for (unsigned b = 1; b < objects.size(); b++) { // Check for mismatch - if (cb_flags_[a]->GetValue() != game::configuration().thingFlagSet(a, (MapThing*)objects[b])) + if (cb_flags_[a]->GetValue() + != game::configuration().thingFlagSet(a, dynamic_cast(objects[b]))) { // Set undefined cb_flags_[a]->Set3StateValue(wxCHK_UNDETERMINED); @@ -822,7 +828,7 @@ void ThingPropsPanel::applyChanges() for (int f = 0; f < game::configuration().nThingFlags(); f++) { if (cb_flags_[f]->Get3StateValue() != wxCHK_UNDETERMINED) - game::configuration().setThingFlag(f, (MapThing*)object, cb_flags_[f]->GetValue()); + game::configuration().setThingFlag(f, dynamic_cast(object), cb_flags_[f]->GetValue()); } } diff --git a/src/MapEditor/UI/PropsPanel/ThingPropsPanel.h b/src/MapEditor/UI/PropsPanel/ThingPropsPanel.h index 1b5c1239d..dc9f6ed89 100644 --- a/src/MapEditor/UI/PropsPanel/ThingPropsPanel.h +++ b/src/MapEditor/UI/PropsPanel/ThingPropsPanel.h @@ -1,7 +1,6 @@ #pragma once #include "PropsPanelBase.h" -#include "UI/Canvas/OGLCanvas.h" #include "UI/Controls/STabCtrl.h" namespace slade @@ -10,56 +9,19 @@ class NumberTextCtrl; class MapObjectPropsPanel; class ArgsPanel; class ActionSpecialPanel; +class AngleControl; +class SpriteTexCanvas; +class ThingDirCanvas; namespace game { class ThingType; } -class SpriteTexCanvas : public OGLCanvas -{ -public: - SpriteTexCanvas(wxWindow* parent); - ~SpriteTexCanvas() = default; - - wxString texName() const { return texname_; } - void setSprite(const game::ThingType& type); - void draw() override; - -private: - unsigned texture_ = 0; - wxString texname_; - ColRGBA colour_ = ColRGBA::WHITE; - bool icon_ = false; -}; - -class AngleControl; -class ThingDirCanvas : public OGLCanvas -{ -public: - ThingDirCanvas(AngleControl* parent); - ~ThingDirCanvas() = default; - - void setAngle(int angle); - void draw() override; - - void onMouseEvent(wxMouseEvent& e); - -private: - AngleControl* parent_ = nullptr; - vector dir_points_; - ColRGBA col_bg_; - ColRGBA col_fg_; - int point_hl_ = -1; - int point_sel_ = -1; - long last_check_ = 0; -}; - - class AngleControl : public wxControl { public: AngleControl(wxWindow* parent); - ~AngleControl() = default; + ~AngleControl() override = default; int angle(int base = 0) const; void setAngle(int angle, bool update_visual = true); @@ -79,7 +41,7 @@ class ThingPropsPanel : public PropsPanelBase { public: ThingPropsPanel(wxWindow* parent); - ~ThingPropsPanel() = default; + ~ThingPropsPanel() override = default; void openObjects(vector& objects) override; void applyChanges() override; diff --git a/src/MapEditor/UI/ScriptEditorPanel.cpp b/src/MapEditor/UI/ScriptEditorPanel.cpp index 3fc42dbbb..81b002eec 100644 --- a/src/MapEditor/UI/ScriptEditorPanel.cpp +++ b/src/MapEditor/UI/ScriptEditorPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -36,6 +36,9 @@ #include "MainEditor/EntryOperations.h" #include "MapEditor/MapEditContext.h" #include "MapEditor/MapEditor.h" +#include "SLADEMap/MapSpecials.h" +#include "SLADEMap/SLADEMap.h" +#include "TextEditor/TextLanguage.h" #include "TextEditor/UI/FindReplacePanel.h" #include "TextEditor/UI/TextEditorCtrl.h" #include "UI/SToolBar/SToolBar.h" @@ -72,7 +75,9 @@ EXTERN_CVAR(Bool, txed_trim_whitespace) // ScriptEditorPanel class constructor // ----------------------------------------------------------------------------- ScriptEditorPanel::ScriptEditorPanel(wxWindow* parent) : - wxPanel(parent, -1), entry_script_{ new ArchiveEntry() }, entry_compiled_{ new ArchiveEntry() } + wxPanel(parent, -1), + entry_script_{ new ArchiveEntry() }, + entry_compiled_{ new ArchiveEntry() } { // Setup sizer auto sizer = new wxBoxSizer(wxVERTICAL); @@ -80,7 +85,7 @@ ScriptEditorPanel::ScriptEditorPanel(wxWindow* parent) : // Toolbar auto toolbar = new SToolBar(this); - sizer->Add(toolbar, 0, wxEXPAND); + sizer->Add(toolbar, wxSizerFlags().Expand()); wxArrayString actions; toolbar->addActionGroup("Scripts", { "mapw_script_save", "mapw_script_compile", "mapw_script_togglelanguage" }); @@ -93,13 +98,13 @@ ScriptEditorPanel::ScriptEditorPanel(wxWindow* parent) : // Add text editor auto hbox = new wxBoxSizer(wxHORIZONTAL); - sizer->Add(hbox, 1, wxEXPAND); + sizer->Add(hbox, wxSizerFlags(1).Expand()); auto vbox = new wxBoxSizer(wxVERTICAL); - hbox->Add(vbox, 1, wxEXPAND); + hbox->Add(vbox, wxSizerFlags(1).Expand()); text_editor_ = new TextEditorCtrl(this, -1); text_editor_->setJumpToControl(choice_jump_to_); - vbox->Add(text_editor_, 1, wxEXPAND | wxALL, ui::pad()); + vbox->Add(text_editor_, wxutil::sfWithBorder(1).Expand()); // Set language wxString lang = game::configuration().scriptLanguage(); @@ -121,13 +126,13 @@ ScriptEditorPanel::ScriptEditorPanel(wxWindow* parent) : // Add Find+Replace panel panel_fr_ = new FindReplacePanel(this, *text_editor_); text_editor_->setFindReplacePanel(panel_fr_); - vbox->Add(panel_fr_, 0, wxEXPAND | wxALL, ui::pad()); + vbox->Add(panel_fr_, wxutil::sfWithBorder().Expand()); panel_fr_->Hide(); // Add function/constants list list_words_ = new wxTreeListCtrl(this, -1); list_words_->SetInitialSize(wxutil::scaledSize(200, -10)); - hbox->Add(list_words_, 0, wxEXPAND | wxALL, ui::pad()); + hbox->Add(list_words_, wxutil::sfWithBorder().Expand()); populateWordList(); list_words_->Show(script_show_language_list); @@ -139,7 +144,7 @@ ScriptEditorPanel::ScriptEditorPanel(wxWindow* parent) : // Opens script text from entry [scripts], and compiled script data from // [compiled] // ----------------------------------------------------------------------------- -bool ScriptEditorPanel::openScripts(ArchiveEntry* script, ArchiveEntry* compiled) const +bool ScriptEditorPanel::openScripts(const ArchiveEntry* script, const ArchiveEntry* compiled) const { // Clear current script data entry_script_->clearData(); @@ -277,7 +282,6 @@ bool ScriptEditorPanel::handleAction(string_view name) // // ----------------------------------------------------------------------------- - // ----------------------------------------------------------------------------- // Called when a word list entry is activated (double-clicked) // ----------------------------------------------------------------------------- @@ -305,8 +309,6 @@ void ScriptEditorPanel::onWordListActivate(wxCommandEvent& e) int pos = text_editor_->GetCurrentPos(); if (language->isFunction(word)) { - auto func = language->function(word); - // Add function + () word += "()"; text_editor_->InsertText(pos, word); diff --git a/src/MapEditor/UI/ScriptEditorPanel.h b/src/MapEditor/UI/ScriptEditorPanel.h index 1428154b4..ff102c764 100644 --- a/src/MapEditor/UI/ScriptEditorPanel.h +++ b/src/MapEditor/UI/ScriptEditorPanel.h @@ -14,12 +14,12 @@ class ScriptEditorPanel : public wxPanel, SActionHandler { public: ScriptEditorPanel(wxWindow* parent); - ~ScriptEditorPanel() = default; + ~ScriptEditorPanel() override = default; ArchiveEntry* scriptEntry() const { return entry_script_.get(); } ArchiveEntry* compiledEntry() const { return entry_compiled_.get(); } - bool openScripts(ArchiveEntry* scripts, ArchiveEntry* compiled = nullptr) const; + bool openScripts(const ArchiveEntry* scripts, const ArchiveEntry* compiled = nullptr) const; void populateWordList() const; void saveScripts() const; void updateUI() const; diff --git a/src/MapEditor/UI/ShapeDrawPanel.cpp b/src/MapEditor/UI/ShapeDrawPanel.cpp index 22a8b926d..69e08c26f 100644 --- a/src/MapEditor/UI/ShapeDrawPanel.cpp +++ b/src/MapEditor/UI/ShapeDrawPanel.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -60,6 +60,8 @@ EXTERN_CVAR(Bool, shapedraw_lockratio) // ----------------------------------------------------------------------------- ShapeDrawPanel::ShapeDrawPanel(wxWindow* parent) : wxPanel{ parent, -1 } { + namespace wx = wxutil; + // Setup sizer auto sizer = new wxBoxSizer(wxVERTICAL); SetSizer(sizer); @@ -68,16 +70,16 @@ ShapeDrawPanel::ShapeDrawPanel(wxWindow* parent) : wxPanel{ parent, -1 } wxString shapes[] = { "Rectangle", "Ellipse" }; choice_shape_ = new wxChoice(this, -1, wxDefaultPosition, wxDefaultSize, 2, shapes); sizer_main_ = new wxBoxSizer(wxHORIZONTAL); - sizer->Add(sizer_main_, 0, wxEXPAND | wxALL, ui::pad()); - sizer_main_->Add(wxutil::createLabelHBox(this, "Shape:", choice_shape_), 0, wxEXPAND | wxRIGHT, ui::padLarge()); + sizer->Add(sizer_main_, wx::sfWithBorder().Expand()); + sizer_main_->Add(wx::createLabelHBox(this, "Shape:", choice_shape_), wx::sfWithLargeBorder(0, wxRIGHT).Expand()); // Centered cb_centered_ = new wxCheckBox(this, -1, "Centered"); - sizer_main_->Add(cb_centered_, 0, wxEXPAND | wxRIGHT, ui::padLarge()); + sizer_main_->Add(cb_centered_, wx::sfWithLargeBorder(0, wxRIGHT).Expand()); // Lock ratio (1:1) cb_lockratio_ = new wxCheckBox(this, -1, "1:1 Size"); - sizer_main_->Add(cb_lockratio_, 0, wxEXPAND | wxRIGHT, ui::padLarge()); + sizer_main_->Add(cb_lockratio_, wx::sfWithLargeBorder(0, wxRIGHT).Expand()); // Sides panel_sides_ = new wxPanel(this, -1); @@ -92,7 +94,7 @@ ShapeDrawPanel::ShapeDrawPanel(wxWindow* parent) : wxPanel{ parent, -1 } wxSP_ARROW_KEYS | wxALIGN_LEFT | wxTE_PROCESS_ENTER, 3, 1000); - hbox2->Add(wxutil::createLabelHBox(panel_sides_, "Sides:", spin_sides_), 1, wxEXPAND); + hbox2->Add(wx::createLabelHBox(panel_sides_, "Sides:", spin_sides_), wxSizerFlags(1).Expand()); // Set control values choice_shape_->SetSelection(shapedraw_shape); @@ -108,10 +110,13 @@ ShapeDrawPanel::ShapeDrawPanel(wxWindow* parent) : wxPanel{ parent, -1 } showShapeOptions(shapedraw_shape); // Bind events - choice_shape_->Bind(wxEVT_CHOICE, [&](wxCommandEvent&) { - shapedraw_shape = choice_shape_->GetSelection(); - showShapeOptions(shapedraw_shape); - }); + choice_shape_->Bind( + wxEVT_CHOICE, + [&](wxCommandEvent&) + { + shapedraw_shape = choice_shape_->GetSelection(); + showShapeOptions(shapedraw_shape); + }); cb_centered_->Bind(wxEVT_CHECKBOX, [&](wxCommandEvent&) { shapedraw_centered = cb_centered_->GetValue(); }); cb_lockratio_->Bind(wxEVT_CHECKBOX, [&](wxCommandEvent&) { shapedraw_lockratio = cb_lockratio_->GetValue(); }); spin_sides_->Bind(wxEVT_SPINCTRL, [&](wxCommandEvent&) { shapedraw_sides = spin_sides_->GetValue(); }); @@ -131,7 +136,7 @@ void ShapeDrawPanel::showShapeOptions(int shape) if (shape == 1) { // Sides - sizer_main_->Add(panel_sides_, 0, wxEXPAND | wxRIGHT, ui::padLarge()); + sizer_main_->Add(panel_sides_, wxutil::sfWithLargeBorder(0, wxRIGHT).Expand()); panel_sides_->Show(true); } diff --git a/src/MapEditor/UI/ShapeDrawPanel.h b/src/MapEditor/UI/ShapeDrawPanel.h index 9b0718d41..75a882f33 100644 --- a/src/MapEditor/UI/ShapeDrawPanel.h +++ b/src/MapEditor/UI/ShapeDrawPanel.h @@ -8,7 +8,7 @@ class ShapeDrawPanel : public wxPanel { public: ShapeDrawPanel(wxWindow* parent); - ~ShapeDrawPanel() = default; + ~ShapeDrawPanel() override = default; void showShapeOptions(int shape); diff --git a/src/MapEditor/UndoSteps.cpp b/src/MapEditor/UndoSteps.cpp index 70eb4cc2c..23ae03379 100644 --- a/src/MapEditor/UndoSteps.cpp +++ b/src/MapEditor/UndoSteps.cpp @@ -1,11 +1,53 @@ +// ----------------------------------------------------------------------------- +// SLADE - It's a Doom Editor +// Copyright(C) 2008 - 2024 Simon Judd +// +// Email: sirjuddington@gmail.com +// Web: http://slade.mancubus.net +// Filename: UndoSteps.cpp +// Description: Various map editor related UndoSteps +// +// This program is free software; you can redistribute it and/or modify it +// under the terms of the GNU General Public License as published by the Free +// Software Foundation; either version 2 of the License, or (at your option) +// any later version. +// +// This program is distributed in the hope that it will be useful, but WITHOUT +// ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or +// FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for +// more details. +// +// You should have received a copy of the GNU General Public License along with +// this program; if not, write to the Free Software Foundation, Inc., +// 51 Franklin Street, Fifth Floor, Boston, MA 02110 - 1301, USA. +// ----------------------------------------------------------------------------- + + +// ----------------------------------------------------------------------------- +// +// Includes +// +// ----------------------------------------------------------------------------- #include "Main.h" #include "UndoSteps.h" +#include "SLADEMap/MapObject/MapLine.h" +#include "SLADEMap/MapObject/MapSector.h" +#include "SLADEMap/MapObject/MapSide.h" +#include "SLADEMap/MapObject/MapThing.h" +#include "SLADEMap/MapObject/MapVertex.h" #include "SLADEMap/SLADEMap.h" using namespace slade; using namespace mapeditor; + +// ----------------------------------------------------------------------------- +// +// PropertyChangeUS Class Functions +// +// ----------------------------------------------------------------------------- + PropertyChangeUS::PropertyChangeUS(MapObject* object) : backup_{ new MapObject::Backup() } { object->backupTo(backup_.get()); @@ -38,6 +80,12 @@ bool PropertyChangeUS::doRedo() } +// ----------------------------------------------------------------------------- +// +// MapObjectCreateDeleteUS Class Functions +// +// ----------------------------------------------------------------------------- + MapObjectCreateDeleteUS::MapObjectCreateDeleteUS() { auto map = undoredo::currentMap(); @@ -219,6 +267,11 @@ bool MapObjectCreateDeleteUS::isOk() } +// ----------------------------------------------------------------------------- +// +// MultiMapObjectPropertyChangeUS Class Functions +// +// ----------------------------------------------------------------------------- MultiMapObjectPropertyChangeUS::MultiMapObjectPropertyChangeUS() { diff --git a/src/MapEditor/UndoSteps.h b/src/MapEditor/UndoSteps.h index df71ff3db..cb7edc800 100644 --- a/src/MapEditor/UndoSteps.h +++ b/src/MapEditor/UndoSteps.h @@ -10,7 +10,7 @@ class PropertyChangeUS : public UndoStep { public: PropertyChangeUS(MapObject* object); - ~PropertyChangeUS() = default; + ~PropertyChangeUS() override = default; void doSwap(MapObject* obj); bool doUndo() override; @@ -25,9 +25,9 @@ class MapObjectCreateDeleteUS : public UndoStep { public: MapObjectCreateDeleteUS(); - ~MapObjectCreateDeleteUS() = default; + ~MapObjectCreateDeleteUS() override = default; - bool isValid(vector& list) const { return !(list.size() == 1 && list[0] == 0); } + bool isValid(const vector& list) const { return !(list.size() == 1 && list[0] == 0); } void swapLists(); bool doUndo() override; bool doRedo() override; @@ -47,7 +47,7 @@ class MultiMapObjectPropertyChangeUS : public UndoStep { public: MultiMapObjectPropertyChangeUS(); - ~MultiMapObjectPropertyChangeUS() = default; + ~MultiMapObjectPropertyChangeUS() override = default; void doSwap(MapObject* obj, unsigned index); bool doUndo() override; diff --git a/src/OpenGL/Drawing.cpp b/src/OpenGL/Drawing.cpp index 71ce0ec86..7440abc59 100644 --- a/src/OpenGL/Drawing.cpp +++ b/src/OpenGL/Drawing.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -246,13 +246,13 @@ FTFont* getFont(Font font) { switch (font) { - case Font::Normal: return font_normal; - case Font::Condensed: return font_condensed; - case Font::Bold: return font_bold; + case Font::Normal: return font_normal; + case Font::Condensed: return font_condensed; + case Font::Bold: return font_bold; case Font::BoldCondensed: return font_boldcondensed; - case Font::Monospace: return font_mono; - case Font::Small: return font_small; - default: return font_normal; + case Font::Monospace: return font_mono; + case Font::Small: return font_small; + default: return font_normal; } } } // namespace slade::drawing @@ -269,7 +269,7 @@ int drawing::fontSize() // ----------------------------------------------------------------------------- // Draws a line from [start] to [end] // ----------------------------------------------------------------------------- -void drawing::drawLine(Vec2d start, Vec2d end) +void drawing::drawLine(const Vec2d& start, const Vec2d& end) { glBegin(GL_LINES); glVertex2d(start.x, start.y); @@ -291,7 +291,7 @@ void drawing::drawLine(double x1, double y1, double x2, double y2) // ----------------------------------------------------------------------------- // Draws a line from [start] to [end] // ----------------------------------------------------------------------------- -void drawing::drawLineTabbed(Vec2d start, Vec2d end, double tab, double tab_max) +void drawing::drawLineTabbed(const Vec2d& start, const Vec2d& end, double tab, double tab_max) { // Draw line glBegin(GL_LINES); @@ -327,8 +327,8 @@ void drawing::drawLineTabbed(Vec2d start, Vec2d end, double tab, double tab_max) // If [twoway] is true, an arrowhead is also drawn at the [p2] end // ----------------------------------------------------------------------------- void drawing::drawArrow( - Vec2d p1, - Vec2d p2, + const Vec2d& p1, + const Vec2d& p2, const ColRGBA& color, bool twoway, double arrowhead_angle, @@ -377,7 +377,7 @@ void drawing::drawArrow( // ----------------------------------------------------------------------------- // Draws a rectangle from [tl] to [br] // ----------------------------------------------------------------------------- -void drawing::drawRect(Vec2d tl, Vec2d br) +void drawing::drawRect(const Vec2d& tl, const Vec2d& br) { glBegin(GL_LINE_LOOP); glVertex2d(tl.x, tl.y); @@ -403,7 +403,7 @@ void drawing::drawRect(double x1, double y1, double x2, double y2) // ----------------------------------------------------------------------------- // Draws a filled rectangle from [tl] to [br] // ----------------------------------------------------------------------------- -void drawing::drawFilledRect(Vec2d tl, Vec2d br) +void drawing::drawFilledRect(const Vec2d& tl, const Vec2d& br) { glBegin(GL_QUADS); glVertex2d(tl.x, tl.y); @@ -429,7 +429,7 @@ void drawing::drawFilledRect(double x1, double y1, double x2, double y2) // ----------------------------------------------------------------------------- // Draws a filled rectangle with a border from [x1,y1] to [x2,y2] // ----------------------------------------------------------------------------- -void drawing::drawBorderedRect(Vec2d tl, Vec2d br, const ColRGBA& colour, const ColRGBA& border_colour) +void drawing::drawBorderedRect(const Vec2d& tl, const Vec2d& br, const ColRGBA& colour, const ColRGBA& border_colour) { drawBorderedRect(tl.x, tl.y, br.x, br.y, colour, border_colour); } @@ -467,7 +467,7 @@ void drawing::drawBorderedRect( // ----------------------------------------------------------------------------- // Draws an ellipse at [mid] // ----------------------------------------------------------------------------- -void drawing::drawEllipse(Vec2d mid, double radius_x, double radius_y, int sides, const ColRGBA& colour) +void drawing::drawEllipse(const Vec2d& mid, double radius_x, double radius_y, int sides, const ColRGBA& colour) { // Set colour gl::setColour(colour); @@ -478,7 +478,7 @@ void drawing::drawEllipse(Vec2d mid, double radius_x, double radius_y, int sides for (int a = 0; a < sides; a++) { glVertex2d(mid.x + sin(rot) * radius_x, mid.y - cos(rot) * radius_y); - rot -= (3.1415926535897932384626433832795 * 2) / (double)sides; + rot -= (3.1415926535897932384626433832795 * 2) / static_cast(sides); } glEnd(); } @@ -486,7 +486,7 @@ void drawing::drawEllipse(Vec2d mid, double radius_x, double radius_y, int sides // ----------------------------------------------------------------------------- // Draws a filled ellipse at [mid] // ----------------------------------------------------------------------------- -void drawing::drawFilledEllipse(Vec2d mid, double radius_x, double radius_y, int sides, const ColRGBA& colour) +void drawing::drawFilledEllipse(const Vec2d& mid, double radius_x, double radius_y, int sides, const ColRGBA& colour) { // Set colour gl::setColour(colour); @@ -498,7 +498,7 @@ void drawing::drawFilledEllipse(Vec2d mid, double radius_x, double radius_y, int for (int a = 0; a < sides + 1; a++) { glVertex2d(mid.x + sin(rot) * radius_x, mid.y - cos(rot) * radius_y); - rot -= (3.1415926535897932384626433832795 * 2) / (double)sides; + rot -= (3.1415926535897932384626433832795 * 2) / static_cast(sides); } glEnd(); } @@ -563,8 +563,8 @@ void drawing::drawTextureTiled(unsigned id, uint32_t width, uint32_t height) // Calculate texture coordinates auto& tex_info = gl::Texture::info(id); - double tex_x = (double)width / (double)tex_info.size.x; - double tex_y = (double)height / (double)tex_info.size.y; + double tex_x = static_cast(width) / static_cast(tex_info.size.x); + double tex_y = static_cast(height) / static_cast(tex_info.size.y); // Draw glBegin(GL_QUADS); @@ -864,7 +864,7 @@ wxColour drawing::lightColour(const wxColour& colour, float percent) ColHSL hsl = ColRGBA(colour).asHSL(); // Increase luminance - hsl.l += (float)((percent * 5.0) / 100.0); + hsl.l += static_cast((percent * 5.0) / 100.0); if (hsl.l > 1.0) hsl.l = 1.0; @@ -883,7 +883,7 @@ wxColour drawing::darkColour(const wxColour& colour, float percent) ColHSL hsl = ColRGBA(colour).asHSL(); // Decrease luminance - hsl.l -= (float)((percent * 5.0) / 100.0); + hsl.l -= static_cast((percent * 5.0) / 100.0); if (hsl.l < 0) hsl.l = 0; @@ -903,7 +903,9 @@ wxColour drawing::darkColour(const wxColour& colour, float percent) // TextBox class constructor // ----------------------------------------------------------------------------- TextBox::TextBox(string_view text, drawing::Font font, int width, int line_height) : - font_{ font }, width_{ width }, line_height_{ line_height } + font_{ font }, + width_{ width }, + line_height_{ line_height } { setText(text); } diff --git a/src/OpenGL/Drawing.h b/src/OpenGL/Drawing.h index d0802f149..4c7731311 100644 --- a/src/OpenGL/Drawing.h +++ b/src/OpenGL/Drawing.h @@ -35,21 +35,21 @@ namespace drawing int fontSize(); // Basic drawing - void drawLine(Vec2d start, Vec2d end); + void drawLine(const Vec2d& start, const Vec2d& end); void drawLine(double x1, double y1, double x2, double y2); - void drawLineTabbed(Vec2d start, Vec2d end, double tab = 0.1, double tab_max = 16); + void drawLineTabbed(const Vec2d& start, const Vec2d& end, double tab = 0.1, double tab_max = 16); void drawArrow( - Vec2d p1, - Vec2d p2, + const Vec2d& p1, + const Vec2d& p2, const ColRGBA& color = ColRGBA::WHITE, bool twoway = false, double arrowhead_angle = 0.7854f, double arrowhead_length = 25.f); - void drawRect(Vec2d tl, Vec2d br); + void drawRect(const Vec2d& tl, const Vec2d& br); void drawRect(double x1, double y1, double x2, double y2); - void drawFilledRect(Vec2d tl, Vec2d br); + void drawFilledRect(const Vec2d& tl, const Vec2d& br); void drawFilledRect(double x1, double y1, double x2, double y2); - void drawBorderedRect(Vec2d tl, Vec2d br, const ColRGBA& colour, const ColRGBA& border_colour); + void drawBorderedRect(const Vec2d& tl, const Vec2d& br, const ColRGBA& colour, const ColRGBA& border_colour); void drawBorderedRect( double x1, double y1, @@ -57,8 +57,8 @@ namespace drawing double y2, const ColRGBA& colour, const ColRGBA& border_colour); - void drawEllipse(Vec2d mid, double radius_x, double radius_y, int sides, const ColRGBA& colour); - void drawFilledEllipse(Vec2d mid, double radius_x, double radius_y, int sides, const ColRGBA& colour); + void drawEllipse(const Vec2d& mid, double radius_x, double radius_y, int sides, const ColRGBA& colour); + void drawFilledEllipse(const Vec2d& mid, double radius_x, double radius_y, int sides, const ColRGBA& colour); // Texture drawing void drawTexture(unsigned id, double x = 0, double y = 0, bool flipx = false, bool flipy = false); @@ -115,7 +115,8 @@ class TextBox void setText(string_view text); void setSize(int width); void setLineHeight(int height) { line_height_ = height; } - void draw(int x, int y, const ColRGBA& colour = ColRGBA::WHITE, drawing::Align alignment = drawing::Align::Left) const; + void draw(int x, int y, const ColRGBA& colour = ColRGBA::WHITE, drawing::Align alignment = drawing::Align::Left) + const; private: string text_; diff --git a/src/OpenGL/GLHeaders.h b/src/OpenGL/GLHeaders.h new file mode 100644 index 000000000..71b0b2155 --- /dev/null +++ b/src/OpenGL/GLHeaders.h @@ -0,0 +1,18 @@ +#pragma once + +// OpenGL +// glad.h replaces gl.h, still need glu.h +// clang-format off +#ifdef __APPLE__ +// OSX GL headers +#include "thirdparty/glad/include/glad/glad.h" +#include +#else +// Windows/Unix GL headers +#include "thirdparty/glad/include/glad/glad.h" +#include +#endif +// clang-format on + +#include +#undef None // Why does #define this? Idiotic diff --git a/src/OpenGL/GLTexture.cpp b/src/OpenGL/GLTexture.cpp index 0a8b0f3dc..3d4881882 100644 --- a/src/OpenGL/GLTexture.cpp +++ b/src/OpenGL/GLTexture.cpp @@ -271,7 +271,7 @@ bool gl::Texture::loadData(unsigned id, const uint8_t* data, unsigned width, uns glTexImage2D(GL_TEXTURE_2D, 0, 4, width, height, 0, GL_RGBA, GL_UNSIGNED_BYTE, data); } - tex_info.size = { (int)width, (int)height }; + tex_info.size = { static_cast(width), static_cast(height) }; return true; } @@ -279,7 +279,7 @@ bool gl::Texture::loadData(unsigned id, const uint8_t* data, unsigned width, uns // ----------------------------------------------------------------------------- // Loads [image] to the OpenGL texture [id], using [pal] if necessary // ----------------------------------------------------------------------------- -bool gl::Texture::loadImage(unsigned id, const SImage& image, Palette* pal) +bool gl::Texture::loadImage(unsigned id, const SImage& image, const Palette* pal) { // Check image dimensions if (validTexDimension(image.width()) && validTexDimension(image.height())) diff --git a/src/OpenGL/GLTexture.h b/src/OpenGL/GLTexture.h index 5a6814970..b3cbe6c6b 100644 --- a/src/OpenGL/GLTexture.h +++ b/src/OpenGL/GLTexture.h @@ -51,7 +51,7 @@ namespace gl TexFilter filter = TexFilter::Nearest, bool tiling = true); static bool loadData(unsigned id, const uint8_t* data, unsigned width, unsigned height); - static bool loadImage(unsigned id, const SImage& image, Palette* pal = nullptr); + static bool loadImage(unsigned id, const SImage& image, const Palette* pal = nullptr); static bool genChequeredTexture(unsigned id, uint8_t block_size, ColRGBA col1, ColRGBA col2); static void clear(unsigned id); static void clearAll(); diff --git a/src/OpenGL/OpenGL.cpp b/src/OpenGL/OpenGL.cpp index c7203f1a3..b41c1698f 100644 --- a/src/OpenGL/OpenGL.cpp +++ b/src/OpenGL/OpenGL.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -141,9 +141,9 @@ bool gl::init() } // Get OpenGL info - info.vendor = (const char*)glGetString(GL_VENDOR); - info.renderer = (const char*)glGetString(GL_RENDERER); - info.version = (const char*)glGetString(GL_VERSION); + info.vendor = reinterpret_cast(glGetString(GL_VENDOR)); + info.renderer = reinterpret_cast(glGetString(GL_RENDERER)); + info.version = reinterpret_cast(glGetString(GL_VERSION)); // Get OpenGL version string_view temp{ info.version.data(), 3 }; diff --git a/src/OpenGL/OpenGL.h b/src/OpenGL/OpenGL.h index 365b56155..5ac22d04c 100644 --- a/src/OpenGL/OpenGL.h +++ b/src/OpenGL/OpenGL.h @@ -1,21 +1,6 @@ #pragma once -// OpenGL -// glad.h replaces gl.h, still need glu.h -// clang-format off -#ifdef __APPLE__ -// OSX GL headers -#include "thirdparty/glad/include/glad/glad.h" -#include -#else -// Windows/Unix GL headers -#include "thirdparty/glad/include/glad/glad.h" -#include -#endif -// clang-format on - -#include -#undef None // Why does #define this? Idiotic +#include "GLHeaders.h" namespace slade { diff --git a/src/OpenGL/View.cpp b/src/OpenGL/View.cpp index d31e19c63..5bf61513c 100644 --- a/src/OpenGL/View.cpp +++ b/src/OpenGL/View.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -118,7 +118,7 @@ void View::zoomToward(double amount, const Vec2i& point) // ----------------------------------------------------------------------------- // Zooms and offsets the view such that [bbox] fits within the current view size // ----------------------------------------------------------------------------- -void View::fitTo(BBox bbox) +void View::fitTo(const BBox& bbox) { // Reset zoom and set offsets to the middle of the canvas scale_ = 2; @@ -221,7 +221,7 @@ bool View::interpolate(double mult, const Vec2d* towards) double View::canvasX(int screen_x, bool inter) const { return inter ? screen_x / scale_inter_ + offset_inter_.x - (size_.x * 0.5 / scale_inter_) : - screen_x / scale_ + offset_.x - (size_.x * 0.5 / scale_); + screen_x / scale_ + offset_.x - (size_.x * 0.5 / scale_); } // ----------------------------------------------------------------------------- @@ -233,12 +233,12 @@ double View::canvasY(int screen_y, bool inter) const if (y_flipped_) { return inter ? -screen_y / scale_inter_ + offset_inter_.y + (size_.y * 0.5 / scale_inter_) : - -screen_y / scale_ + offset_.y + (size_.y * 0.5 / scale_); + -screen_y / scale_ + offset_.y + (size_.y * 0.5 / scale_); } else { return inter ? -screen_y / scale_inter_ + offset_inter_.y - (size_.y * 0.5 / scale_inter_) : - -screen_y / scale_ + offset_.y - (size_.y * 0.5 / scale_); + -screen_y / scale_ + offset_.y - (size_.y * 0.5 / scale_); } } @@ -265,7 +265,7 @@ int View::screenX(double canvas_x) const int View::screenY(double canvas_y) const { return y_flipped_ ? math::round((size_.y * 0.5) - ((canvas_y - offset_inter_.y) * scale_inter_)) : - math::round((size_.y * 0.5) + ((canvas_y - offset_inter_.y) * scale_inter_)); + math::round((size_.y * 0.5) + ((canvas_y - offset_inter_.y) * scale_inter_)); } // ----------------------------------------------------------------------------- diff --git a/src/OpenGL/View.h b/src/OpenGL/View.h index aed23d282..2b3456ec5 100644 --- a/src/OpenGL/View.h +++ b/src/OpenGL/View.h @@ -35,7 +35,7 @@ class View void pan(double x, double y); void zoom(double amount); void zoomToward(double amount, const Vec2i& point); - void fitTo(BBox bbox); + void fitTo(const BBox& bbox); bool interpolate(double mult, const Vec2d* towards = nullptr); // Canvas <-> Screen Coordinate Translation diff --git a/src/SLADEMap/MapFormat/Doom32XMapFormat.cpp b/src/SLADEMap/MapFormat/Doom32XMapFormat.cpp index bdaf2c4ba..81bf8e9a3 100644 --- a/src/SLADEMap/MapFormat/Doom32XMapFormat.cpp +++ b/src/SLADEMap/MapFormat/Doom32XMapFormat.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd, Victor Luchits +// Copyright(C) 2008 - 2024 Simon Judd, Victor Luchits // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -34,6 +34,7 @@ #include "General/UI.h" #include "SLADEMap/MapObject/MapVertex.h" #include "SLADEMap/MapObjectCollection.h" +#include "SLADEMap/MapObjectList/VertexList.h" using namespace slade; diff --git a/src/SLADEMap/MapFormat/Doom32XMapFormat.h b/src/SLADEMap/MapFormat/Doom32XMapFormat.h index 04ca76cbc..cbdb0821e 100644 --- a/src/SLADEMap/MapFormat/Doom32XMapFormat.h +++ b/src/SLADEMap/MapFormat/Doom32XMapFormat.h @@ -1,6 +1,5 @@ #pragma once -#include "MapFormatHandler.h" #include "DoomMapFormat.h" namespace slade diff --git a/src/SLADEMap/MapFormat/Doom64MapFormat.cpp b/src/SLADEMap/MapFormat/Doom64MapFormat.cpp index f69711252..f5a753244 100644 --- a/src/SLADEMap/MapFormat/Doom64MapFormat.cpp +++ b/src/SLADEMap/MapFormat/Doom64MapFormat.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -33,6 +33,16 @@ #include "Doom64MapFormat.h" #include "General/ResourceManager.h" #include "General/UI.h" +#include "SLADEMap/MapObject/MapLine.h" +#include "SLADEMap/MapObject/MapSector.h" +#include "SLADEMap/MapObject/MapSide.h" +#include "SLADEMap/MapObject/MapThing.h" +#include "SLADEMap/MapObject/MapVertex.h" +#include "SLADEMap/MapObjectList/LineList.h" +#include "SLADEMap/MapObjectList/SectorList.h" +#include "SLADEMap/MapObjectList/SideList.h" +#include "SLADEMap/MapObjectList/ThingList.h" +#include "SLADEMap/MapObjectList/VertexList.h" #include "SLADEMap/SLADEMap.h" using namespace slade; @@ -41,7 +51,7 @@ using namespace slade; // ----------------------------------------------------------------------------- // Reads the given Doom64-format [map], populating [map_data] // ----------------------------------------------------------------------------- -bool Doom64MapFormat::readMap(Archive::MapDesc map, MapObjectCollection& map_data, PropertyList& map_extra_props) +bool Doom64MapFormat::readMap(MapDesc map, MapObjectCollection& map_data, PropertyList& map_extra_props) { log::info(2, "Reading Doom64 format map"); diff --git a/src/SLADEMap/MapFormat/Doom64MapFormat.h b/src/SLADEMap/MapFormat/Doom64MapFormat.h index 88c126400..f78280b11 100644 --- a/src/SLADEMap/MapFormat/Doom64MapFormat.h +++ b/src/SLADEMap/MapFormat/Doom64MapFormat.h @@ -58,7 +58,7 @@ class Doom64MapFormat : public MapFormatHandler short tid; }; - bool readMap(Archive::MapDesc map, MapObjectCollection& map_data, PropertyList& map_extra_props) override; + bool readMap(MapDesc map, MapObjectCollection& map_data, PropertyList& map_extra_props) override; vector> writeMap(const MapObjectCollection& map_data, const PropertyList& map_extra_props) override; diff --git a/src/SLADEMap/MapFormat/DoomMapFormat.cpp b/src/SLADEMap/MapFormat/DoomMapFormat.cpp index f5414f9e4..1bce343e2 100644 --- a/src/SLADEMap/MapFormat/DoomMapFormat.cpp +++ b/src/SLADEMap/MapFormat/DoomMapFormat.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -35,8 +35,15 @@ #include "General/UI.h" #include "SLADEMap/MapObject/MapLine.h" #include "SLADEMap/MapObject/MapSector.h" +#include "SLADEMap/MapObject/MapSide.h" +#include "SLADEMap/MapObject/MapThing.h" #include "SLADEMap/MapObject/MapVertex.h" #include "SLADEMap/MapObjectCollection.h" +#include "SLADEMap/MapObjectList/LineList.h" +#include "SLADEMap/MapObjectList/SectorList.h" +#include "SLADEMap/MapObjectList/SideList.h" +#include "SLADEMap/MapObjectList/ThingList.h" +#include "SLADEMap/MapObjectList/VertexList.h" #include "Utility/StringUtils.h" using namespace slade; @@ -52,7 +59,7 @@ using namespace slade; // ----------------------------------------------------------------------------- // Reads the given Doom-format [map], populating [map_data] // ----------------------------------------------------------------------------- -bool DoomMapFormat::readMap(Archive::MapDesc map, MapObjectCollection& map_data, PropertyList& map_extra_props) +bool DoomMapFormat::readMap(MapDesc map, MapObjectCollection& map_data, PropertyList& map_extra_props) { log::info(2, "Reading Doom format map"); @@ -158,8 +165,9 @@ bool DoomMapFormat::readVERTEXES(ArchiveEntry* entry, MapObjectCollection& map_d float p = ui::getSplashProgress(); for (size_t a = 0; a < nv; a++) { - ui::setSplashProgress(p + ((float)a / nv) * 0.2f); - map_data.addVertex(std::make_unique(Vec2d{ (double)vert_data[a].x, (double)vert_data[a].y })); + ui::setSplashProgress(p + (static_cast(a) / nv) * 0.2f); + map_data.addVertex(std::make_unique( + Vec2d{ static_cast(vert_data[a].x), static_cast(vert_data[a].y) })); } log::info(3, "Read {} vertices", map_data.vertices().size()); @@ -191,7 +199,7 @@ bool DoomMapFormat::readSIDEDEFS(ArchiveEntry* entry, MapObjectCollection& map_d float p = ui::getSplashProgress(); for (size_t a = 0; a < ns; a++) { - ui::setSplashProgress(p + ((float)a / ns) * 0.2f); + ui::setSplashProgress(p + (static_cast(a) / ns) * 0.2f); // Add side map_data.addSide(std::make_unique( @@ -231,7 +239,7 @@ bool DoomMapFormat::readLINEDEFS(ArchiveEntry* entry, MapObjectCollection& map_d float p = ui::getSplashProgress(); for (size_t a = 0; a < nl; a++) { - ui::setSplashProgress(p + ((float)a / nl) * 0.2f); + ui::setSplashProgress(p + (static_cast(a) / nl) * 0.2f); const auto& data = line_data[a]; // Check vertices exist @@ -303,7 +311,7 @@ bool DoomMapFormat::readSECTORS(ArchiveEntry* entry, MapObjectCollection& map_da float p = ui::getSplashProgress(); for (size_t a = 0; a < ns; a++) { - ui::setSplashProgress(p + ((float)a / ns) * 0.2f); + ui::setSplashProgress(p + (static_cast(a) / ns) * 0.2f); const auto& data = sect_data[a]; // Add sector @@ -346,9 +354,9 @@ bool DoomMapFormat::readTHINGS(ArchiveEntry* entry, MapObjectCollection& map_dat float p = ui::getSplashProgress(); for (size_t a = 0; a < nt; a++) { - ui::setSplashProgress(p + ((float)a / nt) * 0.2f); + ui::setSplashProgress(p + (static_cast(a) / nt) * 0.2f); MapThing* thing = map_data.addThing(std::make_unique( - Vec3d{ (double)thng_data[a].x, (double)thng_data[a].y, 0. }, + Vec3d{ static_cast(thng_data[a].x), static_cast(thng_data[a].y), 0. }, thng_data[a].type, thng_data[a].angle, thng_data[a].flags)); @@ -356,7 +364,7 @@ bool DoomMapFormat::readTHINGS(ArchiveEntry* entry, MapObjectCollection& map_dat if (game::configuration().currentGame() == "srb2") // Sonic robo blast 2 { // Srb2 stores thing's z position at the upper 12-bit from the thing's flags - thing->setZ((unsigned)(thng_data[a].flags >> 4)); + thing->setZ(static_cast(thng_data[a].flags >> 4)); } } @@ -527,7 +535,7 @@ unique_ptr DoomMapFormat::writeTHINGS(const ThingList& things) con if (game::configuration().currentGame() == "srb2") // Sonic robo blast 2 { // Srb2 stores thing's z position at the upper 12 bits from the thing's flags - data.flags = (data.flags & 0xf) | ((unsigned)thing->zPos() << 4); + data.flags = (data.flags & 0xf) | (static_cast(thing->zPos()) << 4); } entry->write(&data, 10); diff --git a/src/SLADEMap/MapFormat/DoomMapFormat.h b/src/SLADEMap/MapFormat/DoomMapFormat.h index 073ef025b..17a45616c 100644 --- a/src/SLADEMap/MapFormat/DoomMapFormat.h +++ b/src/SLADEMap/MapFormat/DoomMapFormat.h @@ -60,7 +60,7 @@ class DoomMapFormat : public MapFormatHandler short flags; }; - bool readMap(Archive::MapDesc map, MapObjectCollection& map_data, PropertyList& map_extra_props) override; + bool readMap(MapDesc map, MapObjectCollection& map_data, PropertyList& map_extra_props) override; vector> writeMap(const MapObjectCollection& map_data, const PropertyList& map_extra_props) override; diff --git a/src/SLADEMap/MapFormat/HexenMapFormat.cpp b/src/SLADEMap/MapFormat/HexenMapFormat.cpp index f4336fb1c..f02a07a59 100644 --- a/src/SLADEMap/MapFormat/HexenMapFormat.cpp +++ b/src/SLADEMap/MapFormat/HexenMapFormat.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -33,10 +33,18 @@ // ----------------------------------------------------------------------------- #include "Main.h" #include "HexenMapFormat.h" +#include "Game/ActionSpecial.h" #include "Game/Configuration.h" +#include "Game/Game.h" #include "General/UI.h" #include "SLADEMap/MapObject/MapLine.h" +#include "SLADEMap/MapObject/MapSide.h" +#include "SLADEMap/MapObject/MapThing.h" #include "SLADEMap/MapObjectCollection.h" +#include "SLADEMap/MapObjectList/LineList.h" +#include "SLADEMap/MapObjectList/SideList.h" +#include "SLADEMap/MapObjectList/ThingList.h" +#include "SLADEMap/MapObjectList/VertexList.h" using namespace slade; @@ -67,12 +75,12 @@ bool HexenMapFormat::readLINEDEFS(ArchiveEntry* entry, MapObjectCollection& map_ return true; } - auto line_data = (LineDef*)entry->rawData(); + auto line_data = reinterpret_cast(entry->rawData()); unsigned nl = entry->size() / sizeof(LineDef); float p = ui::getSplashProgress(); for (size_t a = 0; a < nl; a++) { - ui::setSplashProgress(p + ((float)a / nl) * 0.2f); + ui::setSplashProgress(p + (static_cast(a) / nl) * 0.2f); const auto& data = line_data[a]; // Check vertices exist @@ -118,8 +126,8 @@ bool HexenMapFormat::readLINEDEFS(ArchiveEntry* entry, MapObjectCollection& map_ { case game::TagType::LineId: case game::TagType::LineId1Line2: line->setId(data.args[0]); break; - case game::TagType::LineIdHi5: line->setId((data.args[0] + (data.args[4] << 8))); break; - default: break; + case game::TagType::LineIdHi5: line->setId((data.args[0] + (data.args[4] << 8))); break; + default: break; } } } @@ -148,13 +156,13 @@ bool HexenMapFormat::readTHINGS(ArchiveEntry* entry, MapObjectCollection& map_da return true; } - auto thng_data = (Thing*)entry->rawData(); + auto thng_data = reinterpret_cast(entry->rawData()); unsigned nt = entry->size() / sizeof(Thing); float p = ui::getSplashProgress(); MapObject::ArgSet args; for (size_t a = 0; a < nt; a++) { - ui::setSplashProgress(p + ((float)a / nt) * 0.2f); + ui::setSplashProgress(p + (static_cast(a) / nt) * 0.2f); const auto& data = thng_data[a]; // Set args @@ -163,7 +171,7 @@ bool HexenMapFormat::readTHINGS(ArchiveEntry* entry, MapObjectCollection& map_da // Create thing map_data.addThing(std::make_unique( - Vec3d{ (double)data.x, (double)data.y, (double)data.z }, + Vec3d{ static_cast(data.x), static_cast(data.y), static_cast(data.z) }, data.type, data.angle, data.flags, diff --git a/src/SLADEMap/MapFormat/MapFormatHandler.cpp b/src/SLADEMap/MapFormat/MapFormatHandler.cpp index 70b3dc779..2c8fbe266 100644 --- a/src/SLADEMap/MapFormat/MapFormatHandler.cpp +++ b/src/SLADEMap/MapFormat/MapFormatHandler.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -32,10 +32,10 @@ // // ----------------------------------------------------------------------------- #include "Main.h" +#include "Doom32XMapFormat.h" #include "Doom64MapFormat.h" #include "DoomMapFormat.h" #include "HexenMapFormat.h" -#include "Doom32XMapFormat.h" #include "UniversalDoomMapFormat.h" using namespace slade; @@ -49,10 +49,7 @@ using namespace slade; class NoMapFormat : public MapFormatHandler { public: - bool readMap(Archive::MapDesc map, MapObjectCollection& map_data, PropertyList& map_extra_props) override - { - return false; - } + bool readMap(MapDesc map, MapObjectCollection& map_data, PropertyList& map_extra_props) override { return false; } vector> writeMap(const MapObjectCollection& map_data, const PropertyList& map_extra_props) override @@ -76,11 +73,11 @@ unique_ptr MapFormatHandler::get(MapFormat format) { switch (format) { - case MapFormat::Doom: return std::make_unique(); - case MapFormat::Hexen: return std::make_unique(); - case MapFormat::UDMF: return std ::make_unique(); - case MapFormat::Doom64: return std::make_unique(); + case MapFormat::Doom: return std::make_unique(); + case MapFormat::Hexen: return std::make_unique(); + case MapFormat::UDMF: return std ::make_unique(); + case MapFormat::Doom64: return std::make_unique(); case MapFormat::Doom32X: return std::make_unique(); - default: return std::make_unique(); + default: return std::make_unique(); } } diff --git a/src/SLADEMap/MapFormat/MapFormatHandler.h b/src/SLADEMap/MapFormat/MapFormatHandler.h index 19ffc418c..bdc1f5cdd 100644 --- a/src/SLADEMap/MapFormat/MapFormatHandler.h +++ b/src/SLADEMap/MapFormat/MapFormatHandler.h @@ -11,7 +11,7 @@ class MapFormatHandler public: virtual ~MapFormatHandler() = default; - virtual bool readMap(Archive::MapDesc map, MapObjectCollection& map_data, PropertyList& map_extra_props) = 0; + virtual bool readMap(MapDesc map, MapObjectCollection& map_data, PropertyList& map_extra_props) = 0; virtual vector> writeMap( const MapObjectCollection& map_data, const PropertyList& map_extra_props) = 0; diff --git a/src/SLADEMap/MapFormat/UniversalDoomMapFormat.cpp b/src/SLADEMap/MapFormat/UniversalDoomMapFormat.cpp index 578655276..aa45b30f0 100644 --- a/src/SLADEMap/MapFormat/UniversalDoomMapFormat.cpp +++ b/src/SLADEMap/MapFormat/UniversalDoomMapFormat.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -36,8 +36,15 @@ #include "General/UI.h" #include "SLADEMap/MapObject/MapLine.h" #include "SLADEMap/MapObject/MapSector.h" +#include "SLADEMap/MapObject/MapSide.h" +#include "SLADEMap/MapObject/MapThing.h" #include "SLADEMap/MapObject/MapVertex.h" #include "SLADEMap/MapObjectCollection.h" +#include "SLADEMap/MapObjectList/LineList.h" +#include "SLADEMap/MapObjectList/SectorList.h" +#include "SLADEMap/MapObjectList/SideList.h" +#include "SLADEMap/MapObjectList/ThingList.h" +#include "SLADEMap/MapObjectList/VertexList.h" #include "SLADEMap/SLADEMap.h" #include "Utility/Parser.h" #include "Utility/StringUtils.h" @@ -55,7 +62,7 @@ using namespace slade; // ----------------------------------------------------------------------------- // Reads the given UDMF-format [map], populating [map_data] // ----------------------------------------------------------------------------- -bool UniversalDoomMapFormat::readMap(Archive::MapDesc map, MapObjectCollection& map_data, PropertyList& map_extra_props) +bool UniversalDoomMapFormat::readMap(MapDesc map, MapObjectCollection& map_data, PropertyList& map_extra_props) { auto m_head = map.head.lock(); if (!m_head) @@ -89,7 +96,7 @@ bool UniversalDoomMapFormat::readMap(Archive::MapDesc map, MapObjectCollection& vector defs_other; for (unsigned a = 0; a < root->nChildren(); a++) { - ui::setSplashProgress((float)a / root->nChildren()); + ui::setSplashProgress(static_cast(a) / root->nChildren()); auto node = root->childPTN(a); @@ -128,7 +135,7 @@ bool UniversalDoomMapFormat::readMap(Archive::MapDesc map, MapObjectCollection& ui::setSplashProgressMessage("Reading Vertices"); for (unsigned a = 0; a < defs_vertices.size(); a++) { - ui::setSplashProgress(((float)a / defs_vertices.size()) * 0.2f); + ui::setSplashProgress((static_cast(a) / defs_vertices.size()) * 0.2f); auto vertex = createVertex(defs_vertices[a]); if (!vertex) @@ -144,7 +151,7 @@ bool UniversalDoomMapFormat::readMap(Archive::MapDesc map, MapObjectCollection& ui::setSplashProgressMessage("Reading Sectors"); for (unsigned a = 0; a < defs_sectors.size(); a++) { - ui::setSplashProgress(0.2f + ((float)a / defs_sectors.size()) * 0.2f); + ui::setSplashProgress(0.2f + (static_cast(a) / defs_sectors.size()) * 0.2f); auto sector = createSector(defs_sectors[a]); if (!sector) @@ -160,7 +167,7 @@ bool UniversalDoomMapFormat::readMap(Archive::MapDesc map, MapObjectCollection& ui::setSplashProgressMessage("Reading Sides"); for (unsigned a = 0; a < defs_sides.size(); a++) { - ui::setSplashProgress(0.4f + ((float)a / defs_sides.size()) * 0.2f); + ui::setSplashProgress(0.4f + (static_cast(a) / defs_sides.size()) * 0.2f); auto side = createSide(defs_sides[a], map_data); if (!side) @@ -176,7 +183,7 @@ bool UniversalDoomMapFormat::readMap(Archive::MapDesc map, MapObjectCollection& ui::setSplashProgressMessage("Reading Lines"); for (unsigned a = 0; a < defs_lines.size(); a++) { - ui::setSplashProgress(0.6f + ((float)a / defs_lines.size()) * 0.2f); + ui::setSplashProgress(0.6f + (static_cast(a) / defs_lines.size()) * 0.2f); auto line = createLine(defs_lines[a], map_data); if (!line) @@ -192,7 +199,7 @@ bool UniversalDoomMapFormat::readMap(Archive::MapDesc map, MapObjectCollection& ui::setSplashProgressMessage("Reading Things"); for (unsigned a = 0; a < defs_things.size(); a++) { - ui::setSplashProgress(0.8f + ((float)a / defs_things.size()) * 0.2f); + ui::setSplashProgress(0.8f + (static_cast(a) / defs_things.size()) * 0.2f); auto thing = createThing(defs_things[a]); if (!thing) diff --git a/src/SLADEMap/MapFormat/UniversalDoomMapFormat.h b/src/SLADEMap/MapFormat/UniversalDoomMapFormat.h index 560f5e1c3..109024ef4 100644 --- a/src/SLADEMap/MapFormat/UniversalDoomMapFormat.h +++ b/src/SLADEMap/MapFormat/UniversalDoomMapFormat.h @@ -14,7 +14,7 @@ class ParseTreeNode; class UniversalDoomMapFormat : public MapFormatHandler { public: - bool readMap(Archive::MapDesc map, MapObjectCollection& map_data, PropertyList& map_extra_props) override; + bool readMap(MapDesc map, MapObjectCollection& map_data, PropertyList& map_extra_props) override; vector> writeMap(const MapObjectCollection& map_data, const PropertyList& map_extra_props) override; diff --git a/src/SLADEMap/MapObject/MapLine.cpp b/src/SLADEMap/MapObject/MapLine.cpp index 4857f7d48..5e9d9bdff 100644 --- a/src/SLADEMap/MapObject/MapLine.cpp +++ b/src/SLADEMap/MapObject/MapLine.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -31,6 +31,7 @@ // ----------------------------------------------------------------------------- #include "Main.h" #include "MapLine.h" +#include "MapSector.h" #include "MapSide.h" #include "MapVertex.h" #include "SLADEMap/SLADEMap.h" @@ -51,7 +52,7 @@ using namespace slade; // ----------------------------------------------------------------------------- // MapLine class constructor // ----------------------------------------------------------------------------- -MapLine::MapLine(MapVertex* v1, MapVertex* v2, MapSide* s1, MapSide* s2, int special, int flags, ArgSet args) : +MapLine::MapLine(MapVertex* v1, MapVertex* v2, MapSide* s1, MapSide* s2, int special, int flags, const ArgSet& args) : MapObject(Type::Line), vertex1_{ v1 }, vertex2_{ v2 }, @@ -77,7 +78,7 @@ MapLine::MapLine(MapVertex* v1, MapVertex* v2, MapSide* s1, MapSide* s2, int spe // ----------------------------------------------------------------------------- // MapLine class constructor from UDMF definition // ----------------------------------------------------------------------------- -MapLine::MapLine(MapVertex* v1, MapVertex* v2, MapSide* s1, MapSide* s2, ParseTreeNode* udmf_def) : +MapLine::MapLine(MapVertex* v1, MapVertex* v2, MapSide* s1, MapSide* s2, const ParseTreeNode* udmf_def) : MapObject(Type::Line), vertex1_{ v1 }, vertex2_{ v2 }, @@ -689,7 +690,7 @@ Vec2d MapLine::dirTabPoint(double tab_length) // ----------------------------------------------------------------------------- // Returns the minimum distance from the point to the line // ----------------------------------------------------------------------------- -double MapLine::distanceTo(Vec2d point) +double MapLine::distanceTo(const Vec2d& point) { // Update length data if needed if (length_ < 0) @@ -717,7 +718,7 @@ double MapLine::distanceTo(Vec2d point) } // Minimum gap between planes for a texture to be considered missing -static const float EPSILON = 0.001f; +static constexpr float EPSILON = 0.001f; // ----------------------------------------------------------------------------- // Returns a flag set of any parts of the line that require a texture @@ -783,7 +784,7 @@ int MapLine::needsTexture() const // Returns true if this line overlaps with [other] // (ie. both lines share the same vertices) // ----------------------------------------------------------------------------- -bool MapLine::overlaps(MapLine* other) const +bool MapLine::overlaps(const MapLine* other) const { return other != this && (vertex1_ == other->vertex1_ && vertex2_ == other->vertex2_ @@ -794,7 +795,7 @@ bool MapLine::overlaps(MapLine* other) const // Returns true if this line intersects with [other]. // If an intersection occurs, [intersect_point] is set to the intersection point // ----------------------------------------------------------------------------- -bool MapLine::intersects(MapLine* other, Vec2d& intersect_point) const +bool MapLine::intersects(const MapLine* other, Vec2d& intersect_point) const { return math::linesIntersect(seg(), other->seg(), intersect_point); } @@ -893,11 +894,11 @@ void MapLine::writeBackup(Backup* backup) if (side1_) backup->props_internal["s1"] = side1_->objId(); else - backup->props_internal["s1"] = (unsigned)0; + backup->props_internal["s1"] = static_cast(0); if (side2_) backup->props_internal["s2"] = side2_->objId(); else - backup->props_internal["s2"] = (unsigned)0; + backup->props_internal["s2"] = static_cast(0); // Flags backup->props_internal[PROP_FLAGS] = flags_; diff --git a/src/SLADEMap/MapObject/MapLine.h b/src/SLADEMap/MapObject/MapLine.h index d4b7ca5a9..e3b58fd79 100644 --- a/src/SLADEMap/MapObject/MapLine.h +++ b/src/SLADEMap/MapObject/MapLine.h @@ -34,15 +34,15 @@ class MapLine : public MapObject inline static const string PROP_ARG4 = "arg4"; MapLine( - MapVertex* v1, - MapVertex* v2, - MapSide* s1 = nullptr, - MapSide* s2 = nullptr, - int special = 0, - int flags = 0, - ArgSet args = {}); - MapLine(MapVertex* v1, MapVertex* v2, MapSide* s1, MapSide* s2, ParseTreeNode* udmf_def); - ~MapLine() = default; + MapVertex* v1, + MapVertex* v2, + MapSide* s1 = nullptr, + MapSide* s2 = nullptr, + int special = 0, + int flags = 0, + const ArgSet& args = {}); + MapLine(MapVertex* v1, MapVertex* v2, MapSide* s1, MapSide* s2, const ParseTreeNode* udmf_def); + ~MapLine() override = default; bool isOk() const { return vertex1_ && vertex2_; } @@ -99,10 +99,10 @@ class MapLine : public MapObject bool doubleSector() const; Vec2d frontVector(); Vec2d dirTabPoint(double tab_length = 0.); - double distanceTo(Vec2d point); + double distanceTo(const Vec2d& point); int needsTexture() const; - bool overlaps(MapLine* other) const; - bool intersects(MapLine* other, Vec2d& intersect_point) const; + bool overlaps(const MapLine* other) const; + bool intersects(const MapLine* other, Vec2d& intersect_point) const; void clearUnneededTextures() const; void resetInternals(); diff --git a/src/SLADEMap/MapObject/MapObject.cpp b/src/SLADEMap/MapObject/MapObject.cpp index c4ed787df..6e7e22c89 100644 --- a/src/SLADEMap/MapObject/MapObject.cpp +++ b/src/SLADEMap/MapObject/MapObject.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -34,7 +34,7 @@ #include "MapObject.h" #include "App.h" #include "Game/Configuration.h" -#include "SLADEMap/SLADEMap.h" +#include "Game/UDMFProperty.h" using namespace slade; @@ -61,7 +61,9 @@ long prop_backup_time = -1; // MapObject class constructor // ----------------------------------------------------------------------------- MapObject::MapObject(Type type, SLADEMap* parent) : - parent_map_{ parent }, modified_time_{ app::runTimer() }, type_{ type } + parent_map_{ parent }, + modified_time_{ app::runTimer() }, + type_{ type } { } @@ -81,11 +83,11 @@ string MapObject::typeName() const switch (type_) { case Type::Vertex: return "Vertex"; - case Type::Side: return "Side"; - case Type::Line: return "Line"; + case Type::Side: return "Side"; + case Type::Line: return "Line"; case Type::Sector: return "Sector"; - case Type::Thing: return "Thing"; - default: return "Unknown"; + case Type::Thing: return "Thing"; + default: return "Unknown"; } } @@ -343,7 +345,7 @@ void MapObject::endPropBackup() // If all values are the same, [value] is set and returns true, otherwise // just returns false // ----------------------------------------------------------------------------- -bool MapObject::multiBoolProperty(vector& objects, string_view prop, bool& value) +bool MapObject::multiBoolProperty(const vector& objects, string_view prop, bool& value) { // Check objects given if (objects.empty()) @@ -368,7 +370,7 @@ bool MapObject::multiBoolProperty(vector& objects, string_view prop, // If all values are the same, [value] is set and returns true, otherwise // just returns false // ----------------------------------------------------------------------------- -bool MapObject::multiIntProperty(vector& objects, string_view prop, int& value) +bool MapObject::multiIntProperty(const vector& objects, string_view prop, int& value) { // Check objects given if (objects.empty()) @@ -393,7 +395,7 @@ bool MapObject::multiIntProperty(vector& objects, string_view prop, // If all values are the same, [value] is set and returns true, otherwise // just returns false // ----------------------------------------------------------------------------- -bool MapObject::multiFloatProperty(vector& objects, string_view prop, double& value) +bool MapObject::multiFloatProperty(const vector& objects, string_view prop, double& value) { // Check objects given if (objects.empty()) @@ -418,7 +420,7 @@ bool MapObject::multiFloatProperty(vector& objects, string_view prop // If all values are the same, [value] is set and returns true, otherwise // just returns false // ----------------------------------------------------------------------------- -bool MapObject::multiStringProperty(vector& objects, string_view prop, string& value) +bool MapObject::multiStringProperty(const vector& objects, string_view prop, string& value) { // Check objects given if (objects.empty()) diff --git a/src/SLADEMap/MapObject/MapObject.h b/src/SLADEMap/MapObject/MapObject.h index f35c1db42..62711e75d 100644 --- a/src/SLADEMap/MapObject/MapObject.h +++ b/src/SLADEMap/MapObject/MapObject.h @@ -103,10 +103,10 @@ class MapObject static void beginPropBackup(long current_time); static void endPropBackup(); - static bool multiBoolProperty(vector& objects, string_view prop, bool& value); - static bool multiIntProperty(vector& objects, string_view prop, int& value); - static bool multiFloatProperty(vector& objects, string_view prop, double& value); - static bool multiStringProperty(vector& objects, string_view prop, string& value); + static bool multiBoolProperty(const vector& objects, string_view prop, bool& value); + static bool multiIntProperty(const vector& objects, string_view prop, int& value); + static bool multiFloatProperty(const vector& objects, string_view prop, double& value); + static bool multiStringProperty(const vector& objects, string_view prop, string& value); protected: unsigned index_ = 0; diff --git a/src/SLADEMap/MapObject/MapSector.cpp b/src/SLADEMap/MapObject/MapSector.cpp index 40886dd27..1beb9ef03 100644 --- a/src/SLADEMap/MapObject/MapSector.cpp +++ b/src/SLADEMap/MapObject/MapSector.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -33,9 +33,15 @@ #include "MapSector.h" #include "App.h" #include "Game/Configuration.h" +#include "MapLine.h" +#include "MapSide.h" +#include "MapVertex.h" +#include "SLADEMap/MapObjectList/SectorList.h" +#include "SLADEMap/MapSpecials.h" #include "SLADEMap/SLADEMap.h" #include "Utility/MathStuff.h" #include "Utility/Parser.h" +#include "Utility/Polygon2D.h" using namespace slade; @@ -64,6 +70,7 @@ MapSector::MapSector( light_{ light }, special_{ special }, id_{ id }, + polygon_{ new Polygon2D() }, geometry_updated_{ app::runTimer() } { } @@ -72,7 +79,9 @@ MapSector::MapSector( // MapSector class constructor from UDMF definition // ----------------------------------------------------------------------------- MapSector::MapSector(string_view f_tex, string_view c_tex, const ParseTreeNode* udmf_def) : - MapObject(Type::Sector), floor_{ f_tex }, ceiling_{ c_tex } + MapObject(Type::Sector), + floor_{ f_tex }, + ceiling_{ c_tex } { // Set UDMF defaults light_ = 160; @@ -213,7 +222,7 @@ void MapSector::setFloatProperty(string_view key, double value) && (key == "xscalefloor" || key == "yscalefloor" || key == "xscaleceiling" || key == "yscaleceiling")) || (game::configuration().featureSupported(UDMFFeature::FlatRotation) && (key == "rotationfloor" || key == "rotationceiling"))) - polygon_.setTexture(0); // Clear texture to force update + polygon_->setTexture(0); // Clear texture to force update } MapObject::setFloatProperty(key, value); @@ -394,17 +403,17 @@ Polygon2D* MapSector::polygon() { if (poly_needsupdate_) { - polygon_.openSector(this); + polygon_->openSector(this); poly_needsupdate_ = false; } - return &polygon_; + return polygon_.get(); } // ----------------------------------------------------------------------------- // Returns true if the given [point] is inside the sector // ----------------------------------------------------------------------------- -bool MapSector::containsPoint(Vec2d point) +bool MapSector::containsPoint(const Vec2d& point) { // Check with bbox first if (!boundingBox().contains(point)) @@ -444,7 +453,7 @@ bool MapSector::containsPoint(Vec2d point) // ----------------------------------------------------------------------------- // Returns the minimum distance from the point to the closest line in the sector // ----------------------------------------------------------------------------- -double MapSector::distanceTo(Vec2d point, double maxdist) +double MapSector::distanceTo(const Vec2d& point, double maxdist) { // Init if (maxdist < 0) @@ -677,7 +686,7 @@ ColRGBA MapSector::colourAt(int where, bool fullbright) ll = 0; // Calculate and return the colour - float lightmult = (float)ll / 255.0f; + float lightmult = static_cast(ll) / 255.0f; return col.ampf(lightmult, lightmult, lightmult, 1.0f); } } @@ -735,7 +744,7 @@ ColRGBA MapSector::colourAt(int where, bool fullbright) ll = 0; // Calculate and return the colour - float lightmult = (float)ll / 255.0f; + float lightmult = static_cast(ll) / 255.0f; return { static_cast(wxcol.Blue() * lightmult), static_cast(wxcol.Green() * lightmult), static_cast(wxcol.Red() * lightmult), diff --git a/src/SLADEMap/MapObject/MapSector.h b/src/SLADEMap/MapObject/MapSector.h index e990fded2..8722138ee 100644 --- a/src/SLADEMap/MapObject/MapSector.h +++ b/src/SLADEMap/MapObject/MapSector.h @@ -2,10 +2,11 @@ #include "MapObject.h" #include "Utility/Colour.h" -#include "Utility/Polygon2D.h" namespace slade { +class Polygon2D; + class MapSector : public MapObject { friend class SLADEMap; @@ -25,7 +26,9 @@ class MapSector : public MapObject Plane plane = { 0., 0., 1., 0. }; Surface(string_view texture = "", int height = 0, const Plane& plane = { 0., 0., 1., 0. }) : - texture{ texture }, height{ height }, plane{ plane } + texture{ texture }, + height{ height }, + plane{ plane } { } }; @@ -126,8 +129,8 @@ class MapSector : public MapObject vector& connectedSides() { return connected_sides_; } void resetPolygon() { poly_needsupdate_ = true; } Polygon2D* polygon(); - bool containsPoint(Vec2d point); - double distanceTo(Vec2d point, double maxdist = -1); + bool containsPoint(const Vec2d& point); + double distanceTo(const Vec2d& point, double maxdist = -1); bool putLines(vector& list) const; bool putVertices(vector& list) const; bool putVertices(vector& list) const; @@ -171,13 +174,13 @@ class MapSector : public MapObject short id_ = 0; // Internal info - vector connected_sides_; - BBox bbox_; - Polygon2D polygon_; - bool poly_needsupdate_ = true; - long geometry_updated_ = 0; - Vec2d text_point_; - vector extra_floors_; + vector connected_sides_; + BBox bbox_; + unique_ptr polygon_; + bool poly_needsupdate_ = true; + long geometry_updated_ = 0; + Vec2d text_point_; + vector extra_floors_; void setGeometryUpdated(); }; diff --git a/src/SLADEMap/MapObject/MapSide.cpp b/src/SLADEMap/MapObject/MapSide.cpp index 01b33234b..e4e03f24b 100644 --- a/src/SLADEMap/MapObject/MapSide.cpp +++ b/src/SLADEMap/MapObject/MapSide.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -30,11 +30,13 @@ // // ----------------------------------------------------------------------------- #include "Main.h" -#include "MapSide.h" + #include "Game/Configuration.h" +#include "MapSector.h" +#include "MapSide.h" +#include "SLADEMap/MapObjectList/SideList.h" #include "SLADEMap/SLADEMap.h" #include "Utility/Parser.h" -#include "Utility/StringUtils.h" using namespace slade; @@ -50,11 +52,11 @@ using namespace slade; // MapSide class constructor // ----------------------------------------------------------------------------- MapSide::MapSide( - MapSector* sector, - string_view tex_upper, - string_view tex_middle, - string_view tex_lower, - Vec2i tex_offset) : + MapSector* sector, + string_view tex_upper, + string_view tex_middle, + string_view tex_lower, + const Vec2i& tex_offset) : MapObject{ Type::Side }, sector_{ sector }, tex_upper_{ tex_upper }, @@ -69,7 +71,7 @@ MapSide::MapSide( // ----------------------------------------------------------------------------- // MapSide class constructor from UDMF definition // ----------------------------------------------------------------------------- -MapSide::MapSide(MapSector* sector, ParseTreeNode* udmf_def) : MapObject{ Type::Side }, sector_{ sector } +MapSide::MapSide(MapSector* sector, const ParseTreeNode* udmf_def) : MapObject{ Type::Side }, sector_{ sector } { if (sector) sector->connectSide(this); diff --git a/src/SLADEMap/MapObject/MapSide.h b/src/SLADEMap/MapObject/MapSide.h index 3b57f5624..33d9320e5 100644 --- a/src/SLADEMap/MapObject/MapSide.h +++ b/src/SLADEMap/MapObject/MapSide.h @@ -22,14 +22,14 @@ class MapSide : public MapObject inline static const string PROP_OFFSETY = "offsety"; MapSide( - MapSector* sector = nullptr, - string_view tex_upper = TEX_NONE, - string_view tex_middle = TEX_NONE, - string_view tex_lower = TEX_NONE, - Vec2i tex_offset = { 0, 0 }); - MapSide(MapSector* sector, ParseTreeNode* udmf_def); + MapSector* sector = nullptr, + string_view tex_upper = TEX_NONE, + string_view tex_middle = TEX_NONE, + string_view tex_lower = TEX_NONE, + const Vec2i& tex_offset = { 0, 0 }); + MapSide(MapSector* sector, const ParseTreeNode* udmf_def); MapSide(MapSector* sector, MapSide* copy_side); - ~MapSide() = default; + ~MapSide() override = default; void copy(MapObject* c) override; diff --git a/src/SLADEMap/MapObject/MapThing.cpp b/src/SLADEMap/MapObject/MapThing.cpp index 4d1d0f786..9e6fa1b92 100644 --- a/src/SLADEMap/MapObject/MapThing.cpp +++ b/src/SLADEMap/MapObject/MapThing.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -62,7 +62,7 @@ MapThing::MapThing(const Vec3d& pos, short type, short angle, short flags, const // ----------------------------------------------------------------------------- // MapThing class constructor from UDMF definition // ----------------------------------------------------------------------------- -MapThing::MapThing(const Vec3d& pos, short type, ParseTreeNode* def) : +MapThing::MapThing(const Vec3d& pos, short type, const ParseTreeNode* def) : MapObject(Type::Thing), type_{ type }, position_{ pos.x, pos.y }, @@ -121,11 +121,11 @@ int MapThing::intProperty(string_view key) if (key == PROP_TYPE) return type_; if (key == PROP_X) - return (int)position_.x; + return static_cast(position_.x); if (key == PROP_Y) - return (int)position_.y; + return static_cast(position_.y); if (key == PROP_Z) - return (int)z_; + return static_cast(z_); if (key == PROP_ANGLE) return angle_; if (key == PROP_FLAGS) @@ -251,7 +251,7 @@ void MapThing::copy(MapObject* c) // Sets the position of the thing to [pos]. // If [modify] is false, the thing won't be marked as modified // ----------------------------------------------------------------------------- -void MapThing::move(Vec2d pos, bool modify) +void MapThing::move(const Vec2d& pos, bool modify) { if (modify) setModified(); @@ -291,7 +291,7 @@ void MapThing::setAngle(int angle, bool modify) // Sets the angle (direction) of the thing to be facing towards [point]. // If [modify] is false, the thing won't be marked as modified // ----------------------------------------------------------------------------- -void MapThing::setAnglePoint(Vec2d point, bool modify) +void MapThing::setAnglePoint(const Vec2d& point, bool modify) { // Calculate direction vector Vec2d vec(point.x - position_.x, point.y - position_.y); diff --git a/src/SLADEMap/MapObject/MapThing.h b/src/SLADEMap/MapObject/MapThing.h index 43780dab0..eb14f8704 100644 --- a/src/SLADEMap/MapObject/MapThing.h +++ b/src/SLADEMap/MapObject/MapThing.h @@ -32,8 +32,8 @@ class MapThing : public MapObject const ArgSet& args = {}, int id = 0, int special = 0); - MapThing(const Vec3d& pos, short type, ParseTreeNode* def); - ~MapThing() = default; + MapThing(const Vec3d& pos, short type, const ParseTreeNode* def); + ~MapThing() override = default; double xPos() const { return position_.x; } double yPos() const { return position_.y; } @@ -58,11 +58,11 @@ class MapThing : public MapObject void copy(MapObject* c) override; - void move(Vec2d pos, bool modify = true); + void move(const Vec2d& pos, bool modify = true); void setZ(double z); void setType(int type); void setAngle(int angle, bool modify = true); - void setAnglePoint(Vec2d point, bool modify = true); + void setAnglePoint(const Vec2d& point, bool modify = true); void setId(int id); void setFlags(int flags); void setFlag(int flag); diff --git a/src/SLADEMap/MapObject/MapVertex.cpp b/src/SLADEMap/MapObject/MapVertex.cpp index 2cd26f836..2f8851e68 100644 --- a/src/SLADEMap/MapObject/MapVertex.cpp +++ b/src/SLADEMap/MapObject/MapVertex.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -30,6 +30,8 @@ // // ----------------------------------------------------------------------------- #include "Main.h" + +#include "MapLine.h" #include "MapVertex.h" #include "SLADEMap/SLADEMap.h" #include "Utility/Parser.h" @@ -52,7 +54,7 @@ MapVertex::MapVertex(const Vec2d& pos) : MapObject(Type::Vertex), position_{ pos // ----------------------------------------------------------------------------- // MapVertex class constructor from UDMF definition // ----------------------------------------------------------------------------- -MapVertex::MapVertex(const Vec2d& pos, ParseTreeNode* udmf_def) : MapObject(Type::Vertex), position_{ pos } +MapVertex::MapVertex(const Vec2d& pos, const ParseTreeNode* udmf_def) : MapObject(Type::Vertex), position_{ pos } { // Set properties from UDMF definition ParseTreeNode* prop; @@ -100,9 +102,9 @@ void MapVertex::move(double nx, double ny) int MapVertex::intProperty(string_view key) { if (key == PROP_X) - return (int)position_.x; + return static_cast(position_.x); else if (key == PROP_Y) - return (int)position_.y; + return static_cast(position_.y); else return MapObject::intProperty(key); } @@ -182,7 +184,7 @@ void MapVertex::connectLine(MapLine* line) // ----------------------------------------------------------------------------- // Removes [line] from the list of lines connected to this vertex // ----------------------------------------------------------------------------- -void MapVertex::disconnectLine(MapLine* line) +void MapVertex::disconnectLine(const MapLine* line) { for (unsigned a = 0; a < connected_lines_.size(); a++) { @@ -197,7 +199,7 @@ void MapVertex::disconnectLine(MapLine* line) // ----------------------------------------------------------------------------- // Returns the connected line at [index] // ----------------------------------------------------------------------------- -MapLine* MapVertex::connectedLine(unsigned index) +MapLine* MapVertex::connectedLine(unsigned index) const { if (index >= connected_lines_.size()) return nullptr; diff --git a/src/SLADEMap/MapObject/MapVertex.h b/src/SLADEMap/MapObject/MapVertex.h index f2a13bd5f..69fbed783 100644 --- a/src/SLADEMap/MapObject/MapVertex.h +++ b/src/SLADEMap/MapObject/MapVertex.h @@ -16,8 +16,8 @@ class MapVertex : public MapObject inline static const string PROP_Y = "y"; MapVertex(const Vec2d& pos); - MapVertex(const Vec2d& pos, ParseTreeNode* udmf_def); - ~MapVertex() = default; + MapVertex(const Vec2d& pos, const ParseTreeNode* udmf_def); + ~MapVertex() override = default; double xPos() const { return position_.x; } double yPos() const { return position_.y; } @@ -34,9 +34,9 @@ class MapVertex : public MapObject bool scriptCanModifyProp(string_view key) override; void connectLine(MapLine* line); - void disconnectLine(MapLine* line); + void disconnectLine(const MapLine* line); unsigned nConnectedLines() const { return connected_lines_.size(); } - MapLine* connectedLine(unsigned index); + MapLine* connectedLine(unsigned index) const; void clearConnectedLines() { connected_lines_.clear(); } bool isDetached() const { return connected_lines_.empty(); } diff --git a/src/SLADEMap/MapObjectCollection.cpp b/src/SLADEMap/MapObjectCollection.cpp index c99c60077..f92c27da5 100644 --- a/src/SLADEMap/MapObjectCollection.cpp +++ b/src/SLADEMap/MapObjectCollection.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -35,16 +35,51 @@ #include "Game/Configuration.h" #include "MapObject/MapLine.h" #include "MapObject/MapSector.h" +#include "MapObject/MapSide.h" +#include "MapObject/MapThing.h" +#include "MapObject/MapVertex.h" +#include "MapObjectList/LineList.h" +#include "MapObjectList/SectorList.h" +#include "MapObjectList/SideList.h" +#include "MapObjectList/ThingList.h" +#include "MapObjectList/VertexList.h" #include "SLADEMap.h" using namespace slade; +namespace +{ +template +void putModifiedObjects(const MapObjectList& objects, long since, vector& modified_objects) +{ + for (const auto& object : objects) + if (object->modifiedTime() >= since) + modified_objects.push_back(object); +} + +template bool anyModifiedSince(const MapObjectList& objects, long since) +{ + for (const auto& object : objects) + if (object->modifiedTime() > since) + return true; + + return false; +} +} // namespace + + // ----------------------------------------------------------------------------- // MapObjectCollection class constructor // ----------------------------------------------------------------------------- MapObjectCollection::MapObjectCollection(SLADEMap* parent_map) : parent_map_{ parent_map } { + vertices_ = std::make_unique(); + sides_ = std::make_unique(); + lines_ = std::make_unique(); + sectors_ = std::make_unique(); + things_ = std::make_unique(); + // Object id 0 is always null objects_.emplace_back(nullptr, false); } @@ -63,7 +98,7 @@ void MapObjectCollection::addMapObject(unique_ptr object) // Removes [object] from the map // (keeps it in the objects list, but removes the 'in map' flag) // ----------------------------------------------------------------------------- -void MapObjectCollection::removeMapObject(MapObject* object) +void MapObjectCollection::removeMapObject(const MapObject* object) { objects_[object->obj_id_].in_map = false; } @@ -75,27 +110,27 @@ void MapObjectCollection::putObjectIdList(MapObject::Type type, vector { if (type == MapObject::Type::Vertex) { - for (auto& vertex : vertices_) + for (auto& vertex : *vertices_) list.push_back(vertex->obj_id_); } else if (type == MapObject::Type::Line) { - for (auto& line : lines_) + for (auto& line : *lines_) list.push_back(line->obj_id_); } else if (type == MapObject::Type::Side) { - for (auto& side : sides_) + for (auto& side : *sides_) list.push_back(side->obj_id_); } else if (type == MapObject::Type::Sector) { - for (auto& sector : sectors_) + for (auto& sector : *sectors_) list.push_back(sector->obj_id_); } else if (type == MapObject::Type::Thing) { - for (auto& thing : things_) + for (auto& thing : *things_) list.push_back(thing->obj_id_); } } @@ -104,81 +139,91 @@ void MapObjectCollection::putObjectIdList(MapObject::Type type, vector // Add all object ids in [list] to the map as [type], clearing any objects of // [type] currently in the map // ----------------------------------------------------------------------------- -void MapObjectCollection::restoreObjectIdList(MapObject::Type type, vector& list) +void MapObjectCollection::restoreObjectIdList(MapObject::Type type, const vector& list) { if (type == MapObject::Type::Vertex) { + auto vertices = *vertices_; + // Clear - for (auto& vertex : vertices_) + for (auto& vertex : vertices) objects_[vertex->obj_id_].in_map = false; - vertices_.clear(); + vertices.clear(); // Restore for (auto id : list) { objects_[id].in_map = true; - vertices_.add(dynamic_cast(objects_[id].object.get())); - vertices_.last()->index_ = vertices_.size() - 1; + vertices.add(dynamic_cast(objects_[id].object.get())); + vertices.last()->index_ = vertices.size() - 1; } } else if (type == MapObject::Type::Line) { + auto lines = *lines_; + // Clear - for (auto& line : lines_) + for (auto& line : lines) objects_[line->obj_id_].in_map = false; - lines_.clear(); + lines.clear(); // Restore for (auto id : list) { objects_[id].in_map = true; - lines_.add(dynamic_cast(objects_[id].object.get())); - lines_.back()->index_ = lines_.size() - 1; + lines.add(dynamic_cast(objects_[id].object.get())); + lines.back()->index_ = lines.size() - 1; } } else if (type == MapObject::Type::Side) { + auto sides = *sides_; + // Clear - for (auto& side : sides_) + for (auto& side : sides) objects_[side->obj_id_].in_map = false; - sides_.clear(); + sides.clear(); // Restore for (auto id : list) { objects_[id].in_map = true; - sides_.add(dynamic_cast(objects_[id].object.get())); - sides_.back()->index_ = sides_.size() - 1; + sides.add(dynamic_cast(objects_[id].object.get())); + sides.back()->index_ = sides.size() - 1; } } else if (type == MapObject::Type::Sector) { + auto sectors = *sectors_; + // Clear - for (auto& sector : sectors_) + for (auto& sector : sectors) objects_[sector->obj_id_].in_map = false; - sectors_.clear(); + sectors.clear(); // Restore for (auto id : list) { objects_[id].in_map = true; - sectors_.add(dynamic_cast(objects_[id].object.get())); - sectors_.back()->index_ = sectors_.size() - 1; + sectors.add(dynamic_cast(objects_[id].object.get())); + sectors.back()->index_ = sectors.size() - 1; } } else if (type == MapObject::Type::Thing) { + auto things = *things_; + // Clear - for (auto& thing : things_) + for (auto& thing : things) objects_[thing->obj_id_].in_map = false; - things_.clear(); + things.clear(); // Restore for (auto id : list) { objects_[id].in_map = true; - things_.add(dynamic_cast(objects_[id].object.get())); - things_.back()->index_ = things_.size() - 1; + things.add(dynamic_cast(objects_[id].object.get())); + things.back()->index_ = things.size() - 1; } } } @@ -186,27 +231,27 @@ void MapObjectCollection::restoreObjectIdList(MapObject::Type type, vectorindex_ = a; + for (unsigned a = 0; a < vertices_->size(); a++) + (*vertices_)[a]->index_ = a; // Side indices - for (unsigned a = 0; a < sides_.size(); a++) - sides_[a]->index_ = a; + for (unsigned a = 0; a < sides_->size(); a++) + (*sides_)[a]->index_ = a; // Line indices - for (unsigned a = 0; a < lines_.size(); a++) - lines_[a]->index_ = a; + for (unsigned a = 0; a < lines_->size(); a++) + (*lines_)[a]->index_ = a; // Sector indices - for (unsigned a = 0; a < sectors_.size(); a++) - sectors_[a]->index_ = a; + for (unsigned a = 0; a < sectors_->size(); a++) + (*sectors_)[a]->index_ = a; // Thing indices - for (unsigned a = 0; a < things_.size(); a++) - things_[a]->index_ = a; + for (unsigned a = 0; a < things_->size(); a++) + (*things_)[a]->index_ = a; } // ----------------------------------------------------------------------------- @@ -215,11 +260,11 @@ void MapObjectCollection::refreshIndices() void MapObjectCollection::clear() { // Clear lists - sides_.clear(); - lines_.clear(); - vertices_.clear(); - sectors_.clear(); - things_.clear(); + sides_->clear(); + lines_->clear(); + vertices_->clear(); + sectors_->clear(); + things_->clear(); // Clear map objects objects_.clear(); @@ -231,7 +276,7 @@ void MapObjectCollection::clear() // ----------------------------------------------------------------------------- // Removes [vertex] from the map // ----------------------------------------------------------------------------- -bool MapObjectCollection::removeVertex(MapVertex* vertex, bool merge_lines) +bool MapObjectCollection::removeVertex(const MapVertex* vertex, bool merge_lines) { // Check vertex was given if (!vertex) @@ -245,13 +290,15 @@ bool MapObjectCollection::removeVertex(MapVertex* vertex, bool merge_lines) // ----------------------------------------------------------------------------- bool MapObjectCollection::removeVertex(unsigned index, bool merge_lines) { + auto vertices = *vertices_; + // Check index - if (index >= vertices_.size()) + if (index >= vertices.size()) return false; // Check if we should merge connected lines bool merged = false; - auto vertex = vertices_[index]; + auto vertex = vertices[index]; if (merge_lines && vertex->nConnectedLines() == 2) { // Get other end vertex of second connected line @@ -298,7 +345,7 @@ bool MapObjectCollection::removeVertex(unsigned index, bool merge_lines) // Remove the vertex removeMapObject(vertex); - vertices_.remove(index); + vertices.remove(index); if (parent_map_) parent_map_->setGeometryUpdated(); @@ -309,7 +356,7 @@ bool MapObjectCollection::removeVertex(unsigned index, bool merge_lines) // ----------------------------------------------------------------------------- // Removes [line] from the map // ----------------------------------------------------------------------------- -bool MapObjectCollection::removeLine(MapLine* line) +bool MapObjectCollection::removeLine(const MapLine* line) { // Check line was given if (!line) @@ -323,14 +370,16 @@ bool MapObjectCollection::removeLine(MapLine* line) // ----------------------------------------------------------------------------- bool MapObjectCollection::removeLine(unsigned index) { + auto lines = *lines_; + // Check index - if (index >= lines_.size()) + if (index >= lines.size()) return false; - log::info(4, "id {} index {} objindex {}", lines_[index]->obj_id_, index, lines_[index]->index_); + log::info(4, "id {} index {} objindex {}", lines[index]->obj_id_, index, lines[index]->index_); // Init - auto line = lines_[index]; + auto line = lines[index]; line->resetInternals(); // Remove the line's sides @@ -345,7 +394,7 @@ bool MapObjectCollection::removeLine(unsigned index) // Remove the line removeMapObject(line); - lines_.remove(index); + lines.remove(index); if (parent_map_) parent_map_->setGeometryUpdated(); @@ -356,7 +405,7 @@ bool MapObjectCollection::removeLine(unsigned index) // ----------------------------------------------------------------------------- // Removes [side] from the map // ----------------------------------------------------------------------------- -bool MapObjectCollection::removeSide(MapSide* side, bool remove_from_line) +bool MapObjectCollection::removeSide(const MapSide* side, bool remove_from_line) { // Check side was given if (!side) @@ -370,18 +419,20 @@ bool MapObjectCollection::removeSide(MapSide* side, bool remove_from_line) // ----------------------------------------------------------------------------- bool MapObjectCollection::removeSide(unsigned index, bool remove_from_line) { + auto sides = *sides_; + // Check index - if (index >= sides_.size()) + if (index >= sides.size()) return false; if (remove_from_line) { // Remove from parent line - auto l = sides_[index]->parentLine(); + auto l = sides[index]->parentLine(); l->setModified(); - if (l->s1() == sides_[index]) + if (l->s1() == sides[index]) l->setS1(nullptr); - if (l->s2() == sides_[index]) + if (l->s2() == sides[index]) l->setS2(nullptr); // Set appropriate line flags @@ -393,13 +444,13 @@ bool MapObjectCollection::removeSide(unsigned index, bool remove_from_line) } // Remove side from its sector, if any - if (sides_[index]->sector()) + if (sides[index]->sector()) { - auto sector = sides_[index]->sector(); + auto sector = sides[index]->sector(); auto& connected_sides = sector->connectedSides(); for (unsigned a = 0; a < connected_sides.size(); a++) { - if (connected_sides[a] == sides_[index]) + if (connected_sides[a] == sides[index]) { connected_sides.erase(connected_sides.begin() + a); @@ -413,8 +464,8 @@ bool MapObjectCollection::removeSide(unsigned index, bool remove_from_line) } // Remove the side - removeMapObject(sides_[index]); - sides_.remove(index); + removeMapObject(sides[index]); + sides.remove(index); return true; } @@ -422,7 +473,7 @@ bool MapObjectCollection::removeSide(unsigned index, bool remove_from_line) // ----------------------------------------------------------------------------- // Removes [sector] from the map // ----------------------------------------------------------------------------- -bool MapObjectCollection::removeSector(MapSector* sector) +bool MapObjectCollection::removeSector(const MapSector* sector) { // Check sector was given if (!sector) @@ -436,13 +487,15 @@ bool MapObjectCollection::removeSector(MapSector* sector) // ----------------------------------------------------------------------------- bool MapObjectCollection::removeSector(unsigned index) { + auto sectors = *sectors_; + // Check index - if (index >= sectors_.size()) + if (index >= sectors.size()) return false; // Remove the sector - removeMapObject(sectors_[index]); - sectors_.remove(index); + removeMapObject(sectors[index]); + sectors.remove(index); return true; } @@ -450,7 +503,7 @@ bool MapObjectCollection::removeSector(unsigned index) // ----------------------------------------------------------------------------- // Removes [thing] from the map // ----------------------------------------------------------------------------- -bool MapObjectCollection::removeThing(MapThing* thing) +bool MapObjectCollection::removeThing(const MapThing* thing) { // Check thing was given if (!thing) @@ -464,13 +517,15 @@ bool MapObjectCollection::removeThing(MapThing* thing) // ----------------------------------------------------------------------------- bool MapObjectCollection::removeThing(unsigned index) { + auto things = *things_; + // Check index - if (index >= things_.size()) + if (index >= things.size()) return false; // Remove the thing - removeMapObject(things_[index]); - things_.remove(index); + removeMapObject(things[index]); + things.remove(index); if (parent_map_) parent_map_->setThingsUpdated(); @@ -483,10 +538,10 @@ bool MapObjectCollection::removeThing(unsigned index) // ----------------------------------------------------------------------------- MapVertex* MapObjectCollection::addVertex(unique_ptr vertex) { - vertex->index_ = vertices_.size(); - vertices_.add(vertex.get()); + vertex->index_ = vertices_->size(); + vertices_->add(vertex.get()); addMapObject(std::move(vertex)); - return vertices_.back(); + return vertices_->back(); } // ----------------------------------------------------------------------------- @@ -494,10 +549,10 @@ MapVertex* MapObjectCollection::addVertex(unique_ptr vertex) // ----------------------------------------------------------------------------- MapSide* MapObjectCollection::addSide(unique_ptr side) { - side->index_ = sides_.size(); - sides_.add(side.get()); + side->index_ = sides_->size(); + sides_->add(side.get()); addMapObject(std::move(side)); - return sides_.back(); + return sides_->back(); } // ----------------------------------------------------------------------------- @@ -505,10 +560,10 @@ MapSide* MapObjectCollection::addSide(unique_ptr side) // ----------------------------------------------------------------------------- MapLine* MapObjectCollection::addLine(unique_ptr line) { - line->index_ = lines_.size(); - lines_.add(line.get()); + line->index_ = lines_->size(); + lines_->add(line.get()); addMapObject(std::move(line)); - return lines_.back(); + return lines_->back(); } // ----------------------------------------------------------------------------- @@ -516,10 +571,10 @@ MapLine* MapObjectCollection::addLine(unique_ptr line) // ----------------------------------------------------------------------------- MapSector* MapObjectCollection::addSector(unique_ptr sector) { - sector->index_ = sectors_.size(); - sectors_.add(sector.get()); + sector->index_ = sectors_->size(); + sectors_->add(sector.get()); addMapObject(std::move(sector)); - return sectors_.back(); + return sectors_->back(); } // ----------------------------------------------------------------------------- @@ -527,10 +582,10 @@ MapSector* MapObjectCollection::addSector(unique_ptr sector) // ----------------------------------------------------------------------------- MapThing* MapObjectCollection::addThing(unique_ptr thing) { - thing->index_ = things_.size(); - things_.add(thing.get()); + thing->index_ = things_->size(); + things_->add(thing.get()); addMapObject(std::move(thing)); - return things_.back(); + return things_->back(); } // ----------------------------------------------------------------------------- @@ -544,7 +599,7 @@ MapSide* MapObjectCollection::duplicateSide(MapSide* side) auto ns = std::make_unique(side->sector()); ns->copy(side); addSide(std::move(ns)); - return sides_.back(); + return sides_->back(); } // ----------------------------------------------------------------------------- @@ -556,15 +611,15 @@ vector MapObjectCollection::modifiedObjects(long since, MapObject::T vector modified_objects; if (type == MapObject::Type::Object || type == MapObject::Type::Vertex) - vertices_.putModifiedObjects(since, modified_objects); + putModifiedObjects(*vertices_, since, modified_objects); if (type == MapObject::Type::Object || type == MapObject::Type::Side) - sides_.putModifiedObjects(since, modified_objects); + putModifiedObjects(*sides_, since, modified_objects); if (type == MapObject::Type::Object || type == MapObject::Type::Line) - lines_.putModifiedObjects(since, modified_objects); + putModifiedObjects(*lines_, since, modified_objects); if (type == MapObject::Type::Object || type == MapObject::Type::Sector) - sectors_.putModifiedObjects(since, modified_objects); + putModifiedObjects(*sectors_, since, modified_objects); if (type == MapObject::Type::Object || type == MapObject::Type::Thing) - things_.putModifiedObjects(since, modified_objects); + putModifiedObjects(*things_, since, modified_objects); return modified_objects; } @@ -609,12 +664,12 @@ bool MapObjectCollection::modifiedSince(long since, MapObject::Type type) const switch (type) { case MapObject::Type::Object: return lastModifiedTime() > since; - case MapObject::Type::Vertex: return vertices_.modifiedSince(since); - case MapObject::Type::Line: return lines_.modifiedSince(since); - case MapObject::Type::Side: return sides_.modifiedSince(since); - case MapObject::Type::Sector: return sectors_.modifiedSince(since); - case MapObject::Type::Thing: return things_.modifiedSince(since); - default: return false; + case MapObject::Type::Vertex: return anyModifiedSince(*vertices_, since); + case MapObject::Type::Line: return anyModifiedSince(*lines_, since); + case MapObject::Type::Side: return anyModifiedSince(*sides_, since); + case MapObject::Type::Sector: return anyModifiedSince(*sectors_, since); + case MapObject::Type::Thing: return anyModifiedSince(*things_, since); + default: return false; } } @@ -624,10 +679,11 @@ bool MapObjectCollection::modifiedSince(long since, MapObject::Type type) const // ----------------------------------------------------------------------------- int MapObjectCollection::removeDetachedVertices() { - int count = 0; - for (int a = vertices_.size() - 1; a >= 0; a--) + auto vertices = *vertices_; + int count = 0; + for (int a = vertices.size() - 1; a >= 0; a--) { - if (vertices_[a]->nConnectedLines() == 0) + if (vertices[a]->nConnectedLines() == 0) { removeVertex(a); count++; @@ -645,10 +701,11 @@ int MapObjectCollection::removeDetachedVertices() // ----------------------------------------------------------------------------- int MapObjectCollection::removeDetachedSides() { - int count = 0; - for (int a = sides_.size() - 1; a >= 0; a--) + auto sides = *sides_; + int count = 0; + for (int a = sides.size() - 1; a >= 0; a--) { - if (!sides_[a]->parentLine()) + if (!sides[a]->parentLine()) { removeSide(a, false); count++; @@ -666,10 +723,11 @@ int MapObjectCollection::removeDetachedSides() // ----------------------------------------------------------------------------- int MapObjectCollection::removeDetachedSectors() { - int count = 0; - for (int a = sectors_.size() - 1; a >= 0; a--) + auto sectors = *sectors_; + int count = 0; + for (int a = sectors.size() - 1; a >= 0; a--) { - if (sectors_[a]->connectedSides().empty()) + if (sectors[a]->connectedSides().empty()) { removeSector(a); count++; @@ -687,10 +745,11 @@ int MapObjectCollection::removeDetachedSectors() // ----------------------------------------------------------------------------- int MapObjectCollection::removeZeroLengthLines() { - int count = 0; - for (unsigned a = 0; a < lines_.size(); a++) + auto lines = *lines_; + int count = 0; + for (unsigned a = 0; a < lines.size(); a++) { - if (lines_[a]->v1() == lines_[a]->v2()) + if (lines[a]->v1() == lines[a]->v2()) { removeLine(a); a--; @@ -706,10 +765,11 @@ int MapObjectCollection::removeZeroLengthLines() // ----------------------------------------------------------------------------- int MapObjectCollection::removeInvalidSides() { - int count = 0; - for (unsigned a = 0; a < sides_.size(); a++) + auto sides = *sides_; + int count = 0; + for (unsigned a = 0; a < sides.size(); a++) { - if (!sides_[a]->sector()) + if (!sides[a]->sector()) { removeSide(a); a--; @@ -726,11 +786,11 @@ int MapObjectCollection::removeInvalidSides() void MapObjectCollection::rebuildConnectedLines() { // Clear vertex connected lines lists - for (auto& vertex : vertices_) + for (auto& vertex : *vertices_) vertex->clearConnectedLines(); // Connect lines to their vertices - for (auto& line : lines_) + for (auto& line : *lines_) { line->v1()->connectLine(line); line->v2()->connectLine(line); @@ -743,11 +803,11 @@ void MapObjectCollection::rebuildConnectedLines() void MapObjectCollection::rebuildConnectedSides() { // Clear sector connected sides lists - for (auto& sector : sectors_) + for (auto& sector : *sectors_) sector->clearConnectedSides(); // Connect sides to their sectors - for (auto& side : sides_) + for (auto& side : *sides_) { if (side->sector()) side->sector()->connectSide(side); diff --git a/src/SLADEMap/MapObjectCollection.h b/src/SLADEMap/MapObjectCollection.h index e261cb0b5..51e92b155 100644 --- a/src/SLADEMap/MapObjectCollection.h +++ b/src/SLADEMap/MapObjectCollection.h @@ -1,41 +1,42 @@ #pragma once -#include "General/Defs.h" -#include "MapObjectList/LineList.h" -#include "MapObjectList/SectorList.h" -#include "MapObjectList/SideList.h" -#include "MapObjectList/ThingList.h" -#include "MapObjectList/VertexList.h" +#include "MapObject/MapObject.h" namespace slade { +class ThingList; +class SectorList; +class LineList; +class SideList; +class VertexList; +class SLADEMap; class MapObjectCollection { public: MapObjectCollection(SLADEMap* parent_map = nullptr); SLADEMap* parentMap() const { return parent_map_; } - VertexList& vertices() { return vertices_; } - SideList& sides() { return sides_; } - LineList& lines() { return lines_; } - SectorList& sectors() { return sectors_; } - ThingList& things() { return things_; } - const VertexList& vertices() const { return vertices_; } - const SideList& sides() const { return sides_; } - const LineList& lines() const { return lines_; } - const SectorList& sectors() const { return sectors_; } - const ThingList& things() const { return things_; } + VertexList& vertices() { return *vertices_; } + SideList& sides() { return *sides_; } + LineList& lines() { return *lines_; } + SectorList& sectors() { return *sectors_; } + ThingList& things() { return *things_; } + const VertexList& vertices() const { return *vertices_; } + const SideList& sides() const { return *sides_; } + const LineList& lines() const { return *lines_; } + const SectorList& sectors() const { return *sectors_; } + const ThingList& things() const { return *things_; } void setParentMap(SLADEMap* map) { parent_map_ = map; } // MapObject id stuff (used for undo/redo) void addMapObject(unique_ptr object); - void removeMapObject(MapObject* object); + void removeMapObject(const MapObject* object); MapObject* getObjectById(unsigned id) const { return objects_[id].object.get(); } void putObjectIdList(MapObject::Type type, vector& list) const; - void restoreObjectIdList(MapObject::Type type, vector& list); + void restoreObjectIdList(MapObject::Type type, const vector& list); - void refreshIndices(); + void refreshIndices() const; void clear(); // Object add @@ -49,15 +50,15 @@ class MapObjectCollection MapSide* duplicateSide(MapSide* side); // Object remove - bool removeVertex(MapVertex* vertex, bool merge_lines = false); + bool removeVertex(const MapVertex* vertex, bool merge_lines = false); bool removeVertex(unsigned index, bool merge_lines = false); - bool removeLine(MapLine* line); + bool removeLine(const MapLine* line); bool removeLine(unsigned index); - bool removeSide(MapSide* side, bool remove_from_line = true); + bool removeSide(const MapSide* side, bool remove_from_line = true); bool removeSide(unsigned index, bool remove_from_line = true); - bool removeSector(MapSector* sector); + bool removeSector(const MapSector* sector); bool removeSector(unsigned index); - bool removeThing(MapThing* thing); + bool removeThing(const MapThing* thing); bool removeThing(unsigned index); // Modified times @@ -88,10 +89,10 @@ class MapObjectCollection SLADEMap* parent_map_ = nullptr; vector objects_; - VertexList vertices_; - SideList sides_; - LineList lines_; - SectorList sectors_; - ThingList things_; + unique_ptr vertices_; + unique_ptr sides_; + unique_ptr lines_; + unique_ptr sectors_; + unique_ptr things_; }; } // namespace slade diff --git a/src/SLADEMap/MapObjectList/LineList.cpp b/src/SLADEMap/MapObjectList/LineList.cpp index 30ff84678..a2f947b8f 100644 --- a/src/SLADEMap/MapObjectList/LineList.cpp +++ b/src/SLADEMap/MapObjectList/LineList.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -33,7 +33,10 @@ // ----------------------------------------------------------------------------- #include "Main.h" #include "LineList.h" +#include "Game/ActionSpecial.h" #include "Game/Configuration.h" +#include "Game/Game.h" +#include "SLADEMap/MapObject/MapLine.h" #include "SLADEMap/SLADEMap.h" #include "Utility/MathStuff.h" @@ -51,7 +54,7 @@ using namespace slade; // Returns the line closest to the point, or null if none is found. // Ignores lines further away than [mindist] // ----------------------------------------------------------------------------- -MapLine* LineList::nearest(Vec2d point, double min) const +MapLine* LineList::nearest(const Vec2d& point, double min) const { // Go through lines double dist; @@ -84,7 +87,7 @@ MapLine* LineList::nearest(Vec2d point, double min) const // If [reverse] is false, only looks for lines with first vertex [v1] and second // vertex [v2] (not the other way around) // ----------------------------------------------------------------------------- -MapLine* LineList::withVertices(MapVertex* v1, MapVertex* v2, bool reverse) const +MapLine* LineList::withVertices(const MapVertex* v1, const MapVertex* v2, bool reverse) const { for (const auto& line : objects_) if (line->v1() == v1 && line->v2() == v2 || reverse && line->v2() == v1 && line->v1() == v2) @@ -132,25 +135,29 @@ vector LineList::cutPoints(const Seg2d& cutter) const { // Sort points along x axis if (xdif >= 0) - std::sort(intersect_points.begin(), intersect_points.end(), [](const Vec2d& left, const Vec2d& right) { - return left.x < right.x; - }); + std::sort( + intersect_points.begin(), + intersect_points.end(), + [](const Vec2d& left, const Vec2d& right) { return left.x < right.x; }); else - std::sort(intersect_points.begin(), intersect_points.end(), [](const Vec2d& left, const Vec2d& right) { - return left.x > right.x; - }); + std::sort( + intersect_points.begin(), + intersect_points.end(), + [](const Vec2d& left, const Vec2d& right) { return left.x > right.x; }); } else { // Sort points along y axis if (ydif >= 0) - std::sort(intersect_points.begin(), intersect_points.end(), [](const Vec2d& left, const Vec2d& right) { - return left.y < right.y; - }); + std::sort( + intersect_points.begin(), + intersect_points.end(), + [](const Vec2d& left, const Vec2d& right) { return left.y < right.y; }); else - std::sort(intersect_points.begin(), intersect_points.end(), [](const Vec2d& left, const Vec2d& right) { - return left.y > right.y; - }); + std::sort( + intersect_points.begin(), + intersect_points.end(), + [](const Vec2d& left, const Vec2d& right) { return left.y > right.y; }); } return intersect_points; @@ -210,9 +217,9 @@ void LineList::putAllTaggingWithId(int id, int type, vector& list) con case TagType::Sector: case TagType::SectorOrBack: case TagType::SectorAndBack: fits = (IDEQ(tag) && type == SLADEMap::SECTORS); break; - case TagType::LineNegative: tag = abs(tag); - case TagType::Line: fits = (IDEQ(tag) && type == SLADEMap::LINEDEFS); break; - case TagType::Thing: fits = (IDEQ(tag) && type == SLADEMap::THINGS); break; + case TagType::LineNegative: tag = abs(tag); + case TagType::Line: fits = (IDEQ(tag) && type == SLADEMap::LINEDEFS); break; + case TagType::Thing: fits = (IDEQ(tag) && type == SLADEMap::THINGS); break; case TagType::Thing1Sector2: arg2 = line->arg(1); fits = (type == SLADEMap::THINGS ? IDEQ(tag) : (IDEQ(arg2) && type == SLADEMap::SECTORS)); diff --git a/src/SLADEMap/MapObjectList/LineList.h b/src/SLADEMap/MapObjectList/LineList.h index 94a327eb4..3b36f0d45 100644 --- a/src/SLADEMap/MapObjectList/LineList.h +++ b/src/SLADEMap/MapObjectList/LineList.h @@ -1,16 +1,18 @@ #pragma once -#include "General/Defs.h" #include "MapObjectList.h" -#include "SLADEMap/MapObject/MapLine.h" namespace slade { +class MapVertex; +class MapLine; +enum class MapFormat; + class LineList : public MapObjectList { public: - MapLine* nearest(Vec2d point, double min = 64) const; - MapLine* withVertices(MapVertex* v1, MapVertex* v2, bool reverse = true) const; + MapLine* nearest(const Vec2d& point, double min = 64) const; + MapLine* withVertices(const MapVertex* v1, const MapVertex* v2, bool reverse = true) const; vector cutPoints(const Seg2d& cutter) const; MapLine* firstWithId(int id) const; void putAllWithId(int id, vector& list) const; diff --git a/src/SLADEMap/MapObjectList/MapObjectList.h b/src/SLADEMap/MapObjectList/MapObjectList.h index 13ec4bbb9..5db8535b3 100644 --- a/src/SLADEMap/MapObjectList/MapObjectList.h +++ b/src/SLADEMap/MapObjectList/MapObjectList.h @@ -46,7 +46,6 @@ template class MapObjectList if (index < count_) { objects_[index] = objects_.back(); - objects_[index]->setIndex(index); objects_.pop_back(); --count_; } @@ -58,7 +57,7 @@ template class MapObjectList } // Misc - void putModifiedObjects(long since, vector& modified_objects) const + /*void putModifiedObjects(long since, vector& modified_objects) const { for (const auto& object : objects_) if (object->modifiedTime() >= since) @@ -71,7 +70,7 @@ template class MapObjectList return true; return false; - } + }*/ protected: vector objects_; diff --git a/src/SLADEMap/MapObjectList/SectorList.cpp b/src/SLADEMap/MapObjectList/SectorList.cpp index d18b97eec..4a0381256 100644 --- a/src/SLADEMap/MapObjectList/SectorList.cpp +++ b/src/SLADEMap/MapObjectList/SectorList.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -34,6 +34,7 @@ #include "Main.h" #include "SectorList.h" #include "General/UI.h" +#include "SLADEMap/MapObject/MapSector.h" #include "Utility/StringUtils.h" using namespace slade; @@ -85,7 +86,7 @@ void SectorList::remove(unsigned index) // ----------------------------------------------------------------------------- // Returns the sector at the given [point], or null if not within a sector // ----------------------------------------------------------------------------- -MapSector* SectorList::atPos(Vec2d point) const +MapSector* SectorList::atPos(const Vec2d& point) const { // Go through sectors for (const auto& sector : objects_) @@ -132,7 +133,7 @@ BBox SectorList::allSectorBounds() const // ----------------------------------------------------------------------------- // Forces building of polygons for all sectors in the list // ----------------------------------------------------------------------------- -void SectorList::initPolygons() +void SectorList::initPolygons() const { ui::setSplashProgressMessage("Building sector polygons"); ui::setSplashProgress(0.0f); @@ -147,7 +148,7 @@ void SectorList::initPolygons() // ----------------------------------------------------------------------------- // Forces update of bounding boxes for all sectors in the list // ----------------------------------------------------------------------------- -void SectorList::initBBoxes() +void SectorList::initBBoxes() const { for (auto& sector : objects_) sector->updateBBox(); diff --git a/src/SLADEMap/MapObjectList/SectorList.h b/src/SLADEMap/MapObjectList/SectorList.h index e4c7782f0..84c17d04d 100644 --- a/src/SLADEMap/MapObjectList/SectorList.h +++ b/src/SLADEMap/MapObjectList/SectorList.h @@ -1,10 +1,11 @@ #pragma once #include "MapObjectList.h" -#include "SLADEMap/MapObject/MapSector.h" namespace slade { +class MapSector; + class SectorList : public MapObjectList { public: @@ -13,10 +14,10 @@ class SectorList : public MapObjectList void add(MapSector* sector) override; void remove(unsigned index) override; - MapSector* atPos(Vec2d point) const; + MapSector* atPos(const Vec2d& point) const; BBox allSectorBounds() const; - void initPolygons(); - void initBBoxes(); + void initPolygons() const; + void initBBoxes() const; void putAllWithId(int id, vector& list) const; vector allWithId(int id) const; MapSector* firstWithId(int id) const; diff --git a/src/SLADEMap/MapObjectList/SideList.cpp b/src/SLADEMap/MapObjectList/SideList.cpp index 4418d6c41..93b643f09 100644 --- a/src/SLADEMap/MapObjectList/SideList.cpp +++ b/src/SLADEMap/MapObjectList/SideList.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -33,6 +33,7 @@ // ----------------------------------------------------------------------------- #include "Main.h" #include "SideList.h" +#include "SLADEMap/MapObject/MapSide.h" #include "Utility/StringUtils.h" using namespace slade; diff --git a/src/SLADEMap/MapObjectList/SideList.h b/src/SLADEMap/MapObjectList/SideList.h index a7867314c..136156e85 100644 --- a/src/SLADEMap/MapObjectList/SideList.h +++ b/src/SLADEMap/MapObjectList/SideList.h @@ -1,10 +1,11 @@ #pragma once #include "MapObjectList.h" -#include "SLADEMap/MapObject/MapSide.h" namespace slade { +class MapSide; + class SideList : public MapObjectList { public: diff --git a/src/SLADEMap/MapObjectList/ThingList.cpp b/src/SLADEMap/MapObjectList/ThingList.cpp index 440548207..27abfe6d2 100644 --- a/src/SLADEMap/MapObjectList/ThingList.cpp +++ b/src/SLADEMap/MapObjectList/ThingList.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -33,7 +33,10 @@ // ----------------------------------------------------------------------------- #include "Main.h" #include "ThingList.h" +#include "Game/ActionSpecial.h" #include "Game/Configuration.h" +#include "Game/Game.h" +#include "SLADEMap/MapObject/MapThing.h" #include "SLADEMap/SLADEMap.h" #include "Utility/MathStuff.h" @@ -51,7 +54,7 @@ using namespace slade; // Returns the thing closest to the point, or null if none found. // Igonres any thing further away than [min] // ----------------------------------------------------------------------------- -MapThing* ThingList::nearest(Vec2d point, double min) const +MapThing* ThingList::nearest(const Vec2d& point, double min) const { // Go through things double dist; @@ -86,7 +89,7 @@ MapThing* ThingList::nearest(Vec2d point, double min) const // Same as 'nearest', but returns a list of things for the case where there are // multiple things at the same point // ----------------------------------------------------------------------------- -vector ThingList::multiNearest(Vec2d point) const +vector ThingList::multiNearest(const Vec2d& point) const { vector ret; @@ -211,9 +214,9 @@ void ThingList::putAllTaggingWithId(int id, int type, vector& list, i case TagType::Sector: case TagType::SectorOrBack: case TagType::SectorAndBack: fits = (IDEQ(tag) && type == SLADEMap::SECTORS); break; - case TagType::LineNegative: tag = abs(tag); - case TagType::Line: fits = (IDEQ(tag) && type == SLADEMap::LINEDEFS); break; - case TagType::Thing: fits = (IDEQ(tag) && type == SLADEMap::THINGS); break; + case TagType::LineNegative: tag = abs(tag); + case TagType::Line: fits = (IDEQ(tag) && type == SLADEMap::LINEDEFS); break; + case TagType::Thing: fits = (IDEQ(tag) && type == SLADEMap::THINGS); break; case TagType::Thing1Sector2: arg2 = thing->arg(1); fits = (type == SLADEMap::THINGS ? IDEQ(tag) : (IDEQ(arg2) && type == SLADEMap::SECTORS)); diff --git a/src/SLADEMap/MapObjectList/ThingList.h b/src/SLADEMap/MapObjectList/ThingList.h index 1a18fa6f7..9f26ce78f 100644 --- a/src/SLADEMap/MapObjectList/ThingList.h +++ b/src/SLADEMap/MapObjectList/ThingList.h @@ -1,15 +1,16 @@ #pragma once #include "MapObjectList.h" -#include "SLADEMap/MapObject/MapThing.h" namespace slade { +class MapThing; + class ThingList : public MapObjectList { public: - MapThing* nearest(Vec2d point, double min = 64) const; - vector multiNearest(Vec2d point) const; + MapThing* nearest(const Vec2d& point, double min = 64) const; + vector multiNearest(const Vec2d& point) const; BBox allThingBounds() const; void putAllWithId(int id, vector& list, unsigned start = 0, int type = 0) const; vector allWithId(int id, unsigned start = 0, int type = 0) const; diff --git a/src/SLADEMap/MapObjectList/VertexList.cpp b/src/SLADEMap/MapObjectList/VertexList.cpp index a21ed6828..2b839dcca 100644 --- a/src/SLADEMap/MapObjectList/VertexList.cpp +++ b/src/SLADEMap/MapObjectList/VertexList.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -33,6 +33,7 @@ // ----------------------------------------------------------------------------- #include "Main.h" #include "VertexList.h" +#include "SLADEMap/MapObject/MapVertex.h" #include "Utility/MathStuff.h" using namespace slade; @@ -49,7 +50,7 @@ using namespace slade; // Returns the vertex closest to the point, or null if none found. // Igonres any vertices further away than [min] // ----------------------------------------------------------------------------- -MapVertex* VertexList::nearest(Vec2d point, double min) const +MapVertex* VertexList::nearest(const Vec2d& point, double min) const { // Go through vertices double dist; diff --git a/src/SLADEMap/MapObjectList/VertexList.h b/src/SLADEMap/MapObjectList/VertexList.h index 7e9a9458c..e5df70691 100644 --- a/src/SLADEMap/MapObjectList/VertexList.h +++ b/src/SLADEMap/MapObjectList/VertexList.h @@ -1,14 +1,15 @@ #pragma once #include "MapObjectList.h" -#include "SLADEMap/MapObject/MapVertex.h" namespace slade { +class MapVertex; + class VertexList : public MapObjectList { public: - MapVertex* nearest(Vec2d point, double min = 64) const; + MapVertex* nearest(const Vec2d& point, double min = 64) const; MapVertex* vertexAt(double x, double y) const; MapVertex* firstCrossed(const Seg2d& line) const; }; diff --git a/src/SLADEMap/MapSpecials.cpp b/src/SLADEMap/MapSpecials.cpp index 2b5be5a1f..c4a7ae680 100644 --- a/src/SLADEMap/MapSpecials.cpp +++ b/src/SLADEMap/MapSpecials.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -32,7 +32,16 @@ // ----------------------------------------------------------------------------- #include "Main.h" #include "MapSpecials.h" +#include "Archive/ArchiveEntry.h" #include "Game/Configuration.h" +#include "MapObject/MapLine.h" +#include "MapObject/MapSide.h" +#include "MapObject/MapThing.h" +#include "MapObject/MapVertex.h" +#include "MapObjectList/LineList.h" +#include "MapObjectList/SectorList.h" +#include "MapObjectList/ThingList.h" +#include "MapObjectList/VertexList.h" #include "SLADEMap.h" #include "Utility/MathStuff.h" #include "Utility/Tokenizer.h" @@ -77,7 +86,6 @@ void MapSpecials::reset() // ----------------------------------------------------------------------------- void MapSpecials::processMapSpecials(SLADEMap* map) { - // Clear out all 3D floors, or every call to this function will create duplicates! // TODO this isn't a very good solution, but we don't have incremental updates yet for (unsigned a = 0; a < map->nSectors(); a++) @@ -329,7 +337,7 @@ void MapSpecials::processZDoomLineSpecial(MapLine* line) tagged.push_back(line); // Get args - double alpha = (double)args[1] / 255.0; + double alpha = static_cast(args[1]) / 255.0; string type = (args[2] == 0) ? "translucent" : "add"; // Set transparency @@ -345,7 +353,7 @@ void MapSpecials::processZDoomLineSpecial(MapLine* line) // ----------------------------------------------------------------------------- // Process 'OPEN' ACS scripts for various specials - sector colours, slopes, etc // ----------------------------------------------------------------------------- -void MapSpecials::processACSScripts(ArchiveEntry* entry) +void MapSpecials::processACSScripts(const ArchiveEntry* entry) { sector_colours_.clear(); sector_fadecolours_.clear(); @@ -584,6 +592,7 @@ void MapSpecials::processSRB2Slopes(const SLADEMap* map) const target->setPlane(math::planeFromTriangle(vertices[0], vertices[1], vertices[2])); } break; + default: break; } } @@ -630,6 +639,7 @@ void MapSpecials::processSRB2Slopes(const SLADEMap* map) const front->setCeilingPlane(tagged->ceiling().plane); } break; + default: break; } } } @@ -641,10 +651,10 @@ void MapSpecials::processSRB2FOFs(const SLADEMap* map) const { for (unsigned a = 0; a < map->nLines(); a++) { - MapLine* line = map->line(a); + MapLine* line = map->line(a); MapSector* control_sector = line->frontSector(); - if(!control_sector) + if (!control_sector) continue; ExtraFloor extra_floor; @@ -652,93 +662,91 @@ void MapSpecials::processSRB2FOFs(const SLADEMap* map) const auto special = line->special(); switch (special) { - // // Solid // - case 100: //Solid, Opaque, Shadowcasting - case 101: //Solid, Opaque, Non-Shadowcasting - case 102: //Solid, Translucent - case 103: //Solid, Sides Only - case 105: //Solid, Invisible - case 140: //Intangible from Bottom, Opaque - case 141: //Intangible from Bottom, Translucent - case 143: //Intangible from Top, Opaque - case 144: //Intangible from Top, Translucent - case 146: //Only Tangible from Sides - + case 100: // Solid, Opaque, Shadowcasting + case 101: // Solid, Opaque, Non-Shadowcasting + case 102: // Solid, Translucent + case 103: // Solid, Sides Only + case 105: // Solid, Invisible + case 140: // Intangible from Bottom, Opaque + case 141: // Intangible from Bottom, Translucent + case 143: // Intangible from Top, Opaque + case 144: // Intangible from Top, Translucent + case 146: // Only Tangible from Sides + // // Intangible // - case 120: //Water, Opaque - case 121: //Water, Translucent - case 124: //Goo Water, Translucent - case 220: //Intangible, Opaque - case 221: //Intangible, Translucent - case 222: //Intangible, Sides Only - case 223: //Intangible, Invisible + case 120: // Water, Opaque + case 121: // Water, Translucent + case 124: // Goo Water, Translucent + case 220: // Intangible, Opaque + case 221: // Intangible, Translucent + case 222: // Intangible, Sides Only + case 223: // Intangible, Invisible // // Moving // - case 150: //Air bobbing - case 151: //Air bobbing (Adjustable) - case 152: //Reverse Air Bobbing (Adjustable) - case 153: //Dynamically Sinking Platform - case 160: //Floating, Bobbing - case 190: //Rising Platform, Solid, Opaque, Shadowcasting - case 191: //Rising Platform, Solid, Opaque, Non-Shadowcasting - case 192: //Rising Platform, Solid, Translucent - case 193: //Rising Platform, Solid, Invisible - case 194: //Rising Platform, Intangible from Bottom, Opaque - case 195: //Rising Platform, Intangible from Bottom, Translucent + case 150: // Air bobbing + case 151: // Air bobbing (Adjustable) + case 152: // Reverse Air Bobbing (Adjustable) + case 153: // Dynamically Sinking Platform + case 160: // Floating, Bobbing + case 190: // Rising Platform, Solid, Opaque, Shadowcasting + case 191: // Rising Platform, Solid, Opaque, Non-Shadowcasting + case 192: // Rising Platform, Solid, Translucent + case 193: // Rising Platform, Solid, Invisible + case 194: // Rising Platform, Intangible from Bottom, Opaque + case 195: // Rising Platform, Intangible from Bottom, Translucent // // Crumbling // - case 170: //Crumbling, Respawn - case 171: //Crumbling, No Respawn - case 172: //Crumbling, Respawn, Intangible from Bottom - case 173: //Crumbling, No Respawn, Intangible from Bottom - case 174: //Crumbling, Respawn, Intangible from Bottom Translucent - case 175: //Crumbling, Respawn, Intangible from Bottom,Translucent - case 176: //Crumbling, Respawn, Floating, Bobbing - case 177: //Crumbling, No Respawn, Floating, Bobbing - case 178: //Crumbling, Respawn, Floating - case 179: //Crumbling, No Respawn, Floating - case 180: //Crumbling, Respawn, Air Bobbing + case 170: // Crumbling, Respawn + case 171: // Crumbling, No Respawn + case 172: // Crumbling, Respawn, Intangible from Bottom + case 173: // Crumbling, No Respawn, Intangible from Bottom + case 174: // Crumbling, Respawn, Intangible from Bottom Translucent + case 175: // Crumbling, Respawn, Intangible from Bottom,Translucent + case 176: // Crumbling, Respawn, Floating, Bobbing + case 177: // Crumbling, No Respawn, Floating, Bobbing + case 178: // Crumbling, Respawn, Floating + case 179: // Crumbling, No Respawn, Floating + case 180: // Crumbling, Respawn, Air Bobbing // // Special // - case 200: //Light Block - case 201: //Half light Block - case 250: //Mario Block - case 251: //Thwomp Block - case 252: //Shatter Block - case 253: //Shatter Block, Translucent - case 254: //Bustable Block - case 255: //Spin-Bustable Block - case 256: //Spin-Bustable Block, Translucent - case 257: //Quicksand - //case 258: //Laser - case 259: //Custom FOF + case 200: // Light Block + case 201: // Half light Block + case 250: // Mario Block + case 251: // Thwomp Block + case 252: // Shatter Block + case 253: // Shatter Block, Translucent + case 254: // Bustable Block + case 255: // Spin-Bustable Block + case 256: // Spin-Bustable Block, Translucent + case 257: // Quicksand + // case 258: //Laser + case 259: // Custom FOF { - extra_floor.floor_type = ExtraFloor::SOLID; extra_floor.effective_height = control_sector->ceiling().height; - //Side only FOFs? - if(special != 103 && special != 222) + // Side only FOFs? + if (special != 103 && special != 222) { - extra_floor.ceiling_plane = control_sector->ceiling().plane; - extra_floor.floor_plane = control_sector->floor().plane; + extra_floor.ceiling_plane = control_sector->ceiling().plane; + extra_floor.floor_plane = control_sector->floor().plane; } else { - extra_floor.ceiling_plane = Plane(); - extra_floor.floor_plane = Plane(); + extra_floor.ceiling_plane = Plane(); + extra_floor.floor_plane = Plane(); } extra_floor.control_sector_index = control_sector->index(); @@ -746,55 +754,39 @@ void MapSpecials::processSRB2FOFs(const SLADEMap* map) const int translucency = 255; - //Translucent FOF? - if ( - special == 102 - || special == 141 - || special == 144 - || special == 121 - || special == 124 - || special == 221 - || special == 192 - || special == 195 - || special == 174 - || special == 175 - || special == 253 + // Translucent FOF? + if (special == 102 || special == 141 || special == 144 || special == 121 || special == 124 || special == 221 + || special == 192 || special == 195 || special == 174 || special == 175 || special == 253 || special == 256) { - translucency = 128; - const string &texture = line->s1()->texUpper(); + translucency = 128; + const string& texture = line->s1()->texUpper(); if (texture.size() >= 4 && texture[0] == '#') { errno = 0; - int n = std::strtol(texture.c_str()+1, NULL, 10); + int n = std::strtol(texture.c_str() + 1, nullptr, 10); if (errno == 0) translucency = n; } - } - else if ( //Invisible FOF? - special == 105 - || special == 223 - || special == 193 - || special == 200 - || special == 201 + } + else if ( // Invisible FOF? + special == 105 || special == 223 || special == 193 || special == 200 || special == 201 || special == 259) { translucency = 0; } extra_floor.flags = 0; - extra_floor.alpha = (translucency/255.f); + extra_floor.alpha = (translucency / 255.f); - //Only draw inside for water FOFs + // Only draw inside for water FOFs extra_floor.draw_inside = (special >= 120 && special <= 125); } break; - default: - continue; - break; + default: continue; } for (auto& sector : map->sectors()) @@ -808,7 +800,7 @@ void MapSpecials::processSRB2FOFs(const SLADEMap* map) const // ----------------------------------------------------------------------------- // Process EDGE-Classic slope specials // ----------------------------------------------------------------------------- -void MapSpecials::processEDGEClassicSlopes(SLADEMap* map) const +void MapSpecials::processEDGEClassicSlopes(const SLADEMap* map) const { // First things first: reset every sector to flat planes for (unsigned a = 0; a < map->nSectors(); a++) @@ -1071,22 +1063,22 @@ void MapSpecials::processZDoomSlopes(SLADEMap* map) const int tag; auto front = line->frontSector(); auto back = line->backSector(); - if ((tag = line->arg(0)) && front) + if (((tag = line->arg(0))) && front) { if (auto sector = map->sectors().firstWithId(tag)) front->setFloorPlane(sector->floor().plane); } - if ((tag = line->arg(1)) && front) + if (((tag = line->arg(1))) && front) { if (auto sector = map->sectors().firstWithId(tag)) front->setCeilingPlane(sector->ceiling().plane); } - if ((tag = line->arg(2)) && back) + if (((tag = line->arg(2))) && back) { if (auto sector = map->sectors().firstWithId(tag)) back->setFloorPlane(sector->floor().plane); } - if ((tag = line->arg(3)) && back) + if (((tag = line->arg(3))) && back) { if (auto sector = map->sectors().firstWithId(tag)) back->setCeilingPlane(sector->ceiling().plane); @@ -1174,22 +1166,22 @@ void MapSpecials::processEternitySlopes(const SLADEMap* map) const int tag; auto front = line->frontSector(); auto back = line->backSector(); - if ((tag = line->arg(0)) && front) + if (((tag = line->arg(0))) && front) { if (auto sector = map->sectors().firstWithId(tag)) front->setFloorPlane(sector->floor().plane); } - if ((tag = line->arg(1)) && front) + if (((tag = line->arg(1))) && front) { if (auto sector = map->sectors().firstWithId(tag)) front->setCeilingPlane(sector->ceiling().plane); } - if ((tag = line->arg(2)) && back) + if (((tag = line->arg(2))) && back) { if (auto sector = map->sectors().firstWithId(tag)) back->setFloorPlane(sector->floor().plane); } - if ((tag = line->arg(3)) && back) + if (((tag = line->arg(3))) && back) { if (auto sector = map->sectors().firstWithId(tag)) back->setCeilingPlane(sector->ceiling().plane); @@ -1469,15 +1461,17 @@ void MapSpecials::applyVertexHeightSlope(MapSector* target, vector& // (EDGE-Classic rectangular sectors only; performs additional validation) // ----------------------------------------------------------------------------- template -void MapSpecials::applyRectangularVertexHeightSlope(MapSector* target, vector& vertices, VertexHeightMap& heights) - const +void MapSpecials::applyRectangularVertexHeightSlope( + MapSector* target, + vector& vertices, + VertexHeightMap& heights) const { std::vector height_verts; - string prop = (T == SurfaceType::Floor ? "zfloor" : "zceiling"); - auto v1_hasheight = heights.count(vertices[0]) || vertices[0]->hasProp(prop); - auto v2_hasheight = heights.count(vertices[1]) || vertices[1]->hasProp(prop); - auto v3_hasheight = heights.count(vertices[2]) || vertices[2]->hasProp(prop); - auto v4_hasheight = heights.count(vertices[3]) || vertices[3]->hasProp(prop); + string prop = (T == SurfaceType::Floor ? "zfloor" : "zceiling"); + auto v1_hasheight = heights.count(vertices[0]) || vertices[0]->hasProp(prop); + auto v2_hasheight = heights.count(vertices[1]) || vertices[1]->hasProp(prop); + auto v3_hasheight = heights.count(vertices[2]) || vertices[2]->hasProp(prop); + auto v4_hasheight = heights.count(vertices[3]) || vertices[3]->hasProp(prop); if (v1_hasheight) height_verts.push_back(0); if (v2_hasheight) @@ -1488,8 +1482,8 @@ void MapSpecials::applyRectangularVertexHeightSlope(MapSector* target, vectorconnectedLines()) @@ -1503,7 +1497,11 @@ void MapSpecials::applyRectangularVertexHeightSlope(MapSector* target, vector(v1, target) - heights.count(v2) ? heights[v2] : vertexHeight(v2, target)) < 0.001f) + if (fabs( + heights.count(v1) ? heights[v1] : + vertexHeight(v1, target) - heights.count(v2) ? heights[v2] : + vertexHeight(v2, target)) + < 0.001f) { // Psuedo-Plane_Align routine double furthest_dist = 0.0; @@ -1537,4 +1535,4 @@ void MapSpecials::applyRectangularVertexHeightSlope(MapSector* target, vector void applyPlaneAlign(MapLine* line, MapSector* target, MapSector* model_sector) const; @@ -70,6 +70,7 @@ class MapSpecials template void applyVertexHeightSlope(MapSector* target, vector& vertices, VertexHeightMap& heights) const; template - void applyRectangularVertexHeightSlope(MapSector* target, vector& vertices, VertexHeightMap& heights) const; + void applyRectangularVertexHeightSlope(MapSector* target, vector& vertices, VertexHeightMap& heights) + const; }; } // namespace slade diff --git a/src/SLADEMap/SLADEMap.cpp b/src/SLADEMap/SLADEMap.cpp index eb931b48e..32df5639e 100644 --- a/src/SLADEMap/SLADEMap.cpp +++ b/src/SLADEMap/SLADEMap.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -36,6 +36,16 @@ #include "Game/Configuration.h" #include "MapEditor/SectorBuilder.h" #include "MapFormat/MapFormatHandler.h" +#include "MapObject/MapLine.h" +#include "MapObject/MapSide.h" +#include "MapObject/MapThing.h" +#include "MapObject/MapVertex.h" +#include "MapObjectList/LineList.h" +#include "MapObjectList/SectorList.h" +#include "MapObjectList/SideList.h" +#include "MapObjectList/ThingList.h" +#include "MapObjectList/VertexList.h" +#include "MapSpecials.h" #include "Utility/MathStuff.h" using namespace slade; @@ -59,7 +69,7 @@ CVAR(Bool, map_split_auto_offset, true, CVar::Flag::Save) // ----------------------------------------------------------------------------- // SLADEMap class constructor // ----------------------------------------------------------------------------- -SLADEMap::SLADEMap() : data_{ this } +SLADEMap::SLADEMap() : data_{ this }, current_format_{ MapFormat::Unknown }, map_specials_{ new MapSpecials() } { // Init opened time so it's not random leftover garbage values setOpenedTime(); @@ -74,21 +84,101 @@ SLADEMap::~SLADEMap() } // ----------------------------------------------------------------------------- -// Returns the object of [type] at [index], or NULL if [index] is invalid +// Returns the vertex at [index], or nullptr if [index] is invalid +// ----------------------------------------------------------------------------- +MapVertex* SLADEMap::vertex(unsigned index) const +{ + return data_.vertices().at(index); +} + +// ----------------------------------------------------------------------------- +// Returns the side at [index], or nullptr if [index] is invalid +// ----------------------------------------------------------------------------- +MapSide* SLADEMap::side(unsigned index) const +{ + return data_.sides().at(index); +} + +// ----------------------------------------------------------------------------- +// Returns the line at [index], or nullptr if [index] is invalid +// ----------------------------------------------------------------------------- +MapLine* SLADEMap::line(unsigned index) const +{ + return data_.lines().at(index); +} + +// ----------------------------------------------------------------------------- +// Returns the sector at [index], or nullptr if [index] is invalid +// ----------------------------------------------------------------------------- +MapSector* SLADEMap::sector(unsigned index) const +{ + return data_.sectors().at(index); +} + +// ----------------------------------------------------------------------------- +// Returns the thing at [index], or nullptr if [index] is invalid +// ----------------------------------------------------------------------------- +MapThing* SLADEMap::thing(unsigned index) const +{ + return data_.things().at(index); +} + +// ----------------------------------------------------------------------------- +// Returns the object of [type] at [index], or nullptr if [index] is invalid // ----------------------------------------------------------------------------- MapObject* SLADEMap::object(MapObject::Type type, unsigned index) const { switch (type) { case MapObject::Type::Vertex: return vertex(index); - case MapObject::Type::Line: return line(index); - case MapObject::Type::Side: return side(index); + case MapObject::Type::Line: return line(index); + case MapObject::Type::Side: return side(index); case MapObject::Type::Sector: return sector(index); - case MapObject::Type::Thing: return thing(index); - default: return nullptr; + case MapObject::Type::Thing: return thing(index); + default: return nullptr; } } +// ----------------------------------------------------------------------------- +// Returns number of vertices in the map +// ----------------------------------------------------------------------------- +size_t SLADEMap::nVertices() const +{ + return data_.vertices().size(); +} + +// ----------------------------------------------------------------------------- +// Returns number of lines in the map +// ----------------------------------------------------------------------------- +size_t SLADEMap::nLines() const +{ + return data_.lines().size(); +} + +// ----------------------------------------------------------------------------- +// Returns number of sides in the map +// ----------------------------------------------------------------------------- +size_t SLADEMap::nSides() const +{ + return data_.sides().size(); +} + +// ----------------------------------------------------------------------------- +// Returns number of sectors in the map +// ----------------------------------------------------------------------------- +size_t SLADEMap::nSectors() const +{ + return data_.sectors().size(); +} + +// ----------------------------------------------------------------------------- +// Returns number of things in the map +// ----------------------------------------------------------------------------- +size_t SLADEMap::nThings() const +{ + return data_.things().size(); +} + // ----------------------------------------------------------------------------- // Sets the geometry last updated time to now // ----------------------------------------------------------------------------- @@ -108,7 +198,7 @@ void SLADEMap::setThingsUpdated() // ----------------------------------------------------------------------------- // Reads map data using info in [map] // ----------------------------------------------------------------------------- -bool SLADEMap::readMap(const Archive::MapDesc& map) +bool SLADEMap::readMap(const MapDesc& map) { auto omap = map; @@ -332,7 +422,7 @@ void SLADEMap::putDragonTargets(MapThing* first, vector& list) // ----------------------------------------------------------------------------- // Returns the first texture at [tex_part] found on lines connected to [vertex] // ----------------------------------------------------------------------------- -string SLADEMap::adjacentLineTexture(MapVertex* vertex, int tex_part) const +string SLADEMap::adjacentLineTexture(const MapVertex* vertex, int tex_part) const { // Go through adjacent lines auto tex = MapSide::TEX_NONE; @@ -495,7 +585,7 @@ void SLADEMap::setOpenedTime() // ----------------------------------------------------------------------------- void SLADEMap::recomputeSpecials() { - map_specials_.processMapSpecials(this); + map_specials_->processMapSpecials(this); } // ----------------------------------------------------------------------------- diff --git a/src/SLADEMap/SLADEMap.h b/src/SLADEMap/SLADEMap.h index 559e59765..0cfe07efc 100644 --- a/src/SLADEMap/SLADEMap.h +++ b/src/SLADEMap/SLADEMap.h @@ -1,12 +1,13 @@ #pragma once -#include "Archive/Archive.h" #include "MapObjectCollection.h" -#include "MapSpecials.h" namespace slade { +class MapSpecials; +struct MapDesc; class ParseTreeNode; +enum class MapFormat; namespace Game { enum class TagType; @@ -40,17 +41,17 @@ class SLADEMap void setThingsUpdated(); // MapObject access - MapVertex* vertex(unsigned index) const { return data_.vertices().at(index); } - MapSide* side(unsigned index) const { return data_.sides().at(index); } - MapLine* line(unsigned index) const { return data_.lines().at(index); } - MapSector* sector(unsigned index) const { return data_.sectors().at(index); } - MapThing* thing(unsigned index) const { return data_.things().at(index); } + MapVertex* vertex(unsigned index) const; + MapSide* side(unsigned index) const; + MapLine* line(unsigned index) const; + MapSector* sector(unsigned index) const; + MapThing* thing(unsigned index) const; MapObject* object(MapObject::Type type, unsigned index) const; - size_t nVertices() const { return data_.vertices().size(); } - size_t nLines() const { return data_.lines().size(); } - size_t nSides() const { return data_.sides().size(); } - size_t nSectors() const { return data_.sectors().size(); } - size_t nThings() const { return data_.things().size(); } + size_t nVertices() const; + size_t nLines() const; + size_t nSides() const; + size_t nSectors() const; + size_t nThings() const; const VertexList& vertices() const { return data_.vertices(); } const LineList& lines() const { return data_.lines(); } const SideList& sides() const { return data_.sides(); } @@ -59,10 +60,10 @@ class SLADEMap vector& udmfExtraEntries() { return udmf_extra_entries_; } - bool readMap(const Archive::MapDesc& map); + bool readMap(const MapDesc& map); void clearMap(); - MapSpecials* mapSpecials() { return &map_specials_; } + MapSpecials* mapSpecials() const { return map_specials_.get(); } void recomputeSpecials(); // Map saving @@ -77,15 +78,21 @@ class SLADEMap MapSide* createSide(MapSector* sector); // Removal - bool removeVertex(MapVertex* vertex, bool merge_lines = false) { return data_.removeVertex(vertex, merge_lines); } + bool removeVertex(const MapVertex* vertex, bool merge_lines = false) + { + return data_.removeVertex(vertex, merge_lines); + } bool removeVertex(unsigned index, bool merge_lines = false) { return data_.removeVertex(index, merge_lines); } - bool removeLine(MapLine* line) { return data_.removeLine(line); } + bool removeLine(const MapLine* line) { return data_.removeLine(line); } bool removeLine(unsigned index) { return data_.removeLine(index); } - bool removeSide(MapSide* side, bool remove_from_line = true) { return data_.removeSide(side, remove_from_line); } + bool removeSide(const MapSide* side, bool remove_from_line = true) + { + return data_.removeSide(side, remove_from_line); + } bool removeSide(unsigned index, bool remove_from_line = true) { return data_.removeSide(index, remove_from_line); } - bool removeSector(MapSector* sector) { return data_.removeSector(sector); } + bool removeSector(const MapSector* sector) { return data_.removeSector(sector); } bool removeSector(unsigned index) { return data_.removeSector(index); } - bool removeThing(MapThing* thing) { return data_.removeThing(thing); } + bool removeThing(const MapThing* thing) { return data_.removeThing(thing); } bool removeThing(unsigned index) { return data_.removeThing(index); } int removeDetachedVertices() { return data_.removeDetachedVertices(); } @@ -99,7 +106,7 @@ class SLADEMap void putDragonTargets(MapThing* first, vector& list); // Info - string adjacentLineTexture(MapVertex* vertex, int tex_part = 255) const; + string adjacentLineTexture(const MapVertex* vertex, int tex_part = 255) const; MapSector* lineSideSector(MapLine* line, bool front = true); bool isModified() const; void setOpenedTime(); @@ -125,7 +132,10 @@ class SLADEMap // Misc. map data access void rebuildConnectedLines() { data_.rebuildConnectedLines(); } void rebuildConnectedSides() { data_.rebuildConnectedSides(); } - void restoreObjectIdList(MapObject::Type type, vector& list) { data_.restoreObjectIdList(type, list); } + void restoreObjectIdList(MapObject::Type type, const vector& list) + { + data_.restoreObjectIdList(type, list); + } // Convert bool convertToHexen() const; @@ -137,13 +147,13 @@ class SLADEMap int thingTypeUsageCount(int type); private: - MapObjectCollection data_; - string udmf_namespace_; - PropertyList udmf_props_; - string name_; - MapFormat current_format_ = MapFormat::Unknown; - long opened_time_ = 0; - MapSpecials map_specials_; + MapObjectCollection data_; + string udmf_namespace_; + PropertyList udmf_props_; + string name_; + MapFormat current_format_; + long opened_time_ = 0; + unique_ptr map_specials_; vector udmf_extra_entries_; // UDMF Extras diff --git a/src/Scripting/Export/Archive.cpp b/src/Scripting/Export/Archive.cpp index ed56c27b4..ee7dbed16 100644 --- a/src/Scripting/Export/Archive.cpp +++ b/src/Scripting/Export/Archive.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -41,6 +41,8 @@ using namespace slade; +// ReSharper disable CppParameterMayBeConstPtrOrRef + // ----------------------------------------------------------------------------- // @@ -311,21 +313,17 @@ void registerArchiveEntry(sol::state& lua) lua_entry["FormattedName"] = sol::overload( [](ArchiveEntry& self) { return formattedEntryName(self, true, true, false); }, [](ArchiveEntry& self, bool include_path) { return formattedEntryName(self, include_path, true, false); }, - [](ArchiveEntry& self, bool include_path, bool include_extension) { - return formattedEntryName(self, include_path, include_extension, false); - }, + [](ArchiveEntry& self, bool include_path, bool include_extension) + { return formattedEntryName(self, include_path, include_extension, false); }, &formattedEntryName); lua_entry["FormattedSize"] = &ArchiveEntry::sizeString; - lua_entry["ImportFile"] = [](ArchiveEntry& self, string_view filename) { - return std::make_tuple(self.importFile(filename), global::error); - }; - lua_entry["ImportEntry"] = [](ArchiveEntry& self, ArchiveEntry* entry) { - return std::make_tuple(self.importEntry(entry), global::error); - }; + lua_entry["ImportFile"] = [](ArchiveEntry& self, string_view filename) + { return std::make_tuple(self.importFile(filename), global::error); }; + lua_entry["ImportEntry"] = [](ArchiveEntry& self, ArchiveEntry* entry) + { return std::make_tuple(self.importEntry(entry), global::error); }; lua_entry["ImportData"] = sol::overload(&entryImportString, &entryImportMC); - lua_entry["ExportFile"] = [](ArchiveEntry& self, string_view filename) { - return std::make_tuple(self.exportFile(filename), global::error); - }; + lua_entry["ExportFile"] = [](ArchiveEntry& self, string_view filename) + { return std::make_tuple(self.exportFile(filename), global::error); }; lua_entry["Rename"] = &entryRename; } @@ -375,12 +373,10 @@ void registerArchivesNamespace(sol::state& lua) archives["All"] = sol::overload( [](bool res) { return app::archiveManager().allArchives(res); }, []() { return app::archiveManager().allArchives(false); }); - archives["Create"] = [](string_view format) { - return std::make_tuple(app::archiveManager().newArchive(format), global::error); - }; - archives["OpenFile"] = [](string_view filename) { - return std::make_tuple(app::archiveManager().openArchive(filename), global::error); - }; + archives["Create"] = [](string_view format) + { return std::make_tuple(app::archiveManager().newArchive(format), global::error); }; + archives["OpenFile"] = [](string_view filename) + { return std::make_tuple(app::archiveManager().openArchive(filename), global::error); }; archives["Close"] = sol::overload( [](Archive* archive) { return app::archiveManager().closeArchive(archive); }, [](int index) { return app::archiveManager().closeArchive(index); }); diff --git a/src/Scripting/Export/Game.cpp b/src/Scripting/Export/Game.cpp index f61f4b8bf..0c2f7d739 100644 --- a/src/Scripting/Export/Game.cpp +++ b/src/Scripting/Export/Game.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net diff --git a/src/Scripting/Export/General.cpp b/src/Scripting/Export/General.cpp index f096499e5..a398e7ca7 100644 --- a/src/Scripting/Export/General.cpp +++ b/src/Scripting/Export/General.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -35,11 +35,14 @@ #include "Graphics/Palette/Palette.h" #include "MainEditor/MainEditor.h" #include "MapEditor/MapEditContext.h" +#include "MapEditor/MapEditor.h" #include "Scripting/Lua.h" #include "thirdparty/sol/sol.hpp" using namespace slade; +// ReSharper disable CppParameterMayBeConstPtrOrRef + // ----------------------------------------------------------------------------- // @@ -73,7 +76,7 @@ bool showArchive(Archive* archive) // ----------------------------------------------------------------------------- string_view memChunkData(MemChunk& mc) { - return string_view{ (char*)mc.data(), mc.size() }; + return string_view{ reinterpret_cast(mc.data()), mc.size() }; } // ----------------------------------------------------------------------------- @@ -142,9 +145,8 @@ void registerMemChunkType(sol::state& lua) // Functions // ------------------------------------------------------------------------- lua_mc["AsString"] = &memChunkData; - lua_mc["SetData"] = [](MemChunk& self, string_view data) { - self.importMem((const uint8_t*)data.data(), data.size()); - }; + lua_mc["SetData"] = [](MemChunk& self, string_view data) + { self.importMem(reinterpret_cast(data.data()), data.size()); }; lua_mc["Clear"] = &MemChunk::clear; lua_mc["Resize"] = &MemChunk::reSize; lua_mc["Copy"] = sol::resolve(&MemChunk::importMem); @@ -169,9 +171,8 @@ void registerMemChunkType(sol::state& lua) lua_mc["WriteUInt32"] = &memChunkWrite; lua_mc["WriteInt64"] = &memChunkWrite; lua_mc["WriteUInt64"] = &memChunkWrite; - lua_mc["WriteString"] = [](MemChunk& self, int offset, string_view value, bool expand) { - self.write(offset, value.data(), value.size(), expand); - }; + lua_mc["WriteString"] = [](MemChunk& self, int offset, string_view value, bool expand) + { self.write(offset, value.data(), value.size(), expand); }; lua_mc["ReadInt8"] = &memChunkRead; lua_mc["ReadUInt8"] = &memChunkRead; lua_mc["ReadInt16"] = &memChunkRead; @@ -180,9 +181,10 @@ void registerMemChunkType(sol::state& lua) lua_mc["ReadUInt32"] = &memChunkRead; lua_mc["ReadInt64"] = &memChunkRead; lua_mc["ReadUInt64"] = &memChunkRead; - lua_mc["ReadString"] = sol::overload(&memChunkReadString, [](MemChunk& self, unsigned offset, unsigned length) { - return memChunkReadString(self, offset, length, false); - }); + lua_mc["ReadString"] = sol::overload( + &memChunkReadString, + [](MemChunk& self, unsigned offset, unsigned length) + { return memChunkReadString(self, offset, length, false); }); } // ----------------------------------------------------------------------------- @@ -257,7 +259,7 @@ void registerMiscTypes(sol::state& lua) lua_plane["b"] = &Plane::b; lua_plane["c"] = &Plane::c; lua_plane["d"] = &Plane::d; - lua_plane["HeightAt"] = sol::resolve(&Plane::heightAt); + lua_plane["HeightAt"] = sol::resolve(&Plane::heightAt); // MemChunk type registerMemChunkType(lua); diff --git a/src/Scripting/Export/Graphics.cpp b/src/Scripting/Export/Graphics.cpp index d1dbd3415..d0330e427 100644 --- a/src/Scripting/Export/Graphics.cpp +++ b/src/Scripting/Export/Graphics.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -44,6 +44,8 @@ using namespace slade; +// ReSharper disable CppParameterMayBeConstPtrOrRef + // ----------------------------------------------------------------------------- // @@ -253,17 +255,15 @@ void registerImageType(sol::state& lua) [](SImage& self, Translation* t, Palette* p) { return imageApplyTranslation(self, t, p, false); }, &imageApplyTranslation); lua_image["DrawPixel"] = sol::overload( - &SImage::drawPixel, [](SImage& self, int x, int y, ColRGBA& col, SImage::DrawProps& props) { - return self.drawPixel(x, y, col, props, nullptr); - }); + &SImage::drawPixel, + [](SImage& self, int x, int y, ColRGBA& col, SImage::DrawProps& props) + { return self.drawPixel(x, y, col, props, nullptr); }); lua_image["DrawImage"] = sol::overload( &imageDrawImage, - [](SImage& self, int x, int y, SImage& img, SImage::DrawProps& props, Palette* pal_src) { - return imageDrawImage(self, x, y, img, props, pal_src, nullptr); - }, - [](SImage& self, int x, int y, SImage& img, SImage::DrawProps& props) { - return imageDrawImage(self, x, y, img, props, nullptr, nullptr); - }); + [](SImage& self, int x, int y, SImage& img, SImage::DrawProps& props, Palette* pal_src) + { return imageDrawImage(self, x, y, img, props, pal_src, nullptr); }, + [](SImage& self, int x, int y, SImage& img, SImage::DrawProps& props) + { return imageDrawImage(self, x, y, img, props, nullptr, nullptr); }); lua_image["Colourise"] = sol::overload( [](SImage& self, ColRGBA& col, Palette* pal) { self.colourise(col, pal); }, [](SImage& self, ColRGBA& col) { self.colourise(col); }); @@ -341,9 +341,8 @@ void registerPaletteType(sol::state& lua) lua_palette["Illuminate"] = &Palette::illuminate; lua_palette["Shift"] = &Palette::shift; lua_palette["Invert"] = &Palette::invert; - lua_palette["Gradient"] = [](Palette& self, const ColRGBA& startC, const ColRGBA& endC, int startI, int endI) { - self.setGradient(startI, endI, startC, endC); - }; + lua_palette["Gradient"] = [](Palette& self, const ColRGBA& startC, const ColRGBA& endC, int startI, int endI) + { self.setGradient(startI, endI, startC, endC); }; } // ----------------------------------------------------------------------------- @@ -503,24 +502,18 @@ void registerTranslationType(sol::state& lua) lua_translation["Range"] = &Translation::range; lua_translation["Parse"] = &Translation::parse; lua_translation["AddRange"] = &Translation::parseRange; - lua_translation["AddPaletteRange"] = [](Translation& self, int range_start, int range_end) { - return addTranslationRange(self, TransRange::Type::Palette, range_start, range_end); - }; - lua_translation["AddColourRange"] = [](Translation& self, int range_start, int range_end) { - return addTranslationRange(self, TransRange::Type::Colour, range_start, range_end); - }; - lua_translation["AddDesatRange"] = [](Translation& self, int range_start, int range_end) { - return addTranslationRange(self, TransRange::Type::Desat, range_start, range_end); - }; - lua_translation["AddBlendRange"] = [](Translation& self, int range_start, int range_end) { - return addTranslationRange(self, TransRange::Type::Blend, range_start, range_end); - }; - lua_translation["AddTintRange"] = [](Translation& self, int range_start, int range_end) { - return addTranslationRange(self, TransRange::Type::Tint, range_start, range_end); - }; - lua_translation["AddSpecialRange"] = [](Translation& self, int range_start, int range_end) { - return addTranslationRange(self, TransRange::Type::Special, range_start, range_end); - }; + lua_translation["AddPaletteRange"] = [](Translation& self, int range_start, int range_end) + { return addTranslationRange(self, TransRange::Type::Palette, range_start, range_end); }; + lua_translation["AddColourRange"] = [](Translation& self, int range_start, int range_end) + { return addTranslationRange(self, TransRange::Type::Colour, range_start, range_end); }; + lua_translation["AddDesatRange"] = [](Translation& self, int range_start, int range_end) + { return addTranslationRange(self, TransRange::Type::Desat, range_start, range_end); }; + lua_translation["AddBlendRange"] = [](Translation& self, int range_start, int range_end) + { return addTranslationRange(self, TransRange::Type::Blend, range_start, range_end); }; + lua_translation["AddTintRange"] = [](Translation& self, int range_start, int range_end) + { return addTranslationRange(self, TransRange::Type::Tint, range_start, range_end); }; + lua_translation["AddSpecialRange"] = [](Translation& self, int range_start, int range_end) + { return addTranslationRange(self, TransRange::Type::Special, range_start, range_end); }; lua_translation["ReadTable"] = &Translation::read; lua_translation["AsText"] = &Translation::asText; lua_translation["Clear"] = &Translation::clear; @@ -666,7 +659,7 @@ void registerPatchTableType(sol::state& lua) lua_ptable["Patch"] = [](PatchTable& self, unsigned index) { return self.patch(index).name; }; lua_ptable["PatchEntry"] = sol::overload( [](PatchTable& self, int index) { return self.patchEntry(index); }, - sol::resolve(&PatchTable::patchEntry)); + sol::resolve(&PatchTable::patchEntry)); lua_ptable["RemovePatch"] = [](PatchTable& self, int index) { self.removePatch(index); }; lua_ptable["ReplacePatch"] = [](PatchTable& self, int index, string_view name) { self.replacePatch(index, name); }; lua_ptable["AddPatch"] = &PatchTable::addPatch; @@ -789,7 +782,8 @@ void registerGraphicsNamespace(sol::state& lua) // Functions // ------------------------------------------------------------------------- gfx["ImageFormat"] = [](string_view id) { return SIFormat::getFormat(id); }; - gfx["AllImageFormats"] = []() { + gfx["AllImageFormats"] = []() + { vector formats; SIFormat::putAllFormats(formats); return formats; diff --git a/src/Scripting/Export/MapEditor.cpp b/src/Scripting/Export/MapEditor.cpp index 40a8c9795..488e0ac75 100644 --- a/src/Scripting/Export/MapEditor.cpp +++ b/src/Scripting/Export/MapEditor.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -31,13 +31,28 @@ // // ----------------------------------------------------------------------------- #include "Main.h" +#include "MapEditor/MapEditor.h" #include "Game/Configuration.h" #include "MapEditor/MapEditContext.h" +#include "SLADEMap/MapObject/MapLine.h" #include "SLADEMap/MapObject/MapObject.h" +#include "SLADEMap/MapObject/MapSector.h" +#include "SLADEMap/MapObject/MapSide.h" +#include "SLADEMap/MapObject/MapThing.h" +#include "SLADEMap/MapObject/MapVertex.h" +#include "SLADEMap/MapObjectList/LineList.h" +#include "SLADEMap/MapObjectList/SectorList.h" +#include "SLADEMap/MapObjectList/SideList.h" +#include "SLADEMap/MapObjectList/ThingList.h" +#include "SLADEMap/MapObjectList/VertexList.h" +#include "SLADEMap/SLADEMap.h" #include "Scripting/Lua.h" #include "thirdparty/sol/sol.hpp" using namespace slade; +using namespace mapeditor; + +// ReSharper disable CppParameterMayBeConstPtrOrRef // ----------------------------------------------------------------------------- @@ -120,7 +135,7 @@ void registerSLADEMap(sol::state& lua) void selectMapObject(MapEditContext& self, MapObject* object, bool select) { if (object) - self.selection().select({ (int)object->index(), mapeditor::itemTypeFromObject(object) }, select); + self.selection().select({ static_cast(object->index()), mapeditor::itemTypeFromObject(object) }, select); } // ----------------------------------------------------------------------------- @@ -181,9 +196,8 @@ void registerMapEditor(sol::state& lua) &selectMapObject, [](MapEditContext& self, MapObject* object) { selectMapObject(self, object, true); }); lua_mapeditor["SetEditMode"] = sol::overload( [](MapEditContext& self, mapeditor::Mode mode) { setEditMode(self, mode); }, - [](MapEditContext& self, mapeditor::Mode mode, mapeditor::SectorMode sector_mode) { - setEditMode(self, mode, sector_mode); - }); + [](MapEditContext& self, mapeditor::Mode mode, mapeditor::SectorMode sector_mode) + { setEditMode(self, mode, sector_mode); }); } // ----------------------------------------------------------------------------- diff --git a/src/Scripting/Export/UI.cpp b/src/Scripting/Export/UI.cpp index a70aef310..389e5036d 100644 --- a/src/Scripting/Export/UI.cpp +++ b/src/Scripting/Export/UI.cpp @@ -1,9 +1,9 @@ #include "Main.h" +#include "General/UI.h" #include "Export.h" #include "Scripting/Lua.h" #include "UI/Dialogs/ExtMessageDialog.h" -#include "UI/Dialogs/Preferences/ACSPrefsPanel.h" #include "Utility/SFileDialog.h" #include "thirdparty/sol/sol.hpp" @@ -42,10 +42,10 @@ void messageBox(const string& title, const string& message, MessageBoxIcon icon long style = 4 | wxCENTRE; switch (icon) { - case MessageBoxIcon::Info: style |= wxICON_INFORMATION; break; + case MessageBoxIcon::Info: style |= wxICON_INFORMATION; break; case MessageBoxIcon::Question: style |= wxICON_QUESTION; break; - case MessageBoxIcon::Warning: style |= wxICON_WARNING; break; - case MessageBoxIcon::Error: style |= wxICON_ERROR; break; + case MessageBoxIcon::Warning: style |= wxICON_WARNING; break; + case MessageBoxIcon::Error: style |= wxICON_ERROR; break; } wxMessageBox(message, title, style, currentWindow()); @@ -77,7 +77,7 @@ string promptString(const string& title, const string& message, const string& de // ----------------------------------------------------------------------------- int promptNumber(const string& title, const string& message, int default_value, int min, int max) { - return (int)wxGetNumberFromUser(message, "", title, default_value, min, max); + return static_cast(wxGetNumberFromUser(message, "", title, default_value, min, max)); } // ----------------------------------------------------------------------------- diff --git a/src/Scripting/Lua.cpp b/src/Scripting/Lua.cpp index 130e139ff..629d8bf4c 100644 --- a/src/Scripting/Lua.cpp +++ b/src/Scripting/Lua.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -31,6 +31,7 @@ // ----------------------------------------------------------------------------- #include "Main.h" #include "Lua.h" +#include "Archive/Archive.h" #include "Export/Export.h" #include "General/Console.h" #include "General/Misc.h" @@ -345,11 +346,11 @@ void lua::setCurrentWindow(wxWindow* window) CONSOLE_COMMAND(script, 1, true) { - auto script = args[0]; + auto script_text = args[0]; for (unsigned a = 1; a < args.size(); a++) - script += " " + args[a]; + script_text += " " + args[a]; - lua::run(script); + lua::run(script_text); } CONSOLE_COMMAND(script_file, 1, true) diff --git a/src/Scripting/ScriptManager.cpp b/src/Scripting/ScriptManager.cpp index 2f6a66f65..f467f7c49 100644 --- a/src/Scripting/ScriptManager.cpp +++ b/src/Scripting/ScriptManager.cpp @@ -1,7 +1,7 @@ // ----------------------------------------------------------------------------- // SLADE - It's a Doom Editor -// Copyright(C) 2008 - 2022 Simon Judd +// Copyright(C) 2008 - 2024 Simon Judd // // Email: sirjuddington@gmail.com // Web: http://slade.mancubus.net @@ -73,7 +73,7 @@ namespace slade::scriptmanager // Adds a new editor script of [type], created from [entry]. [cut_path] will be // removed from the start of the script's path property // ----------------------------------------------------------------------------- -Script* addEditorScriptFromEntry(shared_ptr& entry, ScriptType type, string_view cut_path) +Script* addEditorScriptFromEntry(const shared_ptr& entry, ScriptType type, string_view cut_path) { auto s = std::make_unique