// TnzFarm includes #include "tfarmcontroller.h" // TnzLib includes #include "toonz/txshleveltypes.h" #include "toonz/tpalettehandle.h" #include "toonz/tscenehandle.h" #include "toonz/txshlevelhandle.h" #include "toonz/sceneproperties.h" #include "toonz/levelproperties.h" #include "toonz/levelupdater.h" #include "toonz/preferences.h" #include "toonz/toonzfolders.h" #include "toonz/toonzscene.h" #include "toonz/txshchildlevel.h" #include "toonz/tproject.h" #include "toonz/tcleanupper.h" #include "toonz/txsheet.h" #include "toonz/txshcell.h" #include "toonz/txshcolumn.h" #include "toonz/tlog.h" #include "toonz/imagestyles.h" // TnzBase includes #include "tcli.h" #include "tenv.h" // TnzCore includes #include "tsystem.h" #include "tstream.h" #include "tstopwatch.h" #include "tthread.h" #include "tthreadmessage.h" #include "timagecache.h" #include "tiio_std.h" #include "tnzimage.h" #include "tmsgcore.h" #include "tpluginmanager.h" #include "tpalette.h" #include "tsimplecolorstyles.h" // Qt includes #include using namespace TCli; using namespace std; //------------------------------------------------------------------------ inline ostream &operator<<(ostream &out, const wstring &w) { return out << ::to_string(w); } //------------------------------------------------------------------------ inline ostream &operator<<(ostream &out, const TFilePath &fp) { return out << fp.getWideString(); } //------------------------------------------------------------------------ namespace { const char *rootVarName = "TOONZROOT"; const char *systemVarPrefix = "TOONZ"; namespace { CleanupParameters GlobalParameters; TFilePath CurrentSettingsFile = TFilePath(); //----------------------------------------------------------------------------- void loadSettings(const TFilePath &settingsFile, CleanupParameters *cp) { if (CurrentSettingsFile == TFilePath()) // the parameters were global ...I store them GlobalParameters.assign(cp); CurrentSettingsFile = settingsFile; TIStream *is = new TIStream(settingsFile); int minor, major; string tagName; // Extract file version if any is->matchTag(tagName); if (tagName == "version") { *is >> major >> minor; is->matchEndTag(); is->setVersion(VersionNumber(major, minor)); } else { delete is; is = new TIStream(settingsFile); } cp->loadData(*is, true); delete is; } //----------------------------------------------------------------------------- void restoreGlobalSettings(CleanupParameters *cp) { if (CurrentSettingsFile == TFilePath()) return; // already global! cp->assign(&GlobalParameters); CurrentSettingsFile = TFilePath(); } } // namespace //======================================================================== // // fatalError // //------------------------------------------------------------------------ void fatalError(string msg) { #ifdef _WIN32 msg = "Application can't start:\n" + msg; DVGui::error(QString::fromStdString(msg)); // MessageBox(0,msg.c_str(),"Fatal error",MB_ICONERROR); exit(1); #else // TODO: Come si fa ad aggiungere un messaggio di errore qui? std::cout << msg << std::endl; abort(); #endif } } // namespace #ifdef MACOSX inline bool isBlank(char c) { return c == ' ' || c == '\t' || c == '\n'; } //======================================================================== // setToonzFolder //------------------------------------------------------------------------ // Ritorna il path della variabile passata come secondo argomento // entrambe vengono lette da un file di testo (filename). TFilePath setToonzFolder(const TFilePath &filename, std::string toonzVar) { Tifstream is(filename); if (!is) return TFilePath(); char buffer[1024]; while (is.getline(buffer, sizeof(buffer))) { // le righe dentro toonzenv.txt sono del tipo // export set TOONZPROJECT="....." // devo trovare la linea che contiene toonzVar char *s = buffer; while (isBlank(*s)) s++; // Se la riga  vuota, o inizia per # o ! salto alla prossima if (*s == '\0' || *s == '#' || *s == '!') continue; if (*s == '=') continue; // errore: nome variabile non c' char *t = s; // Mi prendo la sottoStringa fino all'= while (*t && *t != '=') t++; if (*t != '=') continue; // errore: manca '=' char *q = t; // Torno indietro fino al primo blank while (q > s && !isBlank(*(q - 1))) q--; if (q == s) continue; // non dovrebbe mai succedere: prima di '=' tutti blanks string toonzVarString(q, t); // Confronto la stringa trovata con toonzVar, se  lei vado avanti. if (toonzVar != toonzVarString) continue; // errore: stringhe diverse s = t + 1; // Salto gli spazi while (isBlank(*s)) s++; if (*s == '\0') continue; // errore: dst vuoto t = s; while (*t) t++; while (t > s && isBlank(*(t - 1))) t--; if (t == s) continue; // ATTENZIONE : tolgo le virgolette !! string pathName(s + 1, t - s - 2); return TFilePath(pathName); } return TFilePath(); } #endif //============================================================================================== static void prepareToCleanup(TXshSimpleLevel *xl, TPalette *cleanupPalette) { assert(xl->getScene()); if (xl->getProperties()->getSubsampling() != 1) { xl->getProperties()->setSubsampling(1); xl->invalidateFrames(); } /* int ltype = xl->getType(); if(ltype != TZP_XSHLEVEL) xl->makeTlv(xl->getScene()->getDefaultParentDir(TZP_XSHLEVEL)); if(xl->getPalette()==0) { //PaletteController* pc = TApp::instance()->getPaletteController(); xl->setPalette(cleanupPalette); //if(xl == TApp::instance()->getCurrentLevel()->getLevel()) // pc->getCurrentLevelPalette()->setPalette(xl->getPalette()); }*/ } //============================================================================================== namespace { TStopWatch Sw1; TStopWatch Sw2; bool UseRenderFarm = false; string FarmControllerName; int FarmControllerPort; TFarmController *FarmController = 0; string TaskId; } // namespace //======================================================================== // // searchLevelsToCleanup // // Restituisce l'elenco (ordinato per ordine alfabetico di nome) // dei livelli TLV(con scannedPath)/TZI/OVL presenti nell'xsheet (o nei // sottoxsheet) // // se selectedOnly = true salta i livelli presenti nelle colonne senza // "occhietto" // //------------------------------------------------------------------------ static void searchLevelsToCleanup( std::vector>> &levels, TXsheet *xsh, bool selectedOnly) { std::map levelTable; std::map> framesTable; std::set visited; std::vector xsheets; xsheets.push_back(xsh); visited.insert(xsh); while (!xsheets.empty()) { TXsheet *xsh = xsheets.back(); xsheets.pop_back(); for (int c = 0; c < xsh->getColumnCount(); c++) { TXshColumn *column = xsh->getColumn(c); if (!column || column->isEmpty()) continue; // if(selectedOnly && !column->isPreviewVisible()) continue; int r0 = 0, r1 = -1; xsh->getCellRange(c, r0, r1); for (int r = r0; r <= r1; r++) { TXshCell cell = xsh->getCell(r, c); if (cell.isEmpty()) continue; if (TXshSimpleLevel *sl = cell.m_level->getSimpleLevel()) { if (selectedOnly && !column->isPreviewVisible()) // pezza: se questo // "if" veniva fatto // sopra(riga // commentata) // quando si fa save della Scene alla fine della cleanuppata, // venivano backuppate le tif non processate e cancellati gli // originali! // Deliri del levelUPdater; evito di mettere le mani in quel pattume. // vinz { sl->setDirtyFlag(false); continue; } int ltype = sl->getType(); if ((ltype == TZP_XSHLEVEL && sl->getScannedPath() != TFilePath()) || ltype == OVL_XSHLEVEL || ltype == TZI_XSHLEVEL) { wstring levelName = sl->getName(); levelTable[levelName] = sl; framesTable[levelName].insert(cell.m_frameId); } } else if (TXshChildLevel *cl = cell.m_level->getChildLevel()) { TXsheet *subXsh = cl->getXsheet(); if (visited.count(subXsh) == 0) { visited.insert(subXsh); xsheets.push_back(subXsh); } } } } } assert(levelTable.size() == framesTable.size()); for (auto const &level : levelTable) { auto const it = framesTable.find(level.first); if (it == framesTable.end()) { continue; } levels.push_back(std::make_pair(level.second, (*it).second)); } } //------------------------------------------------------------------------------ /*- CleanupDefaultパレットを追加する -*/ static void addCleanupDefaultPalette(TXshSimpleLevel *sl) { /*- 元となるパレットはStudioPaletteフォルダに置く -*/ TFilePath palettePath = ToonzFolder::getStudioPaletteFolder() + "cleanup_default.tpl"; TFileStatus pfs(palettePath); if (!pfs.doesExist() || !pfs.isReadable()) { wcout << L"CleanupDefaultPalette file: " << palettePath.getWideString() << L" is not found!" << endl; return; } TIStream is(palettePath); if (!is) { cout << "CleanupDefaultPalette file: failed to get TIStream" << endl; return; } string tagName; if (!is.matchTag(tagName) || tagName != "palette") { cout << "CleanupDefaultPalette file: This is not palette file" << endl; return; } string gname; is.getTagParam("name", gname); TPalette *defaultPalette = new TPalette(); defaultPalette->loadData(is); sl->getPalette()->setIsCleanupPalette(false); TPalette::Page *dstPage = sl->getPalette()->getPage(0); TPalette::Page *srcPage = defaultPalette->getPage(0); for (int srcIndexInPage = 0; srcIndexInPage < srcPage->getStyleCount(); srcIndexInPage++) { int id = srcPage->getStyleId(srcIndexInPage); bool isUsedInCleanupPalette; isUsedInCleanupPalette = false; for (int dstIndexInPage = 0; dstIndexInPage < dstPage->getStyleCount(); dstIndexInPage++) { if (dstPage->getStyleId(dstIndexInPage) == id) { isUsedInCleanupPalette = true; break; } } if (isUsedInCleanupPalette) continue; else { int addedId = sl->getPalette()->addStyle( srcPage->getStyle(srcIndexInPage)->clone()); dstPage->addStyle(addedId); /*- StudioPalette由来のDefaultPaletteの場合、GrobalNameを消去する -*/ sl->getPalette()->getStyle(addedId)->setGlobalName(L""); sl->getPalette()->getStyle(addedId)->setOriginalName(L""); } } delete defaultPalette; } //======================================================================== // // cleanupLevel // // effettua il cleanup del livello. Se il livello e' un fullcolor // modifica tipo e parametri e crea la palette // // se overwrite == false non fa il cleanup dei frames gia' cleanuppati // //------------------------------------------------------------------------ static void cleanupLevel(TXshSimpleLevel *xl, std::set fidsInXsheet, ToonzScene *scene, bool overwrite, TUserLogAppend &m_userLog) { prepareToCleanup(xl, scene->getProperties() ->getCleanupParameters() ->m_cleanupPalette.getPointer()); TCleanupper *cl = TCleanupper::instance(); TFilePath fp = scene->decodeFilePath(xl->getPath()); TSystem::touchParentDir(fp); cout << "cleanupping " << xl->getName() << " path=" << fp << endl; string info = "cleanupping " + ::to_string(xl->getPath()); LevelUpdater updater(xl); m_userLog.info(info); DVGui::info(QString::fromStdString(info)); bool firstImage = true; for (auto const &fid : fidsInXsheet) { cout << " " << fid << endl; info = " " + fid.expand(); m_userLog.info(info); int status = xl->getFrameStatus(fid); if (0 != (status & TXshSimpleLevel::Cleanupped) && !overwrite) { cout << " skipped" << endl; m_userLog.info(" skipped"); DVGui::info(QString("--skipped frame ") + QString::fromStdString(fid.expand())); continue; } TRasterImageP original = xl->getFrameToCleanup(fid); if (!original) { string err = " *error* missed frame"; m_userLog.error(err); cout << err << endl; continue; } CleanupParameters *params = scene->getProperties()->getCleanupParameters(); if (params->m_lineProcessingMode == lpNone) { TRasterImageP ri; if (params->m_autocenterType == CleanupTypes::AUTOCENTER_NONE) ri = original; else { bool autocentered; ri = cl->autocenterOnly(original, false, autocentered); if (!autocentered) { m_userLog.error("The autocentering failed on the current drawing."); cout << "The autocentering failed on the current drawing." << endl; } } updater.update(fid, ri); continue; } // Obtain the source dpi. Changed it to be done once at the first frame of // each level in order to avoid the following problem: // If the original raster level has no dpi (such as TGA images), obtaining // dpi in every frame causes dpi mismatch between the first frame and the // following frames, since the value // TXshSimpleLevel::m_properties->getDpi() will be changed to the // dpi of cleanup camera (= TLV's dpi) after finishing the first frame. if (firstImage) { TPointD dpi; original->getDpi(dpi.x, dpi.y); if (dpi.x == 0 && dpi.y == 0) dpi = xl->getProperties()->getDpi(); cl->setSourceDpi(dpi); } CleanupPreprocessedImage *cpi; { TRasterImageP resampledImage; cpi = cl->process(original, firstImage, resampledImage); } TToonzImageP timage = cl->finalize(cpi, true); TPointD dpi(0, 0); timage->getDpi(dpi.x, dpi.y); if (dpi.x != 0 && dpi.y != 0) xl->getProperties()->setDpi(dpi); if (firstImage) addCleanupDefaultPalette(xl); firstImage = false; timage->setPalette(xl->getPalette()); xl->setFrameStatus(fid, status | TXshSimpleLevel::Cleanupped); xl->setFrame(fid, timage); updater.update(fid, timage); /*- 1フレーム終わったら、そのフレームのキャッシュは消す -*/ xl->invalidateFrame(fid); delete cpi; } } //======================================================================== // // main // // usage: tcleanup filename.tnz [-selected][-overwrite] // //------------------------------------------------------------------------ int main(int argc, char *argv[]) { QApplication app(argc, argv); // questo definisce la registry root e inizializza TEnv TEnv::setRootVarName(rootVarName); TEnv::setSystemVarPrefix(systemVarPrefix); TEnv::setApplicationFileName(argv[0]); QCoreApplication::setOrganizationName("Tahoma2D"); QCoreApplication::setOrganizationDomain(""); QCoreApplication::setApplicationName( QString::fromStdString(TEnv::getApplicationName())); TSystem::hasMainLoop(false); int i; for (i = 0; i < argc; i++) // tmsg must be set as soon as it's possible { QString str = argv[i]; if (str == "-tmsg") { TMsgCore::instance()->connectTo(argv[i + 1]); break; } } if (i == argc) TMsgCore::instance()->connectTo(""); TFilePath fproot = TEnv::getStuffDir(); if (fproot == TFilePath()) fatalError(string("Undefined: \"") + ::to_string(TEnv::getRootVarPath()) + "\""); if (!TFileStatus(fproot).isDirectory()) fatalError(string("Directory \"") + ::to_string(fproot) + "\" not found or not readable"); TFilePath lRootDir = TEnv::getStuffDir() + "toonzfarm"; TFilePath logFilePath = lRootDir + "tcleanup.log"; TUserLogAppend m_userLog(logFilePath); // TFilePathSet fps = ToonzFolder::getProjectsFolders(); // TFilePathSet::iterator fpIt; // for (fpIt = fps.begin(); fpIt != fps.end(); ++fpIt) // TProjectManager::instance()->addProjectsRoot(*fpIt); TFilePath libraryFolder = ToonzFolder::getLibraryFolder(); TRasterImagePatternStrokeStyle::setRootDir(libraryFolder); TVectorImagePatternStrokeStyle::setRootDir(libraryFolder); TPalette::setRootDir(libraryFolder); TImageStyle::setLibraryDir(libraryFolder); TFilePath cacheRoot = ToonzFolder::getCacheRootFolder(); if (cacheRoot.isEmpty()) cacheRoot = TEnv::getStuffDir() + "cache"; TImageCache::instance()->setRootDir(cacheRoot); FilePathArgument srcName("tnzFile", "Scene file"); SimpleQualifier selectedOnlyOption("-onlyvisible", "Selected column only"); SimpleQualifier overwriteAllOption("-overwriteAll", "Overwrite all already cleanupped frames"); SimpleQualifier overwriteNoPaintOption( "-overwriteNoPaint", "Overwrite only no-paint levels of already cleanupped frames"); StringQualifier farmData("-farm data", "TFarm Controller"); StringQualifier idq("-id n", "id"); StringQualifier tmsg("-tmsg n", "Internal use only"); Usage usage(argv[0]); usage.add(srcName + selectedOnlyOption + overwriteAllOption + overwriteNoPaintOption + farmData + idq + tmsg); if (!usage.parse(argc, argv)) exit(1); TaskId = idq.getValue(); string fdata = farmData.getValue(); if (fdata.empty()) UseRenderFarm = false; else { UseRenderFarm = true; string::size_type pos = fdata.find('@'); if (pos == string::npos) UseRenderFarm = false; else { FarmControllerPort = std::stoi(fdata.substr(0, pos)); FarmControllerName = fdata.substr(pos + 1); } } if (UseRenderFarm) { TFarmControllerFactory factory; factory.create(QString::fromStdString(FarmControllerName), FarmControllerPort, &FarmController); } /*- 画像Read/Writeの関数を登録 -*/ initImageIo(); Tiio::defineStd(); /*- プロジェクトのロード -*/ TProjectManager *pm = TProjectManager::instance(); TProjectP project = pm->loadSceneProject(srcName); if (!project) { string err = "Couldn't find the project" + project->getName().getName(); m_userLog.error(err); cerr << err << endl; return -2; } cout << "project:" << project->getName() << endl; TFilePath fp = srcName; /*- CLNファイルを直接指定した場合 -*/ bool sourceFileIsCleanupSetting = (fp.getType() == "cln"); bool selectedOnly = selectedOnlyOption; ToonzScene *scene = new ToonzScene(); TImageStyle::setCurrentScene(scene); /*- シーンファイルパスを入力した場合 -*/ if (!sourceFileIsCleanupSetting) { try { scene->loadNoResources(fp); } catch (...) { string err = "can't read " + fp.getName(); m_userLog.error(err); cerr << "can't read " << fp << endl; TImageCache::instance()->clear(true); return -3; } } /*-- CleanupSettingsファイルパスを直接入力した場合 --*/ else { try { TProjectManager *pm = TProjectManager::instance(); TProjectP sceneProject = pm->loadSceneProject(fp); if (!sceneProject) { cerr << "can't open project." << endl; return -3; } scene->setProject(sceneProject.getPointer()); /*- CleanupSettingsファイルに対応するTIFファイルが有るかチェック -*/ TFilePath tifImagePath = fp.withType("tif"); std::wcout << L"tifImagePath : " << tifImagePath.getWideString() << std::endl; /*- * 無ければ、連番画像がソースである可能性がある。tifImagePathを連番に差し替える * -*/ if (!TFileStatus(tifImagePath).doesExist()) { tifImagePath = tifImagePath.getParentDir() + (tifImagePath.getName() + "..tif"); std::wcout << "change the source path to : " << tifImagePath.getWideString() << std::endl; } else std::cout << "tif single image found" << std::endl; /*- シーンファイルに対象のTIFファイルをロード -*/ TXshLevel *xl = scene->loadLevel(tifImagePath); if (!xl) { std::cout << "failed to load level" << std::endl; throw TException("Failed to load level."); } std::vector dummy; int frameLength = scene->getXsheet()->exposeLevel(0, 0, xl, dummy); std::cout << "expose done. frameLength : " << frameLength << std::endl; } catch (...) { cerr << "can't read Cleanup Settings file " << fp << endl; TImageCache::instance()->clear(true); return -3; } } // Levels contiene i livelli e i rispettivi frames prsenti nell'xsheet. std::vector>> levels; /*- XsheetからCleanupするLevelのリストを得る -*/ searchLevelsToCleanup(levels, scene->getXsheet(), selectedOnly); TSceneProperties *sprop = scene->getProperties(); CleanupParameters *params = scene->getProperties()->getCleanupParameters(); for (int i = 0; i < (int)levels.size(); i++) { bool overwrite = overwriteAllOption; TXshSimpleLevel *xl = levels[i].first->getSimpleLevel(); if (!xl) continue; /*- CLNファイルパスを取得 -*/ TFilePath settingsFile = xl->getScannedPath().isEmpty() ? xl->getPath() : xl->getScannedPath(); settingsFile = scene->decodeFilePath(settingsFile).withNoFrame().withType("cln"); /*- CLNファイルがあればそれを用いる。無ければGlobal設定を読み込む -*/ // TFilePath settingsFile = // scene->decodeFilePath(xl->getPath()).withNoFrame().withType("cln"); if (TFileStatus(settingsFile).doesExist()) loadSettings(settingsFile, params); else restoreGlobalSettings(params); TCleanupper::instance()->setParameters(params); bool lineProcessing = (params->m_lineProcessingMode != lpNone); TFilePath tmp = params->getPath(scene); int ltype = xl->getType(); assert(ltype == TZP_XSHLEVEL || ltype == TZI_XSHLEVEL || ltype == OVL_XSHLEVEL); // target path TFilePath targetPath = xl->getPath(); if (ltype != TZP_XSHLEVEL) { if (lineProcessing) targetPath = targetPath .withParentDir(params->getPath( scene)) // scene->getDefaultParentDir(TZP_XSHLEVEL)) .withNoFrame() .withType("tlv"); else targetPath = targetPath.withParentDir(params->getPath( scene)); // scene->getDefaultParentDir(TZP_XSHLEVEL)); } else { targetPath = targetPath.withParentDir(params->getPath( scene)); // scene->getDefaultParentDir(TZP_XSHLEVEL)); } /*- NoPaintを作る設定のとき、NoPaintの方だけにOverwriteするようにする -*/ bool isReCleanup; isReCleanup = false; /*- 再Cleanupのときにパスを元に戻すために用いる -*/ TFilePath originalLevelPath = TFilePath(); TFilePath actualTargetPath = scene->decodeFilePath(targetPath); /*- すでにLevelがある場合 -*/ if (TSystem::doesExistFileOrLevel(actualTargetPath) && Preferences::instance()->isSaveUnpaintedInCleanupEnable() && overwriteNoPaintOption) { overwrite = true; originalLevelPath = scene->codeFilePath(targetPath); /*- パスを書き換え、再Cleanupのフラグを立てる -*/ isReCleanup = true; /*- nopaintフォルダの作成 -*/ TFilePath nopaintDir = targetPath.getParentDir() + "nopaint"; if (!TFileStatus(nopaintDir).doesExist()) { try { TSystem::mkDir(nopaintDir); } catch (...) { return 0; } } /*- 保存先のパスをnopaintの方にする -*/ targetPath = targetPath.getParentDir() + "nopaint\\" + TFilePath(targetPath.getName() + "_np." + targetPath.getType()); } std::wcout << L"targetPath = " << targetPath.getWideString() << std::endl; if (lineProcessing) { if (ltype != TZP_XSHLEVEL) { xl->makeTlv(targetPath); } else if (targetPath != xl->getPath()) { xl->setPath(targetPath, false); } xl->setPalette( TCleanupper::instance()->createToonzPaletteFromCleanupPalette()); } else if (!params->getPath(scene).isEmpty()) { xl->setScannedPath(xl->getPath()); xl->setPath(scene->codeFilePath(targetPath), false); } std::set fidsInXsheet = levels[i].second; assert(fidsInXsheet.size() > 0); xl->load(); cleanupLevel(xl, fidsInXsheet, scene, overwrite, m_userLog); /*- Cleanup完了後、Nopaintをnopaintフォルダに保存する -*/ if (Preferences::instance()->isSaveUnpaintedInCleanupEnable() && !isReCleanup) /*-- 再Cleanupのときはnopaintを作らない --*/ { /*- nopaintフォルダの作成 -*/ TFilePath nopaintDir = actualTargetPath.getParentDir() + "nopaint"; if (!TFileStatus(nopaintDir).doesExist()) { try { TSystem::mkDir(nopaintDir); } catch (...) { string err = "Can't make directory " + nopaintDir.getName(); m_userLog.error(err); cerr << "Can't make directory" << endl; } } // Se sono nell'ultimo frame del livello salvo il livello cleanuppato // in un file chiamato nome-unpainted (file di backup del cleanup). /*- 保存先 -*/ TFilePath unpaintedLevelPath = actualTargetPath.getParentDir() + "nopaint\\" + TFilePath(targetPath.getName() + "_np." + targetPath.getType()); if (TFileStatus(actualTargetPath).doesExist() && (!TFileStatus(unpaintedLevelPath).doesExist() || overwriteAllOption) /*- 全て上書きなら既存のNoPaintに上書きする -*/ && xl) { /*- GUI上でCleanupするときと同様に、Cleanup結果をコピーして作る -*/ TSystem::copyFile(unpaintedLevelPath, actualTargetPath); /*- パレットのコピー -*/ TFilePath levelPalettePath = actualTargetPath.getParentDir() + TFilePath(actualTargetPath.getName() + ".tpl"); TFilePath unpaintedLevelPalettePath = levelPalettePath.getParentDir() + "nopaint\\" + TFilePath(levelPalettePath.getName() + "_np." + levelPalettePath.getType()); TSystem::copyFile(unpaintedLevelPalettePath, levelPalettePath); } } /*-- 再Cleanupの場合はXsheet上のパスをオリジナルのもの(NoPaintでないもの)に戻す --*/ else if (isReCleanup) { xl->setPath(originalLevelPath); } } /*- CleanupParamをGrobalに戻す -*/ restoreGlobalSettings(params); /*- CleanupSettingsからCleanupを行った場合はシーンの保存は行わない -*/ if (sourceFileIsCleanupSetting) { std::cout << "Cleanup from Setting file completed" << std::endl; return 0; } wstring wInfo = L"updating scene " + scene->getSceneName(); QString qInfo_ = QString::fromStdWString(wInfo); string info = qInfo_.toStdString(); m_userLog.info(info); cout << "updating scene " << scene->getSceneName() << endl; /*- シーンを上書き保存 -*/ try { scene->save(fp); TImageCache::instance()->clear(true); } catch (...) { wstring wErr = L"Can't save scene " + fp.getWideName(); QString qErr = QString::fromStdWString(wErr); string err = qErr.toStdString(); m_userLog.error(err); cerr << "Can't save scene" << endl; TImageCache::instance()->clear(true); } DVGui::info("Cleanup Done."); return 0; } //------------------------------------------------------------------------