Support creating multiple main windows

This is not yet actually exposed in any way in the UI.
This commit is contained in:
Thomas Goyne 2015-08-22 18:17:51 -07:00
parent f5f5439808
commit 8de8724660
3 changed files with 53 additions and 25 deletions

View file

@ -161,8 +161,6 @@ FrameMain::FrameMain()
} }
FrameMain::~FrameMain () { FrameMain::~FrameMain () {
wxGetApp().frame = nullptr;
context->project->CloseAudio(); context->project->CloseAudio();
context->project->CloseVideo(); context->project->CloseVideo();

View file

@ -293,8 +293,7 @@ bool AegisubApp::OnInit() {
// Open main frame // Open main frame
StartupLog("Create main window"); StartupLog("Create main window");
frame = new FrameMain; NewProjectContext();
SetTopWindow(frame);
// Version checker // Version checker
StartupLog("Possibly perform automatic updates check"); StartupLog("Possibly perform automatic updates check");
@ -318,11 +317,7 @@ bool AegisubApp::OnInit() {
// Get parameter subs // Get parameter subs
StartupLog("Parse command line"); StartupLog("Parse command line");
std::vector<agi::fs::path> files; OpenFiles(argv.GetArguments());
for (int i = 1; i < argc; ++i)
files.push_back(from_wx(argv[i]));
if (!files.empty())
frame->context->project->LoadList(files);
} }
catch (agi::Exception const& e) { catch (agi::Exception const& e) {
wxMessageBox(to_wx(e.GetMessage()), "Fatal error while initializing"); wxMessageBox(to_wx(e.GetMessage()), "Fatal error while initializing");
@ -347,8 +342,9 @@ bool AegisubApp::OnInit() {
} }
int AegisubApp::OnExit() { int AegisubApp::OnExit() {
if (frame) for (auto frame : frames)
delete frame; delete frame;
frames.clear();
if (wxTheClipboard->Open()) { if (wxTheClipboard->Open()) {
wxTheClipboard->Flush(); wxTheClipboard->Flush();
@ -371,10 +367,27 @@ int AegisubApp::OnExit() {
return wxApp::OnExit(); return wxApp::OnExit();
} }
static void UnhandledExeception(bool stackWalk, agi::Context *c) { agi::Context& AegisubApp::NewProjectContext() {
auto frame = new FrameMain;
frame->Bind(wxEVT_DESTROY, [=](wxWindowDestroyEvent&) {
frames.erase(remove(begin(frames), end(frames), frame), end(frames));
if (frames.empty()) {
ExitMainLoop();
}
});
frames.push_back(frame);
return *frame->context;
}
void AegisubApp::UnhandledException(bool stackWalk) {
#if (!defined(_DEBUG) || defined(WITH_EXCEPTIONS)) && (wxUSE_ON_FATAL_EXCEPTION+0) #if (!defined(_DEBUG) || defined(WITH_EXCEPTIONS)) && (wxUSE_ON_FATAL_EXCEPTION+0)
if (c && c->ass && c->subsController) { bool any = false;
auto path = config::path->Decode("?user/recovered"); agi::fs::path path;
for (auto& frame : frames) {
auto c = frame->context.get();
if (!c || !c->ass || !c->subsController) continue;
path = config::path->Decode("?user/recovered");
agi::fs::CreateDirectory(path); agi::fs::CreateDirectory(path);
auto filename = c->subsController->Filename().stem(); auto filename = c->subsController->Filename().stem();
@ -382,26 +395,28 @@ static void UnhandledExeception(bool stackWalk, agi::Context *c) {
path /= filename; path /= filename;
c->subsController->Save(path); c->subsController->Save(path);
any = true;
}
if (stackWalk) if (stackWalk)
crash_writer::Write(); crash_writer::Write();
if (any) {
// Inform user of crash. // Inform user of crash.
wxMessageBox(agi::wxformat(exception_message, path), _("Program error"), wxOK | wxICON_ERROR | wxCENTER, nullptr); wxMessageBox(agi::wxformat(exception_message, path), _("Program error"), wxOK | wxICON_ERROR | wxCENTER, nullptr);
} }
else if (LastStartupState) { else if (LastStartupState) {
if (stackWalk)
crash_writer::Write();
wxMessageBox(fmt_wx("Aegisub has crashed while starting up!\n\nThe last startup step attempted was: %s.", LastStartupState), _("Program error"), wxOK | wxICON_ERROR | wxCENTER); wxMessageBox(fmt_wx("Aegisub has crashed while starting up!\n\nThe last startup step attempted was: %s.", LastStartupState), _("Program error"), wxOK | wxICON_ERROR | wxCENTER);
} }
#endif #endif
} }
void AegisubApp::OnUnhandledException() { void AegisubApp::OnUnhandledException() {
UnhandledExeception(false, frame ? frame->context.get() : nullptr); UnhandledException(false);
} }
void AegisubApp::OnFatalException() { void AegisubApp::OnFatalException() {
UnhandledExeception(true, frame ? frame->context.get() : nullptr); UnhandledException(true);
} }
#define SHOW_EXCEPTION(str) \ #define SHOW_EXCEPTION(str) \
@ -429,7 +444,6 @@ int AegisubApp::OnRun() {
std::string error; std::string error;
try { try {
if (m_exitOnFrameDelete == Later) m_exitOnFrameDelete = Yes;
return MainLoop(); return MainLoop();
} }
catch (const std::exception &e) { error = std::string("std::exception: ") + e.what(); } catch (const std::exception &e) { error = std::string("std::exception: ") + e.what(); }
@ -446,7 +460,14 @@ int AegisubApp::OnRun() {
return 1; return 1;
} }
void AegisubApp::MacOpenFile(const wxString &filename) { void AegisubApp::MacOpenFiles(wxArrayString const& filenames) {
if (frame && !filename.empty()) OpenFiles(filenames);
frame->context->project->LoadSubtitles(agi::fs::path(filename.wx_str())); }
void AegisubApp::OpenFiles(wxArrayStringsAdapter filenames) {
std::vector<agi::fs::path> files;
for (int i = 1; i < argc; ++i)
files.push_back(from_wx(argv[i]));
if (!files.empty())
frames[0]->context->project->LoadList(files);
} }

View file

@ -36,6 +36,9 @@
#endif #endif
class FrameMain; class FrameMain;
namespace agi {
struct Context;
}
class AegisubApp : public wxApp { class AegisubApp : public wxApp {
friend class FrameMain; friend class FrameMain;
@ -50,13 +53,19 @@ class AegisubApp : public wxApp {
void OnAssertFailure(const wxChar *file, int line, const wxChar *func, const wxChar *cond, const wxChar *msg) override; void OnAssertFailure(const wxChar *file, int line, const wxChar *func, const wxChar *cond, const wxChar *msg) override;
FrameMain *frame = nullptr; void UnhandledException(bool);
void OpenFiles(wxArrayStringsAdapter filenames);
std::vector<FrameMain *> frames;
public: public:
AegisubApp(); AegisubApp();
AegisubLocale locale; AegisubLocale locale;
agi::Context& NewProjectContext();
// Apple events // Apple events
void MacOpenFile(const wxString &filename) void MacOpenFiles(wxArrayString const& filenames)
#ifdef __APPLE__ #ifdef __APPLE__
override override
#endif #endif