From 2e08e563a6989b30f3a8839d6503ebd614160252 Mon Sep 17 00:00:00 2001 From: poikilos <7557867+poikilos@users.noreply.github.com> Date: Sun, 28 Nov 2021 16:17:17 -0500 Subject: [PATCH] Add options: --count-meshes, --verbose, --help, --exit. See changelog for more. --- Engine.cpp | 99 ++++++++++++++++++++++------- Engine.h | 5 +- UserInterface.cpp | 154 ++++++++++++++++++++++++++++++++-------------- View.cpp | 28 ++++++--- changelog.md | 15 ++++- main.cpp | 4 +- readme.md | 9 +++ 7 files changed, 237 insertions(+), 77 deletions(-) diff --git a/Engine.cpp b/Engine.cpp index 95aae47..84ab19b 100644 --- a/Engine.cpp +++ b/Engine.cpp @@ -340,7 +340,10 @@ s32 Engine::getNumberOfVertices() Engine::Engine() { - this->m_EnableTestAndExit = false; + this->m_EnableTests = false; + this->m_EnableCountMeshes = false; + this->m_EnableVerbose = false; + this->m_EnableExit = false; settings.set_int("max_recent", 10); std::string profile = std::getenv("HOME"); // ^ changes to USERPROFILE below if blank @@ -473,15 +476,19 @@ bool Engine::loadMesh(const wstring& fileName, bool enableAddRecent) m_Device->setWindowCaption((wstring(L"b3view - ") + fileName).c_str()); m_LoadedMesh = m_Scene->addAnimatedMeshSceneNode(mesh); - Utility::dumpMeshInfoToConsole(m_LoadedMesh); - std::cerr << "Arranging scene..." << std::flush; + if (this->m_EnableVerbose) { + Utility::dumpMeshInfoToConsole(m_LoadedMesh); + std::cerr << "Arranging scene..." << std::flush; + } if (Utility::toLower(Utility::extensionOf(fileName)) == L"3ds") { m_View->setZUp(true); } else { m_View->setZUp(false); } if (m_LoadedMesh != nullptr) { - std::cerr << "unloading old mesh..." << std::flush; + if (this->m_EnableVerbose) { + std::cerr << "unloading old mesh..." << std::flush; + } ret = true; this->m_UserInterface->playbackFPSEditBox->setText( Utility::toWstring(m_LoadedMesh->getAnimationSpeed()).c_str() @@ -534,14 +541,20 @@ bool Engine::loadMesh(const wstring& fileName, bool enableAddRecent) // EMT_TRANSPARENT_ALPHA_CHANNEL: constant transparency } - std::cerr << "setting display mode..." << std::flush; + if (this->m_EnableVerbose) { + std::cerr << "setting display mode..." << std::flush; + } this->setMeshDisplayMode(this->m_EnableWireframe, this->m_EnableLighting, this->m_EnableTextureInterpolation); - std::cerr << "preparing UI..." << std::flush; + if (this->m_EnableVerbose) { + std::cerr << "preparing UI..." << std::flush; + } if (this->m_UserInterface != nullptr) this->m_UserInterface->OnSelectMesh(); - std::cerr << "checking for textures..." << std::flush; - std::cerr << "OK" << std::endl; + if (this->m_EnableVerbose) { + std::cerr << "checking for textures..." << std::flush; + std::cerr << "OK" << std::endl; + } if (Utility::getTextureCount(m_LoadedMesh) == 0) { // NOTE: getMaterialCount doesn't work, since there may not // be loaded textures in any material. @@ -549,7 +562,9 @@ bool Engine::loadMesh(const wstring& fileName, bool enableAddRecent) this->m_UserInterface->loadNextTexture(0); } } - std::cerr << "detecting last frame..." << std::flush; + if (this->m_EnableVerbose) { + std::cerr << "detecting last frame..." << std::flush; + } std::wstring prevStartStr; std::wstring prevEndStr; if (this->m_UserInterface->playbackMenu->getItemText(UIE_PLAYBACKSTARTFRAMEEDITBOX) != nullptr) @@ -565,16 +580,22 @@ bool Engine::loadMesh(const wstring& fileName, bool enableAddRecent) prevEnd = Utility::toF32(prevEndStr); // std::cerr << prevEnd << "..." << std::flush; f32 endFrameF32 = static_cast(m_LoadedMesh->getEndFrame()); - std::cerr << endFrameF32 << "..." << std::flush; + if (this->m_EnableVerbose) { + std::cerr << endFrameF32 << "..." << std::flush; + } if (prevEnd < 0 || prevEnd > endFrameF32) { - std::cerr << "showing End Frame..." << std::flush; + if (this->m_EnableVerbose) { + std::cerr << "showing End Frame..." << std::flush; + } this->m_UserInterface->setPlaybackText( UIE_PLAYBACKENDFRAMEEDITBOX, Utility::toWstring(endFrameF32).c_str() ); } if (prevStart < 0 || prevStart > endFrameF32) { - std::cerr << "showing Start Frame..." << std::flush; + if (this->m_EnableVerbose) { + std::cerr << "showing Start Frame..." << std::flush; + } this->m_UserInterface->setPlaybackText( UIE_PLAYBACKSTARTFRAMEEDITBOX, L"0.0" @@ -582,7 +603,9 @@ bool Engine::loadMesh(const wstring& fileName, bool enableAddRecent) } //this->m_UserInterface->playbackMenu->setItemText(UIE_PLAYBACKSTARTFRAMEEDITBOX, ); //; - std::cerr << "OK" << std::endl; + if (this->m_EnableVerbose) { + std::cerr << "OK" << std::endl; + } } // Don't do anything outside of the mesh != nullptr case that will try to // use mesh! @@ -592,8 +615,26 @@ bool Engine::loadMesh(const wstring& fileName, bool enableAddRecent) bool Engine::pushOption(const std::wstring& optionStr) { if (optionStr == L"--test-and-exit") { - this->m_EnableTestAndExit = true; - std::cerr << "* using option --test-and-exit" << std::endl; + this->m_EnableTests = true; + this->m_EnableExit = true; + } + else if (optionStr == L"--exit") { + this->m_EnableExit = true; + } + else if (optionStr == L"--count-meshes") { + this->m_EnableCountMeshes = true; + } + else if (optionStr == L"--verbose") { + this->m_EnableVerbose = true; + } + else if (optionStr == L"--help") { + std::cerr + << "--test-and-exit Run tests then exit the program." << std::endl + << "--count-meshes Count the number of meshes in the file." << std::endl + << "--verbose Show mesh metadata (must be before mesh filename to show that) and internal events." << std::endl + << "--exit Exit the program after processing other options." << std::endl + ; + this->m_EnableExit = true; } else { std::cerr << "The option is not valid: " << Utility::toString(optionStr) << std::endl; @@ -742,13 +783,17 @@ bool Engine::loadTexture(const wstring& fileName, bool reload) debug() << "* failed to load " << "" << std::endl; } this->m_LoadedTexturePath = fileName; - std::cerr << "Setting texture path box to " << Utility::toString(this->m_LoadedTexturePath) << std::endl; + if (this->m_EnableVerbose) { + std::cerr << "Setting texture path box to " << Utility::toString(this->m_LoadedTexturePath) << std::endl; + } this->m_UserInterface->texturePathEditBox->setText( this->m_LoadedTexturePath.c_str() ); } else { - std::cerr << "NOT Setting texture path box to " << Utility::toString(this->m_LoadedTexturePath) << std::endl; + if (this->m_EnableVerbose) { + std::cerr << "NOT Setting texture path box to " << Utility::toString(this->m_LoadedTexturePath) << std::endl; + } } return ret; } @@ -916,9 +961,15 @@ void Engine::run() // Run the Device with fps frames/sec while (m_Device->run() && m_RunEngine) { - if (this->m_EnableTestAndExit) { + if (this->m_EnableCountMeshes) { + this->m_EnableCountMeshes = false; + if (this->m_LoadedMesh != nullptr) { + std::cout << "mesh_count=" << this->m_LoadedMesh->getMesh()->getMeshBufferCount() << std::endl; + } + } + if (this->m_EnableTests) { std::cerr << "* running tests..." << std::endl; - this->m_EnableTestAndExit = false; + this->m_EnableTests = false; std::cerr << "* loading test model..." << std::endl; if (!this->loadMesh(L"dist/share/b3view/meshes/penguin-lowpoly-poikilos.b3d", false)) { throw "loading dist/share/b3view/meshes/penguin-lowpoly-poikilos.b3d failed."; @@ -927,9 +978,15 @@ void Engine::run() if (!this->m_UserInterface->loadNextTexture(1)) { throw "loading the next texture for dist/share/b3view/meshes/penguin-lowpoly-poikilos.b3d failed."; } - this->m_RunEngine = false; - // Don't break yet. Test the main event loop tooo. } + if (this->m_EnableExit) { + this->m_RunEngine = false; + if (!this->m_EnableTests) { + break; + } + // else don't break yet: Test the main event loop too. + } + u32 startTime = timer->getRealTime(); checkResize(); diff --git a/Engine.h b/Engine.h index 00dc7be..4a4b56c 100644 --- a/Engine.h +++ b/Engine.h @@ -40,7 +40,10 @@ private: bool m_EnableWireframe; bool m_EnableLighting; bool m_EnableTextureInterpolation; - bool m_EnableTestAndExit; + bool m_EnableTests; + bool m_EnableExit; + bool m_EnableCountMeshes; + bool m_EnableVerbose; EventHandler* m_EventHandler; UserInterface* m_UserInterface; diff --git a/UserInterface.cpp b/UserInterface.cpp index 9e54eea..36639d9 100644 --- a/UserInterface.cpp +++ b/UserInterface.cpp @@ -37,7 +37,12 @@ void UserInterface::setupUserInterface() { this->recent_initialized = false; this->recentMenu = nullptr; - + bool enableVerbose = false; + if (this->m_Engine != nullptr) { + enableVerbose = this->m_Engine->m_EnableVerbose; + } else { + std::cerr << "Error: The engine is not ready in setupUserInterface." << std::endl; + } // Menu menu = m_Gui->addMenu(); this->fileMenuIdx = menu->addItem(L"File", UIE_FILEMENU, true, true); @@ -63,13 +68,16 @@ void UserInterface::setupUserInterface() // File, Open Recent submenu this->recentMenu = fileMenu->getSubMenu(this->fileRecentIdx); - std::cerr << "+this->recentMenu text:\"" << Utility::toString((wstring)this->recentMenu->getText()) << "\"" - << " idx:" << Utility::toString((int)this->fileRecentIdx) - << " id:" << Utility::toString((int)this->recentMenu->getID()) - << std::endl; - + if (enableVerbose) { + std::cerr << "+this->recentMenu text:\"" << Utility::toString((wstring)this->recentMenu->getText()) << "\"" + << " idx:" << Utility::toString((int)this->fileRecentIdx) + << " id:" << Utility::toString((int)this->recentMenu->getID()) + << std::endl; + } this->fileRecentClearIdx = this->recentMenu->addItem(L"Clear Recent", UIC_FILE_RECENT_CLEAR); - std::cerr << "+this->fileRecentClearIdx: " << this->fileRecentClearIdx << std::endl; + if (enableVerbose) { + std::cerr << "+this->fileRecentClearIdx: " << this->fileRecentClearIdx << std::endl; + } this->uic_file_recent_next = UserInterface::UIC_FILE_RECENT_FIRST; this->m_file_recent_first_idx = -1; this->m_file_recent_last_idx = -1; @@ -303,12 +311,16 @@ void UserInterface::setupUserInterface() m_GuiFont->attach(m_GuiFontFace, 14); m_Gui->getSkin()->setFont(m_GuiFont); } else { - std::wcerr << L"WARNING: '" << m_Engine->m_FontPath << L"' is missing." - << endl; + if (enableVerbose) { + std::wcerr << L"WARNING: '" << m_Engine->m_FontPath << L"' is missing." + << endl; + } delete m_GuiFontFace; m_GuiFontFace = nullptr; if (m_GuiFont != nullptr) { - std::wcerr << L" - The old font will remain loaded." << endl; + if (enableVerbose) { + std::wcerr << L" - The old font will remain loaded." << endl; + } } } // } @@ -359,21 +371,26 @@ bool UserInterface::handleMenuItemPressed(const SEvent::SGUIEvent* ge) s32 callerID = ge->Caller->getID(); s32 selected = menu->getSelectedItem(); s32 commandID = menu->getItemCommandId(static_cast(selected)); + bool enableVerbose = this->m_Engine->m_EnableVerbose; switch (callerID) { case UIE_RECENTMENU: // if ((ge->Caller->getID() >= this->m_file_recent_first_idx) // && (ge->Caller->getID() <= m_file_recent_last_idx)) { // NOTE: ge->Caller->getID() is probably UIE_RECENTMENU now, but that is not to be used directly! - cerr << "selected " << selected << std::endl; + if (enableVerbose) { + cerr << "selected " << selected << std::endl; + } if (std::find(this->recentIndices.begin(), this->recentIndices.end(), commandID) != this->recentIndices.end()) { // ge->Caller->getText() // Don't do this. Caller is the parent! - cerr << "parent callerID: " << callerID << endl; - // ^ callerID is the parent such as 1100 (or whatever UI_RECENTMENU is) - cerr << " commandID: " << commandID << std::endl; - // ^ commandID is a menu id specified on creation - // such as starting from 1101 - // or from whatever UIC_FILE_RECENT_FIRST is--usually UI_RECENTMENU+1). - // selectedItemID is a sequential number. + if (enableVerbose) { + cerr << "parent callerID: " << callerID << endl; + // ^ callerID is the parent such as 1100 (or whatever UI_RECENTMENU is) + cerr << " commandID: " << commandID << std::endl; + // ^ commandID is a menu id specified on creation + // such as starting from 1101 + // or from whatever UIC_FILE_RECENT_FIRST is--usually UI_RECENTMENU+1). + // selectedItemID is a sequential number. + } // std::wstring menuItemText = menu->getItemText(selected); this->openRecent(commandID, selected); } @@ -381,13 +398,16 @@ bool UserInterface::handleMenuItemPressed(const SEvent::SGUIEvent* ge) cerr << "Unknown commandID: " << commandID << " Text:" << Utility::toString(menu->getItemText(selected)) << endl; // ^ getItemText takes the index (NOT the commandID specified on creation) if (this->recentIndices.size() < 1) { + cerr << "- recentIndices.size(): " << recentIndices.size() << endl; } else { - cerr << " recentIndices: " << recentIndices.size() << endl; - // range based for loop requires C++11 or higher: - for(irr::u32 i : this->recentIndices) { - cerr << " - " << i << endl; + if (enableVerbose) { + cerr << " recentIndices: " << recentIndices.size() << endl; + // range based for loop requires C++11 or higher: + for(irr::u32 i : this->recentIndices) { + cerr << " - " << i << endl; + } } } handled = false; @@ -653,7 +673,13 @@ void UserInterface::setPlaybackText(s32 id, const wchar_t* text) */ bool UserInterface::loadNextTexture(int direction) { - cerr << "Loading texture..." << flush; + bool enableVerbose = false; + if (this->m_Engine != nullptr) { + enableVerbose = this->m_Engine->m_EnableVerbose; + } + if (enableVerbose) { + cerr << "Loading texture..." << flush; + } bool ret = false; std::wstring basePath = L"."; if (this->m_Engine->m_LoadedMeshPath.length() > 0) { @@ -746,9 +772,11 @@ bool UserInterface::loadNextTexture(int direction) vector paths = this->m_MatchingTextures; if (this->m_MatchingTextures.size() < 1) { paths = this->m_AllTextures; - debug() << "There were no matching textures so" - << " the entire list of " << this->m_AllTextures.size() - << " found textures will be used..." << std::flush; + if (enableVerbose) { + debug() << "There were no matching textures so" + << " the entire list of " << this->m_AllTextures.size() + << " found textures will be used..." << std::flush; + } } else { // Assume the user wants to view name-matched texture using @@ -796,43 +824,60 @@ bool UserInterface::loadNextTexture(int direction) } if (lastTexture.length() > 0) { if (direction < 0) { - cerr << "loading the previous texture..."; + if (enableVerbose) { + cerr << "loading the previous texture..."; + } ret = this->m_Engine->loadTexture(prevTexture, false); } else if (direction > 0) { - cerr << "loading the next texture..."; + if (enableVerbose) { + cerr << "loading the next texture..."; + } ret = this->m_Engine->loadTexture(nextTexture, false); } else { // If direction is 0 (such as when a model is loaded that has // no texture), only load a specified or matching texture. if (this->m_Engine->m_LoadedTexturePath.length() > 0) { - cerr << "using a specified texture..."; + if (enableVerbose) { + cerr << "using a specified texture..."; + } ret = this->m_Engine->loadTexture( this->m_Engine->m_LoadedTexturePath, false ); } else if (this->m_MatchingTextures.size() >= 1) { - cerr << "loading matching texture..."; + if (enableVerbose) { + cerr << "loading matching texture..."; + } ret = this->m_Engine->loadTexture(firstTexture, false); } else { ret = true; - cerr << "(cycling was off and there is no matching texture) "; + if (enableVerbose) { + cerr << "(cycling was off and there is no matching texture) "; + } } } } else if (this->m_Engine->m_LoadedTexturePath.length() > 0) { - cerr << "loading the first texture..."; + if (enableVerbose) { + cerr << "loading the first texture..."; + } ret = this->m_Engine->loadTexture( this->m_Engine->m_LoadedTexturePath, false ); } - } else - debug() << "Can't cycle texture since no file was opened" << endl; - cerr << (ret?"OK":"FAILED") << endl; + } else { + if (enableVerbose) { + debug() << "Can't cycle texture since no file was opened" << endl; + } + } + if (enableVerbose) { + cerr << (ret?"OK":"FAILED") << endl; + } return ret; } @@ -888,12 +933,22 @@ void UserInterface::clearRecent() void UserInterface::addRecentMenuItem(std::string path, bool addToEngine) { + bool enableVerbose = false; + if (this->m_Engine != nullptr) { + enableVerbose = this->m_Engine->m_EnableVerbose; + } else { + std::cerr << "Error: m_Engine isn't ready in addRecentMenuItem." << std::endl; + } if (!this->recent_initialized) { throw std::runtime_error("The UI is not ready in addRecentMenuItem."); } - std::cerr << "[addRecentMenuItem] " << path << "..." << std::endl; + if (enableVerbose) { + std::cerr << "[addRecentMenuItem] " << path << "..." << std::endl; + } if (!this->hasRecent(path)) { - std::cerr << "* adding since new..." << std::endl; + if (enableVerbose) { + std::cerr << "* adding since new..." << std::endl; + } wstring path_ws = Utility::toWstring(path); if (this->uic_file_recent_next < UserInterface::UIC_FILE_RECENT_FIRST) { throw std::runtime_error("this->uic_file_recent_next is " @@ -904,10 +959,12 @@ void UserInterface::addRecentMenuItem(std::string path, bool addToEngine) // The first this->uic_file_recent_next is 1101 or whatever // UserInterface::UIC_FILE_RECENT_FIRST (usually UIC_FILE_RECENT+1) is. u32 newI = this->recentMenu->addItem(path_ws.c_str(), this->uic_file_recent_next); - std::cerr << "+this->recentMenu->addItem" - << " idx:" << newI - << " commandID:" << this->uic_file_recent_next - << std::endl; + if (enableVerbose) { + std::cerr << "+this->recentMenu->addItem" + << " idx:" << newI + << " commandID:" << this->uic_file_recent_next + << std::endl; + } // IGUIContextMenu* menu = this->recentMenu->getSubMenu(newI); // NOTE: Caller would be the parent menu id on click! // newI is a sequential number starting at 1 which becomes the @@ -945,12 +1002,19 @@ void UserInterface::addRecentMenuItems(std::vector paths, bool addT bool UserInterface::hasRecent(std::string path) { + bool enableVerbose = false; + if (this->m_Engine != nullptr) { + enableVerbose = this->m_Engine->m_EnableVerbose; + } else { + std::cerr << "Error: The engine is not ready in hasRecent." << std::endl; + } if (!this->recent_initialized) { throw std::runtime_error("The UI is not ready in addRecent."); } - std::cerr << " [hasRecent]" << std::endl; - std::cerr << " * checking children..." << std::endl; - + if (enableVerbose) { + std::cerr << " [hasRecent]" << std::endl; + std::cerr << " * checking children..." << std::endl; + } // See http://irrlicht.sourceforge.net/docu/_i_g_u_i_element_8h_source.html#l00570 // core::list< IGUIElement * > Children = this->getChildren(); // ^ ‘class UserInterface’ has no member named ‘getChildren’ @@ -1264,7 +1328,7 @@ bool UserInterface::OnEvent(const SEvent& event) handled = false; break; case EGET_ELEMENT_LEFT: - debug() << "left " << callerID << "." << std::endl; + // debug() << "left " << callerID << "." << std::endl; handled = false; break; case EGET_MENU_ITEM_SELECTED: diff --git a/View.cpp b/View.cpp index 8029d63..dc71f93 100644 --- a/View.cpp +++ b/View.cpp @@ -120,7 +120,15 @@ View::View(Engine* engine) // m_Yaw = rotationVec3.Y; // m_Pitch = rotationVec3.X; - debug() << "STARTING Yaw: " << radToDeg(m_YawFromTarget)<< " Pitch: " << radToDeg(m_PitchFromTarget) << endl; + bool enableVerbose = false; + if (this->m_Engine != nullptr) { + enableVerbose = this->m_Engine->m_EnableVerbose; + } else { + std::cerr << "Error: The engine is not ready in View::View." << std::endl; + } + if (enableVerbose) { + debug() << "STARTING Yaw: " << radToDeg(m_YawFromTarget)<< " Pitch: " << radToDeg(m_PitchFromTarget) << endl; + } setNewCameraPosition(); } @@ -225,12 +233,18 @@ bool View::OnEvent(const SEvent& event) m_CameraDistance /= 2; } setNewCameraPosition(); - debug() << "View got the event and used event.MouseInput." - // << " event.GUIEvent.Caller: " << callerID // not avail in Irrlicht (Use this->m_MouseUser instead) - << ", m_CamPos: " << m_Engine->m_CamPos.X - << "," << m_Engine->m_CamPos.Y - << " m_CamTarget: " << m_Engine->m_CamTarget.X - << "," << m_Engine->m_CamTarget.Y << endl; + bool enableVerbose = true; + if (this->m_Engine != nullptr) { + enableVerbose = this->m_Engine->m_EnableVerbose; + } + if (enableVerbose) { + debug() << "View got the event and used event.MouseInput." + // << " event.GUIEvent.Caller: " << callerID // not avail in Irrlicht (Use this->m_MouseUser instead) + << ", m_CamPos: " << m_Engine->m_CamPos.X + << "," << m_Engine->m_CamPos.Y + << " m_CamTarget: " << m_Engine->m_CamTarget.X + << "," << m_Engine->m_CamTarget.Y << endl; + } } else if (m_RotMouse) { // debug() << "Yaw: " << radToDeg(m_Yaw) << " Pitch: " << radToDeg(m_Pitch) << endl; int dx = mouseEvent->X - m_LastMousePosition->X; diff --git a/changelog.md b/changelog.md index f70fd0f..559ed3b 100644 --- a/changelog.md +++ b/changelog.md @@ -3,9 +3,21 @@ All notable changes to this project will be documented in this file. The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/). + +## [git] - 2021-11-28 +### Added +- --exit option + +### Changed +- Split the `m_EnableTests` and `m_EnableExit` options (from + `m_EnableTestAndExit`). +- Reduce verbosity unless `--verbose` is specified. + + ## [git] - 2021-03-28 ### Added -- a `--test-and-exit ` option +- a `--test-and-exit` option + ## [git] - 2021-02-22 ### Added @@ -14,6 +26,7 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/). ### Fixed - identification of recent menu items + ## [git] - 2021-02-21 ### Added - codeblocks support diff --git a/main.cpp b/main.cpp index 663ad45..6300312 100644 --- a/main.cpp +++ b/main.cpp @@ -40,8 +40,8 @@ int main(int argc, char** argv) Engine* engine = new Engine(); if (argc >= 2) { for (int i = 1; i < argc; i++) { - wchar_t* optionCS = getWideCharString(argv[1]); - if ((strlen(argv[i]) >=2) && (argv[i][0] == '-') && argv[i][1] == '-') { + wchar_t* optionCS = getWideCharString(argv[i]); + if ((strlen(argv[i]) >=2 ) && (argv[i][0] == '-') && (argv[i][1] == '-')) { engine->pushOption(wstring(optionCS)); } else { diff --git a/readme.md b/readme.md index d4a53e8..eff2dd2 100644 --- a/readme.md +++ b/readme.md @@ -9,6 +9,7 @@ bat: [github.com/poikilos/mobs_sky](https://github.com/poikilos/mobs_sky) Website: [poikilos.org](https://poikilos.org) + ## Requirements - libirrlicht (such as libirrlicht1.8 and libirrlicht-dev on Debian 10) - freetype (such as libfreetype6 and libfreetype6-dev on Debian 10) @@ -36,6 +37,7 @@ CodeBlocks says it is looking for boost_filesystem and boost_system, which may b - In CodeBlocks (once per computer): Settings, Compiler, Search paths, /usr/include/freetype2 * libboost-system-dev + ## Main Features in poikilos fork * stabilized (makes sure font, model or texture loads before using; makes sure model is loaded before setting View options) @@ -57,6 +59,13 @@ CodeBlocks says it is looking for boost_filesystem and boost_system, which may b or `../textures` (where model would be in a parallel directory next to textures). * Set the animation loop range (the animation includes the end frame). +* Use the `--count-meshes` option to count the number of meshes in the + model file (such as for knowing how many copies of the Minetest + texture to apply for each variant). +* Use the `--verbose` option to see model metadata (**before** the model + filename if a filename is part of the command) and various internal + events. +* Use the --help option to see additional features. ## Related Software