From 2e5c5be35799dfe9ac5b4d21df2d4788618b7fe8 Mon Sep 17 00:00:00 2001 From: Mark Vejvoda Date: Sat, 29 Jan 2011 03:53:05 +0000 Subject: [PATCH] - added more options to g3d viewer commandline options --- source/g3d_viewer/main.cpp | 190 +++++++++++++++++- source/g3d_viewer/main.h | 10 +- source/g3d_viewer/renderer.cpp | 47 +---- source/g3d_viewer/renderer.h | 1 + source/shared_lib/include/graphics/particle.h | 29 ++- .../shared_lib/sources/graphics/particle.cpp | 32 +++ 6 files changed, 260 insertions(+), 49 deletions(-) diff --git a/source/g3d_viewer/main.cpp b/source/g3d_viewer/main.cpp index 41a19770..0cd4fbd8 100644 --- a/source/g3d_viewer/main.cpp +++ b/source/g3d_viewer/main.cpp @@ -11,6 +11,7 @@ #include #include #include "game_constants.h" + #ifndef WIN32 #define stricmp strcasecmp #define strnicmp strncasecmp @@ -55,6 +56,7 @@ wxString ToUnicode(const string& str) { const wxChar *GAME_ARGS[] = { wxT("--help"), wxT("--auto-screenshot"), + wxT("--load-unit"), wxT("--load-model"), wxT("--load-model-animation-value"), wxT("--load-particle"), @@ -69,6 +71,7 @@ const wxChar *GAME_ARGS[] = { enum GAME_ARG_TYPE { GAME_ARG_HELP = 0, GAME_ARG_AUTO_SCREENSHOT, + GAME_ARG_LOAD_UNIT, GAME_ARG_LOAD_MODEL, GAME_ARG_LOAD_MODEL_ANIMATION_VALUE, GAME_ARG_LOAD_PARTICLE, @@ -125,8 +128,13 @@ void printParameterHelp(const char *argv0, bool foundInvalidArgs) { printf("Parameter:\t\t\tDescription:"); printf("\n----------------------\t\t------------"); printf("\n%s\t\t\t\tdisplays this help text.",(const char *)wxConvCurrent->cWX2MB(GAME_ARGS[GAME_ARG_HELP])); + + printf("\n%s=x\t\t\tAuto load the unit / skill information specified in path/filename x",(const char *)wxConvCurrent->cWX2MB(GAME_ARGS[GAME_ARG_LOAD_UNIT])); + printf("\n \t\tWhere x is a g3d filename to load seperated with a comma and the skill name to load:"); + printf("\n \t\texample: %s %s=techs/megapack/factions/tech/units/battle_machine,attack_skill",argv0,(const char *)wxConvCurrent->cWX2MB(GAME_ARGS[GAME_ARG_LOAD_MODEL])); + printf("\n%s=x\t\t\tAuto load the model specified in path/filename x",(const char *)wxConvCurrent->cWX2MB(GAME_ARGS[GAME_ARG_LOAD_MODEL])); - printf("\n \t\tWhere x is a G3d filename to load:"); + printf("\n \t\tWhere x is a g3d filename to load:"); printf("\n \t\texample: %s %s=techs/megapack/factions/tech/units/battle_machine/models/battle_machine_dying.g3d",argv0,(const char *)wxConvCurrent->cWX2MB(GAME_ARGS[GAME_ARG_LOAD_MODEL])); printf("\n%s=x\t\tAnimation value when loading a model",(const char *)wxConvCurrent->cWX2MB(GAME_ARGS[GAME_ARG_LOAD_MODEL_ANIMATION_VALUE])); printf("\n \t\tWhere x is a decimal value from -1.0 to 1.0:"); @@ -171,7 +179,8 @@ vector autoScreenShotParams; const string MainWindow::winHeader= "G3D viewer " + g3dviewerVersionString; -MainWindow::MainWindow( const string modelPath, +MainWindow::MainWindow( std::pair unitToLoad, + const string modelPath, const string particlePath, const string projectileParticlePath, const string splashParticlePath, @@ -183,6 +192,9 @@ MainWindow::MainWindow( const string modelPath, { //getGlPlatformExtensions(); renderer= Renderer::getInstance(); + + unitPathList = unitToLoad; + if(modelPath != "") { this->modelPathList.push_back(modelPath); } @@ -196,8 +208,11 @@ MainWindow::MainWindow( const string modelPath, this->particleSplashPathList.push_back(splashParticlePath); } + resetAnimation = false; anim = defaultAnimation; particleLoopStart = defaultParticleLoopStart; + resetAnim = anim; + resetParticleLoopStart = particleLoopStart; rotX= defaultXRot; rotY= defaultYRot; zoom= defaultZoom; @@ -393,6 +408,22 @@ void MainWindow::onPaint(wxPaintEvent &event){ saveScreenshot(); Close(); } + else if(resetAnimation) { + bool haveLoadedParticles = (particleProjectilePathList.size() > 0 || particleSplashPathList.size() > 0); + if(haveLoadedParticles) { + // renderer->hasActiveParticleSystem(ParticleSystem::pst_ProjectileParticleSystem) == false && + // renderer->hasActiveParticleSystem(ParticleSystem::pst_SplashParticleSystem) == false) { + + if(anim >= resetAnim) { + resetAnimation = false; + //anim = resetAnim; + particleLoopStart = resetParticleLoopStart; + + wxCommandEvent event; + onMenuRestart(event); + } + } + } } void MainWindow::onClose(wxCloseEvent &event){ @@ -710,6 +741,119 @@ void MainWindow::onMenuFileExit(wxCommandEvent &event) { Close(); } +void MainWindow::loadUnit(string path, string skillName) { + timer->Stop(); + wxCommandEvent event; + onMenuFileClearAll(event); + + if(path != "" && fileExists(path) == true) { + // std::cout << "Clearing list..." << std::endl; + this->unitPathList.first = path; + this->unitPathList.second = skillName; + } + + try{ + if(this->unitPathList.first != "") { + string titlestring = winHeader; + + string unitPath = this->unitPathList.first; + //string dir= extractDirectoryPathFromFile(unitPath); + string dir = unitPath; + + //size_t pos = dir.find_last_of(folderDelimiter); + //if(pos == dir.length()-1) { + // dir.erase(dir.length() -1); + //} + string name= lastDir(dir); + string path= dir + "/" + name + ".xml"; + + //unitPath= extractFileFromDirectoryPath(unitPath); + titlestring = unitPath + " - "+ titlestring; + + std::string unitXML = path; + + string skillModelFile = ""; + string skillParticleFile = ""; + string skillParticleProjectileFile = ""; + string skillParticleSplashFile = ""; + + printf("Loading unit from file [%s] skill [%s]\n",unitXML.c_str(),this->unitPathList.second.c_str()); + + if(fileExists(unitXML) == true) { + XmlTree xmlTree; + xmlTree.load(unitXML); + const XmlNode *unitNode= xmlTree.getRootNode(); + const XmlNode *skillsNode= unitNode->getChild("skills"); + for(int i = 0; i < skillsNode->getChildCount(); ++i) { + const XmlNode *sn= skillsNode->getChild("skill", i); + const XmlNode *typeNode= sn->getChild("type"); + const XmlNode *nameNode= sn->getChild("name"); + string skillXmlName = nameNode->getAttribute("value")->getRestrictedValue(); + if(skillXmlName == this->unitPathList.second) { + if(sn->getChild("animation") != NULL) + skillModelFile = unitPath + '/' + sn->getChild("animation")->getAttribute("path")->getRestrictedValue(); + + const XmlNode *particlesNode= sn->getChild("particles"); + for(int j = 0; particlesNode != NULL && particlesNode->getAttribute("value")->getRestrictedValue() == "true" && + j < particlesNode->getChildCount(); ++j) { + const XmlNode *pf= particlesNode->getChild("particle-file", j); + if(pf != NULL) { + skillParticleFile = unitPath + '/' + pf->getAttribute("path")->getRestrictedValue(); + break; + } + } + const XmlNode *particlesProjectileNode= sn->getChild("projectile"); + for(int j = 0; particlesProjectileNode != NULL && particlesProjectileNode->getAttribute("value")->getRestrictedValue() == "true" && + j < particlesProjectileNode->getChildCount(); ++j) { + const XmlNode *pf= particlesProjectileNode->getChild("particle", j); + if(pf != NULL && pf->getAttribute("value")->getRestrictedValue() == "true") { + skillParticleProjectileFile = unitPath + '/' + pf->getAttribute("path")->getRestrictedValue(); + break; + } + } + const XmlNode *particlesSplashNode= sn->getChild("splash"); + for(int j = 0; particlesSplashNode != NULL && particlesSplashNode->getAttribute("value")->getRestrictedValue() == "true" && + j < particlesSplashNode->getChildCount(); ++j) { + const XmlNode *pf= particlesSplashNode->getChild("particle", j); + if(pf != NULL && pf->getAttribute("value")->getRestrictedValue() == "true") { + skillParticleSplashFile = unitPath + '/' + pf->getAttribute("path")->getRestrictedValue(); + break; + } + } + + break; + } + } + + if(skillModelFile != "") { + this->modelPathList.push_back(skillModelFile); + } + if(skillParticleFile != "") { + this->particlePathList.push_back(skillParticleFile); + } + if(skillParticleProjectileFile != "") { + this->particleProjectilePathList.push_back(skillParticleProjectileFile); + } + if(skillParticleSplashFile != "") { + this->particleSplashPathList.push_back(skillParticleSplashFile); + } + + glCanvas->SetCurrent(); + renderer->init(); + + //wxCommandEvent event; + //onMenuRestart(event); + } + SetTitle(ToUnicode(titlestring)); + } + } + catch(std::runtime_error e) { + std::cout << e.what() << std::endl; + wxMessageDialog(NULL, ToUnicode(e.what()), ToUnicode("Not a Mega-Glest particle XML file, or broken"), wxOK | wxICON_ERROR).ShowModal(); + } + timer->Start(100); +} + void MainWindow::loadModel(string path) { try { if(path != "" && fileExists(path) == true) { @@ -1238,6 +1382,7 @@ void MainWindow::onTimer(wxTimerEvent &event) { anim = anim + speed; if(anim > 1.0f){ anim -= 1.f; + resetAnimation = true; } wxPaintEvent paintEvent; onPaint(paintEvent); @@ -1342,6 +1487,7 @@ void MainWindow::onMenuRestart(wxCommandEvent &event) { splashParticleSystems.clear(); // as above splashParticleSystemTypes.clear(); + loadUnit("", ""); loadModel(""); loadParticle(""); loadProjectileParticle(""); @@ -1494,6 +1640,43 @@ bool App::OnInit(){ } } + std::pair unitToLoad; + if(hasCommandArgument(argc, argv,(const char *)wxConvCurrent->cWX2MB(GAME_ARGS[GAME_ARG_LOAD_UNIT])) == true) { + const wxWX2MBbuf param = (const char *)wxConvCurrent->cWX2MB(GAME_ARGS[GAME_ARG_LOAD_UNIT]); + //printf("param = [%s]\n",(const char*)param); + + int foundParamIndIndex = -1; + hasCommandArgument(argc, argv,string((const char*)param) + string("="),&foundParamIndIndex); + if(foundParamIndIndex < 0) { + hasCommandArgument(argc, argv,(const char*)param,&foundParamIndIndex); + } + //printf("foundParamIndIndex = %d\n",foundParamIndIndex); + string customPath = (const char *)wxConvCurrent->cWX2MB(argv[foundParamIndIndex]); + vector paramPartTokens; + Tokenize(customPath,paramPartTokens,"="); + if(paramPartTokens.size() >= 2 && paramPartTokens[1].length() > 0) { + string customPathValue = paramPartTokens[1]; + std::vector delimitedList; + Tokenize(customPathValue,delimitedList,","); + + if(delimitedList.size() >= 2) { + unitToLoad.first = delimitedList[0]; + unitToLoad.second = delimitedList[1]; + } + else { + printf("\nInvalid path specified on commandline [%s] value [%s]\n\n",(const char *)wxConvCurrent->cWX2MB(argv[foundParamIndIndex]),(paramPartTokens.size() >= 2 ? paramPartTokens[1].c_str() : NULL)); + printParameterHelp(wxConvCurrent->cWX2MB(argv[0]),false); + return false; + } + + } + else { + printf("\nInvalid path specified on commandline [%s] value [%s]\n\n",(const char *)wxConvCurrent->cWX2MB(argv[foundParamIndIndex]),(paramPartTokens.size() >= 2 ? paramPartTokens[1].c_str() : NULL)); + printParameterHelp(wxConvCurrent->cWX2MB(argv[0]),false); + return false; + } + } + if(hasCommandArgument(argc, argv,(const char *)wxConvCurrent->cWX2MB(GAME_ARGS[GAME_ARG_LOAD_MODEL])) == true) { const wxWX2MBbuf param = (const char *)wxConvCurrent->cWX2MB(GAME_ARGS[GAME_ARG_LOAD_MODEL]); //printf("param = [%s]\n",(const char*)param); @@ -1721,7 +1904,8 @@ bool App::OnInit(){ } - mainWindow= new MainWindow( modelPath, + mainWindow= new MainWindow( unitToLoad, + modelPath, particlePath, projectileParticlePath, splashParticlePath, diff --git a/source/g3d_viewer/main.h b/source/g3d_viewer/main.h index c494c559..5615ff51 100644 --- a/source/g3d_viewer/main.h +++ b/source/g3d_viewer/main.h @@ -74,11 +74,16 @@ private: Model *model; + std::pair unitPathList; std::vector modelPathList; std::vector particlePathList; std::vector particleProjectilePathList; std::vector particleSplashPathList; // as above + bool resetAnimation; + float resetAnim; + int resetParticleLoopStart; + float speed; float anim; int particleLoopStart; @@ -97,6 +102,8 @@ private: string statusbarText; bool isControlKeyPressed; + + void loadUnit(string path, string skillName); void loadModel(string path); void loadParticle(string path); void loadProjectileParticle(string path); @@ -105,7 +112,8 @@ private: void saveScreenshot(); public: - MainWindow( const string modelPath,const string particlePath, + MainWindow( std::pair unitToLoad, + const string modelPath,const string particlePath, const string projectileParticlePath,const string splashParticlePath, float defaultAnimation,int defaultParticleLoopStart, float defaultZoom,float defaultXRot, float defaultYRot); diff --git a/source/g3d_viewer/renderer.cpp b/source/g3d_viewer/renderer.cpp index 8e72f802..4bc0934e 100644 --- a/source/g3d_viewer/renderer.cpp +++ b/source/g3d_viewer/renderer.cpp @@ -384,6 +384,10 @@ void Renderer::updateParticleManager() { particleManager->update(); } +bool Renderer::hasActiveParticleSystem(ParticleSystem::ParticleSystemType type) const { + return particleManager->hasActiveParticleSystem(type); +} + void Renderer::renderParticleManager() { glPushAttrib(GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT); glDepthFunc(GL_LESS); @@ -467,49 +471,6 @@ void Renderer::setAlphaColor(float alpha) { } void Renderer::saveScreen(const string &path) { - -/* - int x = 0; - int y = 0; - int w = width; - int h = height; - - // get data - std::auto_ptr imdata(new png_byte[w*h*4]); - std::auto_ptr imrow(new png_byte*[h]); - for(int i=0; igetW(), pixmapScreenShot->getH(),GL_RGBA, GL_UNSIGNED_BYTE, pixmapScreenShot->getPixels()); diff --git a/source/g3d_viewer/renderer.h b/source/g3d_viewer/renderer.h index eeddf188..8683672c 100644 --- a/source/g3d_viewer/renderer.h +++ b/source/g3d_viewer/renderer.h @@ -147,6 +147,7 @@ public: void setBackgroundColor(float red, float green, float blue); void setAlphaColor(float alpha); void saveScreen(const string &path); + bool hasActiveParticleSystem(ParticleSystem::ParticleSystemType typeName) const; }; }}//end namespace diff --git a/source/shared_lib/include/graphics/particle.h b/source/shared_lib/include/graphics/particle.h index 3711eb2a..c68d654e 100644 --- a/source/shared_lib/include/graphics/particle.h +++ b/source/shared_lib/include/graphics/particle.h @@ -84,17 +84,27 @@ class ParticleSystem { public: -enum State{ +enum State { sPause, // No updates sPlay, sFade // No new particles }; -enum BlendMode{ +enum BlendMode { bmOne, bmOneMinusAlpha }; +enum ParticleSystemType { + pst_All, + pst_FireParticleSystem, + pst_UnitParticleSystem, + pst_RainParticleSystem, + pst_SnowParticleSystem, + pst_ProjectileParticleSystem, + pst_SplashParticleSystem, +}; + protected: std::vector particles; @@ -129,6 +139,8 @@ public: ParticleSystem(int particleCount); virtual ~ParticleSystem(); + virtual ParticleSystemType getParticleSystemType() const = 0; + //public virtual void update(); virtual void render(ParticleRenderer *pr, ModelRenderer *mr); @@ -191,6 +203,8 @@ private: public: FireParticleSystem(int particleCount= 2000); + virtual ParticleSystemType getParticleSystemType() const { return pst_FireParticleSystem;} + //virtual virtual void initParticle(Particle *p, int particleIndex); virtual void updateParticle(Particle *p); @@ -233,6 +247,8 @@ public: public: UnitParticleSystem(int particleCount= 2000); + virtual ParticleSystemType getParticleSystemType() const { return pst_UnitParticleSystem;} + //virtual virtual void initParticle(Particle *p, int particleIndex); virtual void updateParticle(Particle *p); @@ -270,6 +286,8 @@ private: public: RainParticleSystem(int particleCount= 4000); + virtual ParticleSystemType getParticleSystemType() const { return pst_RainParticleSystem;} + virtual void render(ParticleRenderer *pr, ModelRenderer *mr); virtual void initParticle(Particle *p, int particleIndex); @@ -291,6 +309,8 @@ private: public: SnowParticleSystem(int particleCount= 4000); + virtual ParticleSystemType getParticleSystemType() const { return pst_SnowParticleSystem;} + virtual void initParticle(Particle *p, int particleIndex); virtual bool deathTest(Particle *p); @@ -324,6 +344,8 @@ protected: public: AttackParticleSystem(int particleCount); + virtual ParticleSystemType getParticleSystemType() const { return pst_ProjectileParticleSystem;} + virtual void render(ParticleRenderer *pr, ModelRenderer *mr); Model *getModel() const {return model;} @@ -375,6 +397,8 @@ public: ProjectileParticleSystem(int particleCount= 1000); virtual ~ProjectileParticleSystem(); + virtual ParticleSystemType getParticleSystemType() const { return pst_SplashParticleSystem;} + void link(SplashParticleSystem *particleSystem); virtual void update(); @@ -442,6 +466,7 @@ public: void cleanupUnitParticleSystems(vector &particleSystems); int findParticleSystems(ParticleSystem *psFind, const vector &particleSystems) const; bool validateParticleSystemStillExists(ParticleSystem * particleSystem) const; + bool hasActiveParticleSystem(ParticleSystem::ParticleSystemType type) const; }; }}//end namespace diff --git a/source/shared_lib/sources/graphics/particle.cpp b/source/shared_lib/sources/graphics/particle.cpp index 549e36c8..b05f8076 100644 --- a/source/shared_lib/sources/graphics/particle.cpp +++ b/source/shared_lib/sources/graphics/particle.cpp @@ -941,6 +941,38 @@ void ParticleManager::render(ParticleRenderer *pr, ModelRenderer *mr) const{ } } +bool ParticleManager::hasActiveParticleSystem(ParticleSystem::ParticleSystemType type) const { + bool result = false; + + size_t particleSystemCount = particleSystems.size(); + int currentParticleCount = 0; + + vector cleanupParticleSystemsList; + for (unsigned int i = 0; i < particleSystems.size(); i++) { + ParticleSystem *ps = particleSystems[i]; + if(ps != NULL) { + currentParticleCount += ps->getAliveParticleCount(); + + bool showParticle = true; + if( dynamic_cast(ps) != NULL || + dynamic_cast(ps) != NULL ) { + showParticle = ps->getVisible() || (ps->getState() == ParticleSystem::sFade); + } + if(showParticle == true) { + //printf("Looking for [%d] current id [%d] i = %d\n",type,ps->getParticleSystemType(),i); + + if(type == ParticleSystem::pst_All || type == ps->getParticleSystemType()) { + //printf("FOUND particle system type match for [%d] current id [%d] i = %d\n",type,ps->getParticleSystemType(),i); + result = true; + break; + } + } + } + } + + return result; +} + void ParticleManager::update(int renderFps) { Chrono chrono; chrono.start();