X-Git-Url: https://git.saurik.com/wxWidgets.git/blobdiff_plain/c6e4d276a34ff0bf57c2da45f3cd84f296afacd2..67fdb6f9af36cba7a0b06e61be320ce914dc3f4f:/src/common/docview.cpp?ds=inline diff --git a/src/common/docview.cpp b/src/common/docview.cpp index 5d53187c73..459ce5585c 100644 --- a/src/common/docview.cpp +++ b/src/common/docview.cpp @@ -56,7 +56,9 @@ #include "wx/cmdproc.h" #include "wx/tokenzr.h" #include "wx/filename.h" +#include "wx/stdpaths.h" #include "wx/vector.h" +#include "wx/ptr_scpd.h" #if wxUSE_STD_IOSTREAM #include "wx/ioswrap.h" @@ -111,7 +113,7 @@ wxWindow *wxFindSuitableParent() wxString FindExtension(const wxString& path) { wxString ext; - wxSplitPath(path, NULL, NULL, &ext); + wxFileName::SplitPath(path, NULL, NULL, &ext); // VZ: extensions are considered not case sensitive - is this really a good // idea? @@ -259,7 +261,7 @@ bool wxDocument::OnNewDocument() bool wxDocument::Save() { - if (!IsModified() && m_savedYet) + if ( AlreadySaved() ) return true; if ( m_documentFile.empty() || !m_savedYet ) @@ -306,10 +308,14 @@ bool wxDocument::SaveAs() wxString filter = docTemplate->GetFileFilter() ; #endif wxString defaultDir = docTemplate->GetDirectory(); - if (defaultDir.IsEmpty()) + if ( defaultDir.empty() ) + { defaultDir = wxPathOnly(GetFilename()); + if ( defaultDir.empty() ) + defaultDir = GetDocumentManager()->GetLastDirectory(); + } - wxString tmp = wxFileSelector(_("Save As"), + wxString fileName = wxFileSelector(_("Save As"), defaultDir, wxFileNameFromPath(GetFilename()), docTemplate->GetDefaultExtension(), @@ -317,12 +323,11 @@ bool wxDocument::SaveAs() wxFD_SAVE | wxFD_OVERWRITE_PROMPT, GetDocumentWindow()); - if (tmp.empty()) + if (fileName.empty()) return false; - wxString fileName(tmp); - wxString path, name, ext; - wxSplitPath(fileName, & path, & name, & ext); + wxString ext; + wxFileName::SplitPath(fileName, NULL, NULL, &ext); if (ext.empty()) { @@ -330,22 +335,13 @@ bool wxDocument::SaveAs() fileName += docTemplate->GetDefaultExtension(); } - SetFilename(fileName); - SetTitle(wxFileNameFromPath(fileName)); - - // Notify the views that the filename has changed - wxList::compatibility_iterator node = m_documentViews.GetFirst(); - while (node) - { - wxView *view = (wxView *)node->GetData(); - view->OnChangeFilename(); - node = node->GetNext(); - } - // Files that were not saved correctly are not added to the FileHistory. - if (!OnSaveDocument(m_documentFile)) + if (!OnSaveDocument(fileName)) return false; + SetTitle(wxFileNameFromPath(fileName)); + SetFilename(fileName, true); // will call OnChangeFileName automatically + // A file that doesn't use the default extension of its document template cannot be opened // via the FileHistory, so we do not add it. if (docTemplate->FileMatchesTemplate(fileName)) @@ -480,12 +476,12 @@ bool wxDocument::OnSaveModified() ( wxString::Format ( - _("Do you want to save changes to document %s?"), + _("Do you want to save changes to %s?"), GetUserReadableName() ), wxTheApp->GetAppDisplayName(), - wxYES_NO | wxCANCEL | wxICON_QUESTION, - GetDocumentWindow() + wxYES_NO | wxCANCEL | wxICON_QUESTION | wxCENTRE, + wxFindSuitableParent() ) ) { case wxNO: @@ -565,6 +561,11 @@ void wxDocument::NotifyClosing() void wxDocument::SetFilename(const wxString& filename, bool notifyViews) { m_documentFile = filename; + OnChangeFilename(notifyViews); +} + +void wxDocument::OnChangeFilename(bool notifyViews) +{ if ( notifyViews ) { // Notify the views that the filename has changed @@ -580,30 +581,21 @@ void wxDocument::SetFilename(const wxString& filename, bool notifyViews) bool wxDocument::DoSaveDocument(const wxString& file) { - wxString msgTitle; - if (!wxTheApp->GetAppDisplayName().empty()) - msgTitle = wxTheApp->GetAppDisplayName(); - else - msgTitle = wxString(_("File error")); - #if wxUSE_STD_IOSTREAM wxSTD ofstream store(file.mb_str(), wxSTD ios::binary); - if (store.fail() || store.bad()) + if ( !store ) #else wxFileOutputStream store(file); - if (store.GetLastError() != wxSTREAM_NO_ERROR) + if ( store.GetLastError() != wxSTREAM_NO_ERROR ) #endif { - (void)wxMessageBox(_("Sorry, could not open this file for saving."), msgTitle, wxOK | wxICON_EXCLAMATION, - GetDocumentWindow()); - // Saving error + wxLogError(_("File \"%s\" could not be opened for writing."), file); return false; } + if (!SaveObject(store)) { - (void)wxMessageBox(_("Sorry, could not save this file."), msgTitle, wxOK | wxICON_EXCLAMATION, - GetDocumentWindow()); - // Saving error + wxLogError(_("Failed to save document to the file \"%s\"."), file); return false; } @@ -614,24 +606,29 @@ bool wxDocument::DoOpenDocument(const wxString& file) { #if wxUSE_STD_IOSTREAM wxSTD ifstream store(file.mb_str(), wxSTD ios::binary); - if (!store.fail() && !store.bad()) + if ( !store ) #else wxFileInputStream store(file); - if (store.GetLastError() == wxSTREAM_NO_ERROR) + if (store.GetLastError() != wxSTREAM_NO_ERROR || !store.IsOk()) #endif { + wxLogError(_("File \"%s\" could not be opened for reading."), file); + return false; + } + #if wxUSE_STD_IOSTREAM - LoadObject(store); - if ( !!store || store.eof() ) + LoadObject(store); + if ( !store ) #else - int res = LoadObject(store).GetLastError(); - if ( res == wxSTREAM_NO_ERROR || res == wxSTREAM_EOF ) + int res = LoadObject(store).GetLastError(); + if ( res != wxSTREAM_NO_ERROR && res != wxSTREAM_EOF ) #endif - return true; + { + wxLogError(_("Failed to read document from the file \"%s\"."), file); + return false; } - wxLogError(_("Sorry, could not open this file.")); - return false; + return true; } @@ -652,13 +649,10 @@ wxView::~wxView() m_viewDocument->RemoveView(this); } -// Extend event processing to search the document's event table -bool wxView::ProcessEvent(wxEvent& event) +bool wxView::TryValidator(wxEvent& event) { - if ( !GetDocument() || !GetDocument()->ProcessEvent(event) ) - return wxEvtHandler::ProcessEvent(event); - - return true; + wxDocument * const doc = GetDocument(); + return doc && doc->ProcessEventHere(event); } void wxView::OnActivateView(bool WXUNUSED(activate), wxView *WXUNUSED(activeView), wxView *WXUNUSED(deactiveView)) @@ -786,20 +780,15 @@ wxDocTemplate::InitDocument(wxDocument* doc, const wxString& path, long flags) wxView *wxDocTemplate::CreateView(wxDocument *doc, long flags) { - wxView *view = DoCreateView(); - if ( view == NULL ) + wxScopedPtr view(DoCreateView()); + if ( !view ) return NULL; view->SetDocument(doc); - if (view->OnCreate(doc, flags)) - { - return view; - } - else - { - delete view; + if ( !view->OnCreate(doc, flags) ) return NULL; - } + + return view.release(); } // The default (very primitive) format detection: check is the extension is @@ -954,6 +943,19 @@ bool wxDocManager::Initialize() return true; } +wxString wxDocManager::GetLastDirectory() const +{ + // use the system-dependent default location for the document files if + // we're being opened for the first time + if ( m_lastDirectory.empty() ) + { + wxDocManager * const self = const_cast(this); + self->m_lastDirectory = wxStandardPaths::Get().GetAppDocumentsDir(); + } + + return m_lastDirectory; +} + wxFileHistory *wxDocManager::OnCreateFileHistory() { return new wxFileHistory; @@ -979,7 +981,7 @@ void wxDocManager::OnFileCloseAll(wxCommandEvent& WXUNUSED(event)) void wxDocManager::OnFileNew(wxCommandEvent& WXUNUSED(event)) { - CreateDocument( wxEmptyString, wxDOC_NEW ); + CreateNewDocument(); } void wxDocManager::OnFileOpen(wxCommandEvent& WXUNUSED(event)) @@ -1086,7 +1088,9 @@ void wxDocManager::OnRedo(wxCommandEvent& event) void wxDocManager::OnUpdateFileOpen(wxUpdateUIEvent& event) { - event.Enable( true ); + // CreateDocument() (which is called from OnFileOpen) may succeed + // only when there is at least a template: + event.Enable( GetTemplates().GetCount()>0 ); } void wxDocManager::OnUpdateDisableIfNoDoc(wxUpdateUIEvent& event) @@ -1096,13 +1100,15 @@ void wxDocManager::OnUpdateDisableIfNoDoc(wxUpdateUIEvent& event) void wxDocManager::OnUpdateFileNew(wxUpdateUIEvent& event) { - event.Enable( true ); + // CreateDocument() (which is called from OnFileNew) may succeed + // only when there is at least a template: + event.Enable( GetTemplates().GetCount()>0 ); } void wxDocManager::OnUpdateFileSave(wxUpdateUIEvent& event) { - wxDocument *doc = GetCurrentDocument(); - event.Enable( doc && doc->IsModified() ); + wxDocument * const doc = GetCurrentDocument(); + event.Enable( doc && !doc->AlreadySaved() ); } void wxDocManager::OnUpdateUndo(wxUpdateUIEvent& event) @@ -1145,14 +1151,10 @@ wxView *wxDocManager::GetCurrentView() const return NULL; } -// Extend event processing to search the view's event table -bool wxDocManager::ProcessEvent(wxEvent& event) +bool wxDocManager::TryValidator(wxEvent& event) { wxView * const view = GetCurrentView(); - if ( view && view->ProcessEvent(event) ) - return true; - - return wxEvtHandler::ProcessEvent(event); + return view && view->ProcessEventHere(event); } namespace @@ -1506,7 +1508,7 @@ wxDocTemplate *wxDocManager::SelectDocumentPath(wxDocTemplate **templates, wxWindow* parent = wxFindSuitableParent(); wxString pathTmp = wxFileSelectorEx(_("Open File"), - m_lastDirectory, + GetLastDirectory(), wxEmptyString, &FilterIndex, descrBuf, @@ -1524,13 +1526,14 @@ wxDocTemplate *wxDocManager::SelectDocumentPath(wxDocTemplate **templates, else msgTitle = wxString(_("File error")); - (void)wxMessageBox(_("Sorry, could not open this file."), msgTitle, wxOK | wxICON_EXCLAMATION, + (void)wxMessageBox(_("Sorry, could not open this file."), msgTitle, wxOK | wxICON_EXCLAMATION | wxCENTRE, parent); path = wxEmptyString; return NULL; } - m_lastDirectory = wxPathOnly(pathTmp); + + SetLastDirectory(wxPathOnly(pathTmp)); path = pathTmp; @@ -1546,7 +1549,7 @@ wxDocTemplate *wxDocManager::SelectDocumentPath(wxDocTemplate **templates, // can only happen if the application changes the allowed templates in runtime. (void)wxMessageBox(_("Sorry, the format for this file is unknown."), _("Open File"), - wxOK | wxICON_EXCLAMATION, wxFindSuitableParent()); + wxOK | wxICON_EXCLAMATION | wxCENTRE, wxFindSuitableParent()); } } else @@ -1782,22 +1785,15 @@ wxDocChildFrame::wxDocChildFrame(wxDocument *doc, view->SetFrame(this); } -// Extend event processing to search the view's event table -bool wxDocChildFrame::ProcessEvent(wxEvent& event) +bool wxDocChildFrame::TryValidator(wxEvent& event) { - if (m_childView) - m_childView->Activate(true); + if ( !m_childView ) + return false; - if ( !m_childView || ! m_childView->ProcessEvent(event) ) - { - // Only hand up to the parent if it's a menu command - if (!event.IsKindOf(CLASSINFO(wxCommandEvent)) || !GetParent() || !GetParent()->ProcessEvent(event)) - return wxEvtHandler::ProcessEvent(event); - else - return true; - } - else - return true; + // FIXME: why is this needed here? + m_childView->Activate(true); + + return m_childView->ProcessEventHere(event); } void wxDocChildFrame::OnActivate(wxActivateEvent& event) @@ -1912,13 +1908,9 @@ void wxDocParentFrame::OnMRUFile(wxCommandEvent& event) } // Extend event processing to search the view's event table -bool wxDocParentFrame::ProcessEvent(wxEvent& event) +bool wxDocParentFrame::TryValidator(wxEvent& event) { - // Try the document manager, then do default processing - if (!m_docManager || !m_docManager->ProcessEvent(event)) - return wxEvtHandler::ProcessEvent(event); - else - return true; + return m_docManager && m_docManager->ProcessEventHere(event); } // Define the behaviour for the frame closing @@ -2035,24 +2027,22 @@ void wxFileHistory::AddFileToHistory(const wxString& file) { RemoveFileFromHistory(--numFiles); } - else // add a new menu item to all file menus (will be updated below) + + // add a new menu item to all file menus (they will be updated below) + for ( wxList::compatibility_iterator node = m_fileMenus.GetFirst(); + node; + node = node->GetNext() ) { - for ( wxList::compatibility_iterator node = m_fileMenus.GetFirst(); - node; - node = node->GetNext() ) - { - wxMenu * const menu = (wxMenu *)node->GetData(); + wxMenu * const menu = (wxMenu *)node->GetData(); - if ( !numFiles && menu->GetMenuItemCount() ) - menu->AppendSeparator(); + if ( !numFiles && menu->GetMenuItemCount() ) + menu->AppendSeparator(); - // label doesn't matter, it will be set below anyhow, but it can't - // be empty (this is supposed to indicate a stock item) - menu->Append(m_idBase + numFiles, " "); - } + // label doesn't matter, it will be set below anyhow, but it can't + // be empty (this is supposed to indicate a stock item) + menu->Append(m_idBase + numFiles, " "); } - // insert the new file in the beginning of the file history m_fileHistory.insert(m_fileHistory.begin(), file); numFiles++;