Skip to content

Commit

Permalink
Bug fix: Panel focus was lost in some situations
Browse files Browse the repository at this point in the history
1) When opening local-local more workspace (since 6.0)
2) When switching tabs (since 6.2 – 75044ab)

Source commit: 5d759fcc55518aa2377754cf3819987d37291f15
  • Loading branch information
martinprikryl committed Nov 15, 2023
1 parent 7c2a33e commit 7503292
Show file tree
Hide file tree
Showing 5 changed files with 86 additions and 30 deletions.
19 changes: 19 additions & 0 deletions source/forms/CustomScpExplorer.cpp
Expand Up @@ -10257,6 +10257,15 @@ void __fastcall TCustomScpExplorerForm::UnlockWindow()
{
DebugAssert(FLockSuspendLevel == 0);
Enabled = true;
// VCL_COPY (TCustomForm.SetWindowFocus)
if (Active && (ActiveControl != NULL))
{
::SetFocus(ActiveControl->Handle);
if (GetFocus() == ActiveControl->Handle)
{
ActiveControl->Perform(CM_UIACTIVATE, 0, 0);
}
}
}
}
//---------------------------------------------------------------------------
Expand Down Expand Up @@ -12062,3 +12071,13 @@ void TCustomScpExplorerForm::QueueResetLayoutColumns()
{
LoadListViewStr(QueueView3, QueueViewLayoutDefault);
}
//---------------------------------------------------------------------------
void * TCustomScpExplorerForm::SaveFocus()
{
return NULL;
}
//---------------------------------------------------------------------------
void TCustomScpExplorerForm::RestoreFocus(void * Focus)
{
DebugAssert(Focus == NULL);
}
2 changes: 2 additions & 0 deletions source/forms/CustomScpExplorer.h
Expand Up @@ -915,6 +915,8 @@ friend class TEditorUploadQueueItem;
void AutoSizeColumns(TOperationSide Side);
virtual void ResetLayoutColumns(TOperationSide Side) = 0;
void QueueResetLayoutColumns();
virtual void * SaveFocus();
virtual void RestoreFocus(void * Focus);

__property bool ComponentVisible[Byte Component] = { read = GetComponentVisible, write = SetComponentVisible };
__property bool EnableFocusedOperation[TOperationSide Side] = { read = GetEnableFocusedOperation, index = 0 };
Expand Down
87 changes: 57 additions & 30 deletions source/forms/ScpCommander.cpp
Expand Up @@ -1023,8 +1023,7 @@ void __fastcall TScpCommanderForm::SetToolbar2ItemAction(TTBXItem * Item, TBasic
void __fastcall TScpCommanderForm::UpdateControls()
{
// Before TCustomScpExplorerForm disables them (when disconnecting)
bool DirViewWasFocused = DirView(osOther)->Focused();
bool DriveViewWasFocused = DriveView(osOther)->Focused();
void * Focus = SaveFocus();

// When implicitly connecting a not-yet-connected session by switching to its tab opened with workspace,
// Terminal property is still NULL, but ActiveTerminal is already set.
Expand Down Expand Up @@ -1124,34 +1123,7 @@ void __fastcall TScpCommanderForm::UpdateControls()
bool LocalOnLeft = (Panel(true) == LocalPanel);
LocalMenuButton->Caption = LoadStr(HasTerminal ? LOCAL_MENU_CAPTION : (LocalOnLeft ? LEFT_MENU_CAPTION : RIGHT_MENU_CAPTION));
RemoteMenuButton->Caption = LoadStr(HasTerminal ? REMOTE_MENU_CAPTION : (LocalOnLeft ? RIGHT_MENU_CAPTION : LEFT_MENU_CAPTION));
if (DirViewWasFocused)
{
if (DirView(osOther)->Enabled)
{
DirView(osOther)->SetFocus();
}
else
{
LocalDirView->SetFocus();
}
}
if (DriveViewWasFocused)
{
if (DriveView(osOther)->Enabled)
{
DriveView(osOther)->SetFocus();
}
else if (LocalDriveView->Visible)
{
LocalDriveView->SetFocus();
}
else
{
// Switching to a disconnected session with local drive view hidden - fallback to the local dir view (should always be visible)
DebugAssert(LocalDirView->Visible);
LocalDirView->SetFocus();
}
}
RestoreFocus(Focus);

if (RemotePathLabel->FocusControl != DirView(osOther))
{
Expand Down Expand Up @@ -2976,3 +2948,58 @@ void TScpCommanderForm::ResetLayoutColumns(TOperationSide Side)

DirView(Side)->ColProperties->ParamsStr = DirViewParamsDefault;
}
//---------------------------------------------------------------------------
void * TScpCommanderForm::SaveFocus()
{
// When window is disabled, the ActiveControl might actually not be focusable
return ((ActiveControl != NULL) && ActiveControl->Focused()) ? ActiveControl : NULL;
}
//---------------------------------------------------------------------------
void TScpCommanderForm::RestoreFocus(void * Focus)
{
TWinControl * ControlFocus = static_cast<TWinControl *>(Focus);
if ((ControlFocus == LocalDirView) || (ControlFocus == LocalDriveView))
{
DebugAssert(ActiveControl == ControlFocus);
DebugAssert(ControlFocus->Enabled);
// noop
}
else if ((ControlFocus == RemoteDirView) || (ControlFocus == OtherLocalDirView))
{
if (DirView(osOther)->Enabled)
{
ControlFocus = DirView(osOther);
}
else
{
ControlFocus = LocalDirView;
}
}
else if ((ControlFocus == RemoteDriveView) || (ControlFocus == OtherLocalDriveView))
{
if (DriveView(osOther)->Enabled)
{
ControlFocus = DriveView(osOther);
}
else if (LocalDriveView->Visible)
{
ControlFocus = LocalDriveView;
}
else
{
// Switching to a disconnected session with local drive view hidden -
// fallback to the local dir view (should always be visible)
DebugAssert(LocalDirView->Visible);
ControlFocus = LocalDirView;
}
}
else
{
ControlFocus = NULL;
}

if (ControlFocus != NULL)
{
ControlFocus->SetFocus();
}
}
2 changes: 2 additions & 0 deletions source/forms/ScpCommander.h
Expand Up @@ -692,6 +692,8 @@ class TScpCommanderForm : public TCustomScpExplorerForm
virtual UnicodeString __fastcall DefaultDownloadTargetDirectory();
virtual bool SupportedSession(TSessionData * SessionData);
virtual void ResetLayoutColumns(TOperationSide Side);
virtual void * SaveFocus();
virtual void RestoreFocus(void * Focus);

__property double LeftPanelWidth = { read = GetLeftPanelWidth, write = SetLeftPanelWidth };
};
Expand Down
6 changes: 6 additions & 0 deletions source/windows/TerminalManager.cpp
Expand Up @@ -759,6 +759,7 @@ void __fastcall TTerminalManager::DoSetActiveSession(TManagedTerminal * value, b
{
NonVisualDataModule->StartBusy();
}
void * Focus = NULL;
try
{
// here used to be call to TCustomScpExporer::UpdateSessionData (now UpdateSession)
Expand All @@ -768,6 +769,7 @@ void __fastcall TTerminalManager::DoSetActiveSession(TManagedTerminal * value, b
FActiveSession = value;
if (ScpExplorer)
{
Focus = ScpExplorer->SaveFocus();
if ((ActiveSession != NULL) &&
((ActiveSession->Status == ssOpened) || ActiveSession->Disconnected || ActiveSession->LocalBrowser))
{
Expand Down Expand Up @@ -852,6 +854,10 @@ void __fastcall TTerminalManager::DoSetActiveSession(TManagedTerminal * value, b
{
NonVisualDataModule->EndBusy();
}
if ((Focus != NULL) && DebugAlwaysTrue(ScpExplorer != NULL))
{
ScpExplorer->RestoreFocus(Focus);
}
}
}
}
Expand Down

0 comments on commit 7503292

Please sign in to comment.