Fix flickering issue if Doc is deleted from outside
Improve behavior when notifying the user about a buffer change (opened file changed or deleted)
- Restore the Notepad++ window and switch to the document in question *before* showing the dialog (this was only done afterwards before)
- Fix flickering issue described in #1018 and #2010 which was exposed by f2cd779066
Closes #2956
This commit is contained in:
parent
61bc5e27bb
commit
ffe2ddace3
@ -4963,6 +4963,27 @@ void Notepad_plus::drawTabbarColoursFromStylerArray()
|
|||||||
TabBarPlus::setColour(stInact->_bgColor, TabBarPlus::inactiveBg);
|
TabBarPlus::setColour(stInact->_bgColor, TabBarPlus::inactiveBg);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Notepad_plus::prepareBufferChangedDialog(Buffer * buffer)
|
||||||
|
{
|
||||||
|
// immediately show window if it was minimized before
|
||||||
|
if (::IsIconic(_pPublicInterface->getHSelf()))
|
||||||
|
::ShowWindow(_pPublicInterface->getHSelf(), SW_RESTORE);
|
||||||
|
|
||||||
|
// switch to the file that changed
|
||||||
|
int index = _pDocTab->getIndexByBuffer(buffer->getID());
|
||||||
|
int iView = currentView();
|
||||||
|
if (index == -1)
|
||||||
|
iView = otherView();
|
||||||
|
activateBuffer(buffer->getID(), iView); //activate the buffer in the first view possible
|
||||||
|
|
||||||
|
// prevent flickering issue by "manually" clicking and activating the _pEditView
|
||||||
|
// (mouse events seem to get lost / improperly handled when showing the dialog)
|
||||||
|
auto curPos = _pEditView->execute(SCI_GETCURRENTPOS);
|
||||||
|
::PostMessage(_pEditView->getHSelf(), WM_LBUTTONDOWN, 0, 0);
|
||||||
|
::PostMessage(_pEditView->getHSelf(), WM_LBUTTONUP, 0, 0);
|
||||||
|
::PostMessage(_pEditView->getHSelf(), SCI_SETSEL, curPos, curPos);
|
||||||
|
}
|
||||||
|
|
||||||
void Notepad_plus::notifyBufferChanged(Buffer * buffer, int mask)
|
void Notepad_plus::notifyBufferChanged(Buffer * buffer, int mask)
|
||||||
{
|
{
|
||||||
// To avoid to crash while MS-DOS style is set as default language,
|
// To avoid to crash while MS-DOS style is set as default language,
|
||||||
@ -4983,8 +5004,6 @@ void Notepad_plus::notifyBufferChanged(Buffer * buffer, int mask)
|
|||||||
//Only event that applies to non-active Buffers
|
//Only event that applies to non-active Buffers
|
||||||
if (mask & BufferChangeStatus)
|
if (mask & BufferChangeStatus)
|
||||||
{ //reload etc
|
{ //reload etc
|
||||||
bool didDialog = false;
|
|
||||||
bool doCloseDoc = false;
|
|
||||||
switch(buffer->getStatus())
|
switch(buffer->getStatus())
|
||||||
{
|
{
|
||||||
case DOC_UNNAMED: //nothing todo
|
case DOC_UNNAMED: //nothing todo
|
||||||
@ -4997,28 +5016,9 @@ void Notepad_plus::notifyBufferChanged(Buffer * buffer, int mask)
|
|||||||
bool autoUpdate = (nppGUI._fileAutoDetection == cdAutoUpdate) || (nppGUI._fileAutoDetection == cdAutoUpdateGo2end);
|
bool autoUpdate = (nppGUI._fileAutoDetection == cdAutoUpdate) || (nppGUI._fileAutoDetection == cdAutoUpdateGo2end);
|
||||||
if (!autoUpdate || buffer->isDirty())
|
if (!autoUpdate || buffer->isDirty())
|
||||||
{
|
{
|
||||||
// if file updating is not silently, we switch to the file to update.
|
prepareBufferChangedDialog(buffer);
|
||||||
int index = _pDocTab->getIndexByBuffer(buffer->getID());
|
|
||||||
int iView = currentView();
|
|
||||||
if (index == -1)
|
|
||||||
iView = otherView();
|
|
||||||
activateBuffer(buffer->getID(), iView); //activate the buffer in the first view possible
|
|
||||||
|
|
||||||
// Then we ask user to update
|
|
||||||
didDialog = true;
|
|
||||||
|
|
||||||
// This section deal with the flicking issue which was caused by f2cd779 (discussed in detail @ #1018)
|
|
||||||
// Idea is :
|
|
||||||
// 1. First get the current caret position.
|
|
||||||
// 2. Send WM_LBUTTONDOWN and WM_LBUTTONUP message (which acts as double click at 0,0)
|
|
||||||
// 3. Now set caret back to original position.
|
|
||||||
//
|
|
||||||
auto curPos = _pEditView->execute(SCI_GETCURRENTPOS);
|
|
||||||
::PostMessage(_pEditView->getHSelf(), WM_LBUTTONDOWN, 0, 0);
|
|
||||||
::PostMessage(_pEditView->getHSelf(), WM_LBUTTONUP, 0, 0);
|
|
||||||
::PostMessage(_pEditView->getHSelf(), SCI_SETSEL, curPos, curPos);
|
|
||||||
// Now the flickering issue is not seen.
|
|
||||||
|
|
||||||
|
// Then we ask user to update
|
||||||
if (doReloadOrNot(buffer->getFullPathName(), buffer->isDirty()) != IDYES)
|
if (doReloadOrNot(buffer->getFullPathName(), buffer->isDirty()) != IDYES)
|
||||||
break; //abort
|
break; //abort
|
||||||
}
|
}
|
||||||
@ -5050,42 +5050,26 @@ void Notepad_plus::notifyBufferChanged(Buffer * buffer, int mask)
|
|||||||
}
|
}
|
||||||
case DOC_DELETED: //ask for keep
|
case DOC_DELETED: //ask for keep
|
||||||
{
|
{
|
||||||
|
prepareBufferChangedDialog(buffer);
|
||||||
|
|
||||||
SCNotification scnN;
|
SCNotification scnN;
|
||||||
scnN.nmhdr.code = NPPN_FILEDELETED;
|
scnN.nmhdr.code = NPPN_FILEDELETED;
|
||||||
scnN.nmhdr.hwndFrom = _pPublicInterface->getHSelf();
|
scnN.nmhdr.hwndFrom = _pPublicInterface->getHSelf();
|
||||||
scnN.nmhdr.idFrom = (uptr_t)buffer->getID();
|
scnN.nmhdr.idFrom = (uptr_t)buffer->getID();
|
||||||
_pluginsManager.notify(&scnN);
|
_pluginsManager.notify(&scnN);
|
||||||
|
|
||||||
int index = _pDocTab->getIndexByBuffer(buffer->getID());
|
int doCloseDoc = doCloseOrNot(buffer->getFullPathName()) == IDNO;
|
||||||
int iView = currentView();
|
|
||||||
if (index == -1)
|
|
||||||
iView = otherView();
|
|
||||||
|
|
||||||
activateBuffer(buffer->getID(), iView); //activate the buffer in the first view possible
|
|
||||||
didDialog = true;
|
|
||||||
doCloseDoc = doCloseOrNot(buffer->getFullPathName()) == IDNO;
|
|
||||||
if (doCloseDoc)
|
if (doCloseDoc)
|
||||||
{
|
{
|
||||||
//close in both views, doing current view last since that has to remain opened
|
//close in both views, doing current view last since that has to remain opened
|
||||||
bool isSnapshotMode = nppGUI.isSnapshotMode();
|
bool isSnapshotMode = nppGUI.isSnapshotMode();
|
||||||
doClose(buffer->getID(), otherView(), isSnapshotMode);
|
doClose(buffer->getID(), otherView(), isSnapshotMode);
|
||||||
doClose(buffer->getID(), currentView(), isSnapshotMode);
|
doClose(buffer->getID(), currentView(), isSnapshotMode);
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (didDialog)
|
|
||||||
{
|
|
||||||
auto curPos = _pEditView->execute(SCI_GETCURRENTPOS);
|
|
||||||
::PostMessage(_pEditView->getHSelf(), WM_LBUTTONUP, 0, 0);
|
|
||||||
::PostMessage(_pEditView->getHSelf(), SCI_SETSEL, curPos, curPos);
|
|
||||||
if (::IsIconic(_pPublicInterface->getHSelf()))
|
|
||||||
::ShowWindow(_pPublicInterface->getHSelf(), SW_RESTORE);
|
|
||||||
|
|
||||||
if (doCloseDoc) // buffer has been deleted, cannot (and no need to) go on
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (mask & (BufferChangeReadonly))
|
if (mask & (BufferChangeReadonly))
|
||||||
|
@ -207,6 +207,7 @@ public:
|
|||||||
void loadLastSession();
|
void loadLastSession();
|
||||||
bool loadSession(Session & session, bool isSnapshotMode = false);
|
bool loadSession(Session & session, bool isSnapshotMode = false);
|
||||||
|
|
||||||
|
void prepareBufferChangedDialog(Buffer * buffer);
|
||||||
void notifyBufferChanged(Buffer * buffer, int mask);
|
void notifyBufferChanged(Buffer * buffer, int mask);
|
||||||
bool findInFinderFiles(FindersInfo *findInFolderInfo);
|
bool findInFinderFiles(FindersInfo *findInFolderInfo);
|
||||||
bool findInFiles();
|
bool findInFiles();
|
||||||
|
Loading…
Reference in New Issue
Block a user