1 /*! 2 @file 3 @author Albert Semenov 4 @date 08/2010 5 */ 6 7 #include "Precompiled.h" 8 #include "EditorState.h" 9 #include "Application.h" 10 #include "FileSystemInfo/FileSystemInfo.h" 11 #include "Localise.h" 12 #include "CommandManager.h" 13 #include "ActionManager.h" 14 #include "MessageBoxManager.h" 15 #include "DialogManager.h" 16 #include "StateManager.h" 17 #include "RecentFilesManager.h" 18 #include "ExportManager.h" 19 #include "DataManager.h" 20 #include "DataSelectorManager.h" 21 #include "FactoryManager.h" 22 #include "SettingsManager.h" 23 24 namespace tools 25 { 26 FACTORY_ITEM_ATTRIBUTE(EditorState)27 FACTORY_ITEM_ATTRIBUTE(EditorState) 28 29 EditorState::EditorState() : 30 mMainPane(nullptr), 31 mOpenSaveFileDialog(nullptr), 32 mSettingsWindow(nullptr) 33 { 34 CommandManager::getInstance().getEvent("Command_FileDrop")->connect(this, &EditorState::commandFileDrop); 35 CommandManager::getInstance().getEvent("Command_FileLoad")->connect(this, &EditorState::commandLoad); 36 CommandManager::getInstance().getEvent("Command_FileSave")->connect(this, &EditorState::commandSave); 37 CommandManager::getInstance().getEvent("Command_FileSaveAs")->connect(this, &EditorState::commandSaveAs); 38 CommandManager::getInstance().getEvent("Command_ClearAll")->connect(this, &EditorState::commandClear); 39 CommandManager::getInstance().getEvent("Command_Settings")->connect(this, &EditorState::commandSettings); 40 CommandManager::getInstance().getEvent("Command_RecentFiles")->connect(this, &EditorState::commandRecentFiles); 41 CommandManager::getInstance().getEvent("Command_Quit")->connect(this, &EditorState::commandQuit); 42 CommandManager::getInstance().getEvent("Command_Undo")->connect(this, &EditorState::commandUndo); 43 CommandManager::getInstance().getEvent("Command_Redo")->connect(this, &EditorState::commandRedo); 44 45 if (!SettingsManager::getInstance().tryGetValue("EditorState/DefaultFileName", mDefaultFileName)) 46 mDefaultFileName = "unnamed.xml"; 47 mFileName = mDefaultFileName; 48 } 49 initState()50 void EditorState::initState() 51 { 52 addUserTag("\\n", "\n"); 53 addUserTag("CurrentFileName", mFileName); 54 55 mMainPane = new Control(); 56 mMainPane->Initialise(SettingsManager::getInstance().getValue("EditorState/MainPaneLayout")); 57 58 mSettingsWindow = new SettingsWindow(); 59 mSettingsWindow->Initialise(SettingsManager::getInstance().getValue("EditorState/SettingsWindowLayout")); 60 mSettingsWindow->eventEndDialog.connect(this, &EditorState::notifySettingsWindowEndDialog); 61 62 mOpenSaveFileDialog = new OpenSaveFileDialog(); 63 mOpenSaveFileDialog->Initialise(SettingsManager::getInstance().getValue("EditorState/OpenSaveFileDialogLayout")); 64 mOpenSaveFileDialog->eventEndDialog.connect(this, &EditorState::notifyEndDialog); 65 mOpenSaveFileDialog->setCurrentFolder(RecentFilesManager::getInstance().getRecentFolder()); 66 mOpenSaveFileDialog->setRecentFolders(RecentFilesManager::getInstance().getRecentFolders()); 67 68 std::string fileMask; 69 if (!SettingsManager::getInstance().tryGetValue("EditorState/DefaultFileMask", fileMask)) 70 fileMask = "*.xml"; 71 mOpenSaveFileDialog->setFileMask(fileMask); 72 73 ActionManager::getInstance().eventChanges.connect(this, &EditorState::notifyChanges); 74 75 updateCaption(); 76 77 if (!Application::getInstance().getParams().empty()) 78 { 79 mFileName = Application::getInstance().getParams().front(); 80 addUserTag("CurrentFileName", mFileName); 81 82 load(); 83 updateCaption(); 84 } 85 } 86 cleanupState()87 void EditorState::cleanupState() 88 { 89 ActionManager::getInstance().eventChanges.disconnect(this); 90 91 mOpenSaveFileDialog->eventEndDialog.disconnect(this); 92 delete mOpenSaveFileDialog; 93 mOpenSaveFileDialog = nullptr; 94 95 delete mSettingsWindow; 96 mSettingsWindow = nullptr; 97 98 delete mMainPane; 99 mMainPane = nullptr; 100 } 101 pauseState()102 void EditorState::pauseState() 103 { 104 mMainPane->getRoot()->setVisible(false); 105 } 106 resumeState()107 void EditorState::resumeState() 108 { 109 mMainPane->getRoot()->setVisible(true); 110 } 111 updateCaption()112 void EditorState::updateCaption() 113 { 114 addUserTag("HasChanged", ActionManager::getInstance().getChanges() ? "*" : ""); 115 116 CommandManager::getInstance().executeCommand("Command_UpdateAppCaption"); 117 } 118 commandLoad(const MyGUI::UString & _commandName,bool & _result)119 void EditorState::commandLoad(const MyGUI::UString& _commandName, bool& _result) 120 { 121 if (!checkCommand()) 122 return; 123 124 if (ActionManager::getInstance().getChanges()) 125 { 126 MyGUI::Message* message = MessageBoxManager::getInstance().create( 127 replaceTags("Warning"), 128 replaceTags("MessageUnsavedData"), 129 MyGUI::MessageBoxStyle::IconQuest 130 | MyGUI::MessageBoxStyle::Yes 131 | MyGUI::MessageBoxStyle::No 132 | MyGUI::MessageBoxStyle::Cancel); 133 message->eventMessageBoxResult += MyGUI::newDelegate(this, &EditorState::notifyMessageBoxResultLoad); 134 } 135 else 136 { 137 showLoadWindow(); 138 } 139 140 _result = true; 141 } 142 commandSave(const MyGUI::UString & _commandName,bool & _result)143 void EditorState::commandSave(const MyGUI::UString& _commandName, bool& _result) 144 { 145 if (!checkCommand()) 146 return; 147 148 if (ActionManager::getInstance().getChanges()) 149 { 150 if (mFileName == mDefaultFileName) 151 showSaveAsWindow(); 152 else 153 save(); 154 } 155 156 _result = true; 157 } 158 commandSaveAs(const MyGUI::UString & _commandName,bool & _result)159 void EditorState::commandSaveAs(const MyGUI::UString& _commandName, bool& _result) 160 { 161 if (!checkCommand()) 162 return; 163 164 showSaveAsWindow(); 165 166 _result = true; 167 } 168 commandClear(const MyGUI::UString & _commandName,bool & _result)169 void EditorState::commandClear(const MyGUI::UString& _commandName, bool& _result) 170 { 171 if (!checkCommand()) 172 return; 173 174 if (ActionManager::getInstance().getChanges()) 175 { 176 MyGUI::Message* message = MessageBoxManager::getInstance().create( 177 replaceTags("Warning"), 178 replaceTags("MessageUnsavedData"), 179 MyGUI::MessageBoxStyle::IconQuest 180 | MyGUI::MessageBoxStyle::Yes 181 | MyGUI::MessageBoxStyle::No 182 | MyGUI::MessageBoxStyle::Cancel); 183 message->eventMessageBoxResult += MyGUI::newDelegate(this, &EditorState::notifyMessageBoxResultClear); 184 } 185 else 186 { 187 clear(); 188 } 189 190 _result = true; 191 } 192 commandQuit(const MyGUI::UString & _commandName,bool & _result)193 void EditorState::commandQuit(const MyGUI::UString& _commandName, bool& _result) 194 { 195 if (!checkCommand()) 196 return; 197 198 if (ActionManager::getInstance().getChanges()) 199 { 200 MyGUI::Message* message = MessageBoxManager::getInstance().create( 201 replaceTags("Warning"), 202 replaceTags("MessageUnsavedData"), 203 MyGUI::MessageBoxStyle::IconQuest 204 | MyGUI::MessageBoxStyle::Yes 205 | MyGUI::MessageBoxStyle::No 206 | MyGUI::MessageBoxStyle::Cancel); 207 message->eventMessageBoxResult += MyGUI::newDelegate(this, &EditorState::notifyMessageBoxResultQuit); 208 } 209 else 210 { 211 StateManager::getInstance().stateEvent(this, "Exit"); 212 } 213 214 _result = true; 215 } 216 commandFileDrop(const MyGUI::UString & _commandName,bool & _result)217 void EditorState::commandFileDrop(const MyGUI::UString& _commandName, bool& _result) 218 { 219 if (!checkCommand()) 220 return; 221 222 mDropFileName = CommandManager::getInstance().getCommandData(); 223 if (mDropFileName.empty()) 224 return; 225 226 if (ActionManager::getInstance().getChanges()) 227 { 228 MyGUI::Message* message = MessageBoxManager::getInstance().create( 229 replaceTags("Warning"), 230 replaceTags("MessageUnsavedData"), 231 MyGUI::MessageBoxStyle::IconQuest 232 | MyGUI::MessageBoxStyle::Yes 233 | MyGUI::MessageBoxStyle::No 234 | MyGUI::MessageBoxStyle::Cancel); 235 message->eventMessageBoxResult += MyGUI::newDelegate(this, &EditorState::notifyMessageBoxResultLoadDropFile); 236 } 237 else 238 { 239 clear(); 240 241 loadDropFile(); 242 } 243 244 _result = true; 245 } 246 notifyMessageBoxResultLoad(MyGUI::Message * _sender,MyGUI::MessageBoxStyle _result)247 void EditorState::notifyMessageBoxResultLoad(MyGUI::Message* _sender, MyGUI::MessageBoxStyle _result) 248 { 249 if (_result == MyGUI::MessageBoxStyle::Yes) 250 { 251 save(); 252 clear(); 253 254 showLoadWindow(); 255 } 256 else if (_result == MyGUI::MessageBoxStyle::No) 257 { 258 clear(); 259 260 showLoadWindow(); 261 } 262 } 263 notifyMessageBoxResultLoadDropFile(MyGUI::Message * _sender,MyGUI::MessageBoxStyle _result)264 void EditorState::notifyMessageBoxResultLoadDropFile(MyGUI::Message* _sender, MyGUI::MessageBoxStyle _result) 265 { 266 if (_result == MyGUI::MessageBoxStyle::Yes) 267 { 268 save(); 269 clear(); 270 271 loadDropFile(); 272 } 273 else if (_result == MyGUI::MessageBoxStyle::No) 274 { 275 clear(); 276 277 loadDropFile(); 278 } 279 } 280 loadDropFile()281 void EditorState::loadDropFile() 282 { 283 mFileName = mDropFileName; 284 addUserTag("CurrentFileName", mFileName); 285 286 load(); 287 updateCaption(); 288 } 289 showLoadWindow()290 void EditorState::showLoadWindow() 291 { 292 mOpenSaveFileDialog->setCurrentFolder(RecentFilesManager::getInstance().getRecentFolder()); 293 mOpenSaveFileDialog->setRecentFolders(RecentFilesManager::getInstance().getRecentFolders()); 294 mOpenSaveFileDialog->setDialogInfo(replaceTags("CaptionOpenFile"), replaceTags("ButtonOpenFile")); 295 mOpenSaveFileDialog->setMode("Load"); 296 mOpenSaveFileDialog->doModal(); 297 } 298 notifyEndDialog(Dialog * _sender,bool _result)299 void EditorState::notifyEndDialog(Dialog* _sender, bool _result) 300 { 301 if (_result) 302 { 303 if (mOpenSaveFileDialog->getMode() == "SaveAs") 304 { 305 RecentFilesManager::getInstance().setRecentFolder(mOpenSaveFileDialog->getCurrentFolder()); 306 mFileName = common::concatenatePath(mOpenSaveFileDialog->getCurrentFolder(), mOpenSaveFileDialog->getFileName()); 307 addUserTag("CurrentFileName", mFileName); 308 309 save(); 310 updateCaption(); 311 } 312 else if (mOpenSaveFileDialog->getMode() == "Load") 313 { 314 RecentFilesManager::getInstance().setRecentFolder(mOpenSaveFileDialog->getCurrentFolder()); 315 mFileName = common::concatenatePath(mOpenSaveFileDialog->getCurrentFolder(), mOpenSaveFileDialog->getFileName()); 316 addUserTag("CurrentFileName", mFileName); 317 318 load(); 319 updateCaption(); 320 } 321 } 322 323 mOpenSaveFileDialog->endModal(); 324 } 325 notifyMessageBoxResultClear(MyGUI::Message * _sender,MyGUI::MessageBoxStyle _result)326 void EditorState::notifyMessageBoxResultClear(MyGUI::Message* _sender, MyGUI::MessageBoxStyle _result) 327 { 328 if (_result == MyGUI::MessageBoxStyle::Yes) 329 { 330 save(); 331 clear(); 332 } 333 else if (_result == MyGUI::MessageBoxStyle::No) 334 { 335 clear(); 336 } 337 } 338 showSaveAsWindow()339 void EditorState::showSaveAsWindow() 340 { 341 mOpenSaveFileDialog->setCurrentFolder(RecentFilesManager::getInstance().getRecentFolder()); 342 mOpenSaveFileDialog->setRecentFolders(RecentFilesManager::getInstance().getRecentFolders()); 343 mOpenSaveFileDialog->setDialogInfo(replaceTags("CaptionSaveFile"), replaceTags("ButtonSaveFile")); 344 mOpenSaveFileDialog->setMode("SaveAs"); 345 mOpenSaveFileDialog->doModal(); 346 } 347 notifyMessageBoxResultQuit(MyGUI::Message * _sender,MyGUI::MessageBoxStyle _result)348 void EditorState::notifyMessageBoxResultQuit(MyGUI::Message* _sender, MyGUI::MessageBoxStyle _result) 349 { 350 if (_result == MyGUI::MessageBoxStyle::Yes) 351 { 352 if (mFileName == mDefaultFileName) 353 { 354 showSaveAsWindow(); 355 } 356 else 357 { 358 save(); 359 StateManager::getInstance().stateEvent(this, "Exit"); 360 } 361 } 362 else if (_result == MyGUI::MessageBoxStyle::No) 363 { 364 StateManager::getInstance().stateEvent(this, "Exit"); 365 } 366 } 367 notifyChanges()368 void EditorState::notifyChanges() 369 { 370 updateCaption(); 371 } 372 checkCommand()373 bool EditorState::checkCommand() 374 { 375 if (DialogManager::getInstance().getAnyDialog()) 376 return false; 377 378 if (MessageBoxManager::getInstance().hasAny()) 379 return false; 380 381 if (!StateManager::getInstance().getStateActivate(this)) 382 return false; 383 384 return true; 385 } 386 clear()387 void EditorState::clear() 388 { 389 DataManager::getInstance().clear(); 390 ActionManager::getInstance().reset(); 391 DataSelectorManager::getInstance().changeParent(DataManager::getInstance().getRoot()); 392 393 mFileName = mDefaultFileName; 394 addUserTag("CurrentFileName", mFileName); 395 396 updateCaption(); 397 } 398 load()399 void EditorState::load() 400 { 401 DataManager::getInstance().clear(); 402 ActionManager::getInstance().reset(); 403 DataSelectorManager::getInstance().changeParent(DataManager::getInstance().getRoot()); 404 405 pugi::xml_document doc; 406 pugi::xml_parse_result result = doc.load_file(mFileName.asWStr_c_str()); 407 if (result) 408 { 409 bool success = ExportManager::getInstance().deserialization(doc); 410 if (success) 411 { 412 if (mFileName != mDefaultFileName) 413 RecentFilesManager::getInstance().addRecentFile(mFileName); 414 415 DataSelectorManager::getInstance().changeParent(DataManager::getInstance().getRoot()); 416 } 417 else 418 { 419 /*MyGUI::Message* message =*/ MessageBoxManager::getInstance().create( 420 replaceTags("Error"), 421 replaceTags("MessageIncorrectFileFormat"), 422 MyGUI::MessageBoxStyle::IconError 423 | MyGUI::MessageBoxStyle::Yes); 424 425 mFileName = mDefaultFileName; 426 addUserTag("CurrentFileName", mFileName); 427 428 updateCaption(); 429 } 430 } 431 else 432 { 433 /*MyGUI::Message* message =*/ MessageBoxManager::getInstance().create( 434 replaceTags("Error"), 435 result.description(), 436 MyGUI::MessageBoxStyle::IconError 437 | MyGUI::MessageBoxStyle::Yes); 438 } 439 } 440 save()441 bool EditorState::save() 442 { 443 pugi::xml_document doc; 444 pugi::xml_node decl = doc.prepend_child(pugi::node_declaration); 445 decl.append_attribute("version") = "1.0"; 446 decl.append_attribute("encoding") = "UTF-8"; 447 448 ExportManager::getInstance().serialization(doc); 449 450 bool result = doc.save_file(mFileName.asWStr_c_str(), "\t", (pugi::format_indent | pugi::format_write_bom | pugi::format_win_new_line) & (~pugi::format_space_before_slash)); 451 452 if (result) 453 { 454 if (mFileName != mDefaultFileName) 455 RecentFilesManager::getInstance().addRecentFile(mFileName); 456 457 ActionManager::getInstance().saveChanges(); 458 return true; 459 } 460 461 /*MyGUI::Message* message =*/ MessageBoxManager::getInstance().create( 462 replaceTags("Error"), 463 "Error save file", 464 MyGUI::MessageBoxStyle::IconError 465 | MyGUI::MessageBoxStyle::Yes); 466 467 return false; 468 } 469 commandRecentFiles(const MyGUI::UString & _commandName,bool & _result)470 void EditorState::commandRecentFiles(const MyGUI::UString& _commandName, bool& _result) 471 { 472 commandFileDrop(_commandName, _result); 473 } 474 commandSettings(const MyGUI::UString & _commandName,bool & _result)475 void EditorState::commandSettings(const MyGUI::UString& _commandName, bool& _result) 476 { 477 mSettingsWindow->SendCommand("Command_LoadSettings"); 478 mSettingsWindow->doModal(); 479 480 _result = true; 481 } 482 notifySettingsWindowEndDialog(Dialog * _dialog,bool _result)483 void EditorState::notifySettingsWindowEndDialog(Dialog* _dialog, bool _result) 484 { 485 MYGUI_ASSERT(mSettingsWindow == _dialog, "mSettingsWindow == _sender"); 486 487 if (_result) 488 mSettingsWindow->SendCommand("Command_SaveSettings"); 489 490 mSettingsWindow->endModal(); 491 } 492 commandUndo(const MyGUI::UString & _commandName,bool & _result)493 void EditorState::commandUndo(const MyGUI::UString& _commandName, bool& _result) 494 { 495 if (!checkCommand()) 496 return; 497 498 ActionManager::getInstance().undoAction(); 499 500 _result = true; 501 } 502 commandRedo(const MyGUI::UString & _commandName,bool & _result)503 void EditorState::commandRedo(const MyGUI::UString& _commandName, bool& _result) 504 { 505 if (!checkCommand()) 506 return; 507 508 ActionManager::getInstance().redoAction(); 509 510 _result = true; 511 } 512 513 } 514