Browse Source

Enhanced ScreenTips

Source commit: 51df00652b9a7f7106079e31b54a8c3c06d9382b
Martin Prikryl 9 years ago
parent
commit
0656a11e36

+ 5 - 31
source/forms/CustomScpExplorer.cpp

@@ -170,7 +170,6 @@ __fastcall TCustomScpExplorerForm::TCustomScpExplorerForm(TComponent* Owner):
   NonVisualDataModule->ScpExplorer = this;
   FAutoOperation = false;
   FForceExecution = false;
-  FShowStatusBarHint = false;
   FIgnoreNextDialogChar = 0;
   FErrorList = NULL;
   FSynchronizeProgressForm = NULL;
@@ -259,6 +258,8 @@ __fastcall TCustomScpExplorerForm::TCustomScpExplorerForm(TComponent* Owner):
   UseDesktopFont(RemoteStatusBar);
 
   reinterpret_cast<TLabel*>(QueueSplitter)->OnDblClick = QueueSplitterDblClick;
+  QueueSplitter->ShowHint = true;
+  RemotePanelSplitter->ShowHint = true;
 
   FSystemImageList = SharedSystemImageList(false);
   FSystemImageList->DrawingStyle = dsTransparent;
@@ -876,11 +877,10 @@ void __fastcall TCustomScpExplorerForm::UpdateTransferList()
     // this way we get name for "default" settings (COPY_PARAM_DEFAULT)
     UnicodeString Name = TransferList->Strings->Strings[TransferList->ItemIndex];
     TransferDropDown->Text = StripHotkey(Name);
-    TransferDropDown->Hint = FORMAT(L"%s\n \n%s:\n%s|%s",
+    TransferDropDown->Hint = FORMAT(L"%s|%s:\n%s",
       (FTransferDropDownHint, StripHotkey(Name),
        GUIConfiguration->CurrentCopyParam.GetInfoStr(L"; ",
-         FLAGMASK(Terminal != NULL, Terminal->UsableCopyParamAttrs(0).General)),
-       FTransferDropDownHint));
+         FLAGMASK(Terminal != NULL, Terminal->UsableCopyParamAttrs(0).General))));
     // update the label, otherwise when it is updated only on the first draw
     // of the list, it is drawn "bold" for some reason
     FTransferListHoverIndex = TransferList->ItemIndex;
@@ -4113,12 +4113,7 @@ void __fastcall TCustomScpExplorerForm::UpdateStatusBar()
     SessionStatusBar->SimplePanel = false;
     const TSessionInfo & SessionInfo = Terminal->GetSessionInfo();
 
-    if (FShowStatusBarHint)
-    {
-      // escape hotkeys particularly because of the custom commands names
-      SessionStatusBar->Panels->Items[0]->Caption = EscapeHotkey(FStatusBarHint);
-    }
-    else if (!FNote.IsEmpty())
+    if (!FNote.IsEmpty())
     {
       SessionStatusBar->Panels->Items[0]->Caption = FNote;
     }
@@ -4223,23 +4218,6 @@ void __fastcall TCustomScpExplorerForm::UserActionTimer(TObject * /*Sender*/)
   }
 }
 //---------------------------------------------------------------------------
-void __fastcall TCustomScpExplorerForm::ApplicationHint(TObject * /*Sender*/)
-{
-  DebugAssert(Application);
-  // Application->Hint contains long hint only
-  UnicodeString AHint = Application->Hint;
-  FShowStatusBarHint = Active && !AHint.IsEmpty();
-  if (FShowStatusBarHint)
-  {
-    FStatusBarHint = AHint;
-  }
-  else
-  {
-    FStatusBarHint = L"";
-  }
-  UpdateStatusBar();
-}
-//---------------------------------------------------------------------------
 void __fastcall TCustomScpExplorerForm::ApplicationMinimize(TObject * /*Sender*/)
 {
   if (WinConfiguration->MinimizeToTray)
@@ -8484,10 +8462,6 @@ void __fastcall TCustomScpExplorerForm::DirViewEditing(
   }
 }
 //---------------------------------------------------------------------------
-void __fastcall TCustomScpExplorerForm::FormActivate(TObject * /*Sender*/)
-{
-  ApplicationEvents->OnHint = ApplicationHint;
-}
 //---------------------------------------------------------------------------
 TDragDropFilesEx * __fastcall TCustomScpExplorerForm::CreateDragDropFilesEx()
 {

+ 1 - 2
source/forms/CustomScpExplorer.dfm

@@ -8,7 +8,6 @@ object CustomScpExplorerForm: TCustomScpExplorerForm
   ParentFont = True
   KeyPreview = True
   OldCreateOrder = False
-  OnActivate = FormActivate
   OnClose = FormClose
   OnCloseQuery = FormCloseQuery
   OnConstrainedResize = FormConstrainedResize
@@ -227,6 +226,7 @@ object CustomScpExplorerForm: TCustomScpExplorerForm
         Top = 0
         Caption = 'QueueToolbar'
         Images = GlyphsModule.ExplorerImages
+        Options = [tboShowHint]
         ParentShowHint = False
         ShowHint = True
         TabOrder = 0
@@ -317,7 +317,6 @@ object CustomScpExplorerForm: TCustomScpExplorerForm
     end
   end
   object ApplicationEvents: TApplicationEvents
-    OnHint = ApplicationHint
     OnMinimize = ApplicationMinimize
     OnRestore = ApplicationRestore
     Left = 88

+ 0 - 4
source/forms/CustomScpExplorer.h

@@ -102,7 +102,6 @@ __published:
     const TPoint &MousePos, bool &Handled);
   void __fastcall RemoteDirViewGetSelectFilter(
     TCustomDirView *Sender, bool Select, TFileFilter &Filter);
-  void __fastcall ApplicationHint(TObject * Sender);
   void __fastcall FormCloseQuery(TObject *Sender, bool &CanClose);
   void __fastcall RemoteDirViewDisplayProperties(TObject *Sender);
   void __fastcall DirViewColumnRightClick(TObject *Sender,
@@ -173,7 +172,6 @@ __published:
   void __fastcall RemotePathComboBoxCancel(TObject * Sender);
   void __fastcall DirViewEditing(TObject *Sender, TListItem *Item,
           bool &AllowEdit);
-  void __fastcall FormActivate(TObject *Sender);
   void __fastcall FormShow(TObject *Sender);
   void __fastcall SessionsPageControlChange(TObject *Sender);
   void __fastcall SessionsPageControlMouseDown(TObject *Sender, TMouseButton Button,
@@ -199,8 +197,6 @@ private:
   bool FFormRestored;
   bool FAutoOperation;
   bool FForceExecution;
-  bool FShowStatusBarHint;
-  UnicodeString FStatusBarHint;
   unsigned short FIgnoreNextDialogChar;
   TStringList * FErrorList;
   HANDLE FDDExtMutex;

+ 53 - 86
source/forms/Editor.cpp

@@ -674,7 +674,6 @@ __fastcall TEditorForm::TEditorForm(TComponent* Owner)
   FCaretPos = TPoint(-1, -1);
   FLastFindDialog = NULL;
   FCloseAnnounced = false;
-  FShowStatusBarHint = false;
   ApplyConfiguration();
   FFindDialog = new TFindDialogEx(this);
   FFindDialog->OnFind = FindDialogFind;
@@ -776,7 +775,7 @@ void __fastcall TEditorForm::EditorActionsUpdate(TBasicAction *Action,
   {
     SaveAction->Enabled = IsFileModified();
   }
-  else if (Action == SaveAllAction)
+  else if (Action == SaveAllAction2)
   {
     bool Enabled = !FStandaloneEditor;
     if (Enabled)
@@ -788,7 +787,7 @@ void __fastcall TEditorForm::EditorActionsUpdate(TBasicAction *Action,
         FOnAnyModified(this, Enabled);
       }
     }
-    SaveAllAction->Enabled = Enabled;
+    SaveAllAction2->Enabled = Enabled;
   }
   else if (Action == FindNextAction)
   {
@@ -859,7 +858,7 @@ void __fastcall TEditorForm::EditorActionsExecute(TBasicAction *Action,
   {
     SaveFile();
   }
-  else if (Action == SaveAllAction)
+  else if (Action == SaveAllAction2)
   {
     OnSaveAll(this);
   }
@@ -1010,83 +1009,73 @@ void __fastcall TEditorForm::FileUploadComplete()
 //---------------------------------------------------------------------------
 void __fastcall TEditorForm::UpdateControls()
 {
-  if (FShowStatusBarHint)
-  {
-    StatusBar->SimplePanel = true;
-    StatusBar->SimpleText = FStatusBarHint;
-    FCaretPos = TPoint(-1, -1);
-  }
-  else
-  {
-    TPoint ACaretPos = EditorMemo->CaretPos;
+  TPoint ACaretPos = EditorMemo->CaretPos;
 
-    if (ACaretPos.x != FCaretPos.x || ACaretPos.y != FCaretPos.y)
+  if (ACaretPos.x != FCaretPos.x || ACaretPos.y != FCaretPos.y)
+  {
+    FCaretPos = ACaretPos;
+    int Count = EditorMemo->Lines->Count;
+    StatusBar->Panels->Items[0]->Caption = FMTLOAD(EDITOR_LINE_STATUS,
+      ((int)FCaretPos.y+1, Count));
+    int Column = 0;
+    UnicodeString Character;
+    if (FCaretPos.y >= 0 && FCaretPos.y < EditorMemo->Lines->Count)
     {
-      FCaretPos = ACaretPos;
-      int Count = EditorMemo->Lines->Count;
-      StatusBar->Panels->Items[0]->Caption = FMTLOAD(EDITOR_LINE_STATUS,
-        ((int)FCaretPos.y+1, Count));
-      int Column = 0;
-      UnicodeString Character;
-      if (FCaretPos.y >= 0 && FCaretPos.y < EditorMemo->Lines->Count)
+      UnicodeString Line = EditorMemo->Lines->Strings[FCaretPos.y];
+      int TabSize = WinConfiguration->Editor.TabSize;
+      for (int Index = 1; Index <= FCaretPos.x + 1; Index++)
       {
-        UnicodeString Line = EditorMemo->Lines->Strings[FCaretPos.y];
-        int TabSize = WinConfiguration->Editor.TabSize;
-        for (int Index = 1; Index <= FCaretPos.x + 1; Index++)
+        if ((Index - 1 >= 1) && (Index - 1 <= Line.Length()) && (Line[Index - 1] == L'\t') &&
+            (TabSize > 0)) // sanity check
         {
-          if ((Index - 1 >= 1) && (Index - 1 <= Line.Length()) && (Line[Index - 1] == L'\t') &&
-              (TabSize > 0)) // sanity check
-          {
-            Column = (((Column / TabSize) + 1) * TabSize) + 1;
-          }
-          else
-          {
-            Column++;
-          }
+          Column = (((Column / TabSize) + 1) * TabSize) + 1;
         }
+        else
+        {
+          Column++;
+        }
+      }
 
-        if (FCaretPos.x+1 <= Line.Length())
+      if (FCaretPos.x+1 <= Line.Length())
+      {
+        int Code;
+        wchar_t Ch = Line[FCaretPos.x + 1];
+        if (FEncoding == TEncoding::Default)
         {
-          int Code;
-          wchar_t Ch = Line[FCaretPos.x + 1];
-          if (FEncoding == TEncoding::Default)
+          char Buf[10];
+          BOOL UsedDefaultChar = FALSE;
+          int Conversion =
+            WideCharToMultiByte(CP_ACP, WC_NO_BEST_FIT_CHARS, &Ch, 1,
+              Buf, sizeof(Buf), NULL, &UsedDefaultChar);
+          // actually with multibyte encoding it may be > 1,
+          if ((Conversion == 1) && !UsedDefaultChar)
           {
-            char Buf[10];
-            BOOL UsedDefaultChar = FALSE;
-            int Conversion =
-              WideCharToMultiByte(CP_ACP, WC_NO_BEST_FIT_CHARS, &Ch, 1,
-                Buf, sizeof(Buf), NULL, &UsedDefaultChar);
-            // actually with multibyte encoding it may be > 1,
-            if ((Conversion == 1) && !UsedDefaultChar)
-            {
-              Code = static_cast<int>(static_cast<unsigned char>(Buf[0]));
-            }
-            else
-            {
-              Code = -1;
-            }
+            Code = static_cast<int>(static_cast<unsigned char>(Buf[0]));
           }
           else
           {
-            Code = static_cast<int>(Ch);
+            Code = -1;
           }
+        }
+        else
+        {
+          Code = static_cast<int>(Ch);
+        }
 
-          if (Code >= 0)
-          {
-            Character = FMTLOAD(EDITOR_CHARACTER_STATUS2, (Code, Code));
-          }
+        if (Code >= 0)
+        {
+          Character = FMTLOAD(EDITOR_CHARACTER_STATUS2, (Code, Code));
         }
       }
-      StatusBar->Panels->Items[1]->Caption =
-        (Column > 0) ? FMTLOAD(EDITOR_COLUMN_STATUS, (Column)) : UnicodeString();
-      StatusBar->Panels->Items[2]->Caption = Character;
     }
-    StatusBar->Panels->Items[3]->Caption = FMTLOAD(EDITOR_ENCODING_STATUS, (FEncodingName));
-    StatusBar->Panels->Items[4]->Caption =
-      (FSaving ? LoadStr(EDITOR_SAVING) :
-        (IsFileModified() ? LoadStr(EDITOR_MODIFIED) : UnicodeString(L"")));
-    StatusBar->SimplePanel = false;
+    StatusBar->Panels->Items[1]->Caption =
+      (Column > 0) ? FMTLOAD(EDITOR_COLUMN_STATUS, (Column)) : UnicodeString();
+    StatusBar->Panels->Items[2]->Caption = Character;
   }
+  StatusBar->Panels->Items[3]->Caption = FMTLOAD(EDITOR_ENCODING_STATUS, (FEncodingName));
+  StatusBar->Panels->Items[4]->Caption =
+    (FSaving ? LoadStr(EDITOR_SAVING) :
+      (IsFileModified() ? LoadStr(EDITOR_MODIFIED) : UnicodeString(L"")));
 
   EditorActions->UpdateAction(SaveAction);
 }
@@ -1567,28 +1556,6 @@ void __fastcall TEditorForm::Reload()
   }
 }
 //---------------------------------------------------------------------------
-void __fastcall TEditorForm::ApplicationHint(TObject * /*Sender*/)
-{
-  DebugAssert(Application);
-  // Application->Hint contains long hint only
-  UnicodeString AHint = Application->Hint;
-  FShowStatusBarHint = Active && !AHint.IsEmpty();
-  if (FShowStatusBarHint)
-  {
-    FStatusBarHint = AHint;
-  }
-  else
-  {
-    FStatusBarHint = L"";
-  }
-  UpdateControls();
-}
-//---------------------------------------------------------------------------
-void __fastcall TEditorForm::FormActivate(TObject * /*Sender*/)
-{
-  ApplicationEvents->OnHint = ApplicationHint;
-}
-//---------------------------------------------------------------------------
 void __fastcall TEditorForm::FormKeyDown(TObject * /*Sender*/, WORD & Key, TShiftState Shift)
 {
   if (((Key == VK_ESCAPE) || (Key == VK_F10)) && Shift.Empty())

+ 5 - 8
source/forms/Editor.dfm

@@ -1356,7 +1356,6 @@ object EditorForm: TEditorForm
     0000000300000001000000000000000000000010000000390000FFFF0000}
   KeyPreview = True
   OldCreateOrder = False
-  OnActivate = FormActivate
   OnClose = FormClose
   OnCloseQuery = FormCloseQuery
   OnKeyDown = FormKeyDown
@@ -1374,6 +1373,7 @@ object EditorForm: TEditorForm
       Top = 0
       Caption = 'ToolBar'
       Images = EditorImages
+      Options = [tboShowHint]
       ParentShowHint = False
       ShowHint = True
       TabOrder = 0
@@ -1381,7 +1381,7 @@ object EditorForm: TEditorForm
         Action = SaveAction
       end
       object TBXItem1: TTBXItem
-        Action = SaveAllAction
+        Action = SaveAllAction2
       end
       object TBXItem16: TTBXItem
         Action = ReloadAction
@@ -1503,8 +1503,9 @@ object EditorForm: TEditorForm
         'F2')
       ShortCut = 16467
     end
-    object SaveAllAction: TAction
+    object SaveAllAction2: TAction
       Caption = 'Save &All'
+      Hint = 'Save files in all editors'
       ImageIndex = 15
       ShortCut = 24659
     end
@@ -3358,6 +3359,7 @@ object EditorForm: TEditorForm
   end
   object EditorPopup: TTBXPopupMenu
     Images = EditorImages
+    Options = [tboShowHint]
     Left = 464
     Top = 136
     object Undo1: TTBXItem
@@ -9303,9 +9305,4 @@ object EditorForm: TEditorForm
     Top = 272
     Bitmap = {}
   end
-  object ApplicationEvents: TApplicationEvents
-    OnHint = ApplicationHint
-    Left = 464
-    Top = 208
-  end
 end

+ 1 - 6
source/forms/Editor.h

@@ -75,12 +75,11 @@ __published:
   TAction *UTF8EncodingAction;
   TTBXColorItem *ColorItem;
   TAction *ColorAction;
-  TAction *SaveAllAction;
+  TAction *SaveAllAction2;
   TTBXItem *TBXItem1;
   TPngImageList *EditorImages120;
   TPngImageList *EditorImages144;
   TPngImageList *EditorImages192;
-  TApplicationEvents *ApplicationEvents;
   void __fastcall EditorActionsUpdate(TBasicAction *Action, bool &Handled);
   void __fastcall EditorActionsExecute(TBasicAction *Action,
           bool &Handled);
@@ -93,9 +92,7 @@ __published:
   void __fastcall FindDialogFind(TObject *Sender);
   void __fastcall FormShow(TObject *Sender);
   void __fastcall FormClose(TObject *Sender, TCloseAction &Action);
-  void __fastcall FormActivate(TObject *Sender);
   void __fastcall FormKeyDown(TObject *Sender, WORD &Key, TShiftState Shift);
-  void __fastcall ApplicationHint(TObject * Sender);
 private:
   UnicodeString FFileName;
   TNotifyEvent FOnFileChanged;
@@ -110,8 +107,6 @@ private:
   TReplaceDialog * FReplaceDialog;
   bool FCloseAnnounced;
   TRichEdit20 * EditorMemo;
-  bool FShowStatusBarHint;
-  UnicodeString FStatusBarHint;
   bool FFormRestored;
   UnicodeString FWindowParams;
   unsigned int FInstance;

+ 2 - 2
source/forms/Log.dfm

@@ -1397,12 +1397,12 @@ object LogForm: TLogForm
         Action = NonVisualDataModule.LogCopyAction
       end
       object TBXItem4: TTBXItem
-        Action = NonVisualDataModule.LogSelectAllAction
+        Action = NonVisualDataModule.LogSelectAllAction2
       end
       object TBXSeparatorItem2: TTBXSeparatorItem
       end
       object TBXItem5: TTBXItem
-        Action = NonVisualDataModule.LogPreferencesAction
+        Action = NonVisualDataModule.LogPreferencesAction2
       end
     end
   end

+ 4 - 5
source/forms/NonVisual.cpp

@@ -103,10 +103,10 @@ void __fastcall TNonVisualDataModule::LogActionsUpdate(
   bool ValidLogMemo = LogMemo && LogMemo->Parent;
   UPD(LogClearAction, ValidLogMemo && LogMemo->Lines->Count)
   // removed potentially CPU intensive check for "all selected already"
-  UPD(LogSelectAllAction, ValidLogMemo && LogMemo->Lines->Count)
+  UPD(LogSelectAllAction2, ValidLogMemo && LogMemo->Lines->Count)
   UPD(LogCopyAction, ValidLogMemo && LogMemo->SelLength)
 
-  UPD(LogPreferencesAction, true)
+  UPD(LogPreferencesAction2, true)
   ;
 }
 //---------------------------------------------------------------------------
@@ -120,10 +120,10 @@ void __fastcall TNonVisualDataModule::LogActionsExecute(
     TLogMemo * LogMemo = TTerminalManager::Instance()->LogMemo;
     DebugAssert(LogMemo && LogMemo->Parent);
     EXE(LogClearAction, LogMemo->SessionLog->Clear())
-    EXE(LogSelectAllAction, LogMemo->SelectAll())
+    EXE(LogSelectAllAction2, LogMemo->SelectAll())
     EXE(LogCopyAction, LogMemo->CopyToClipboard())
 
-    EXE(LogPreferencesAction, PreferencesDialog(pmLogging));
+    EXE(LogPreferencesAction2, PreferencesDialog(pmLogging));
     ;
   }
 
@@ -1352,7 +1352,6 @@ void __fastcall TNonVisualDataModule::CreateSessionListMenuLevel(
           TTBCustomItem * Item = new TTBXSubmenuItem(Menu);
           Item->Caption = Name;
           Item->Tag = ((Level + 1) << 16) | Index; // MAKELONG
-          Item->Hint = FMTLOAD(SAVEDSESSIONFOLDER_HINT, (Root + Name));
           Item->ImageIndex = SavedSessionsAction2->ImageIndex;
           Item->OnClick = SessionFolderItemClick;
 

+ 19 - 5
source/forms/NonVisual.dfm

@@ -15,10 +15,10 @@ object NonVisualDataModule: TNonVisualDataModule
       ImageIndex = 0
       ShortCut = 16430
     end
-    object LogSelectAllAction: TAction
+    object LogSelectAllAction2: TAction
       Category = 'LogMemo'
       Caption = 'Select &All'
-      Hint = 'Select all'
+      Hint = 'Select all text'
       ImageIndex = 2
       ShortCut = 16449
     end
@@ -29,15 +29,16 @@ object NonVisualDataModule: TNonVisualDataModule
       ImageIndex = 1
       ShortCut = 16451
     end
-    object LogPreferencesAction: TAction
+    object LogPreferencesAction2: TAction
       Category = 'LogForm'
-      Caption = 'LogPreferencesAction'
+      Caption = '&Preferences...'
       Hint = 'Configure logging'
       ImageIndex = 3
     end
   end
   object LogMemoPopup: TTBXPopupMenu
     Images = GlyphsModule.LogImages
+    Options = [tboShowHint]
     Left = 32
     Top = 152
     object Clear1: TTBXItem
@@ -47,11 +48,12 @@ object NonVisualDataModule: TNonVisualDataModule
       Action = LogCopyAction
     end
     object Selectall1: TTBXItem
-      Action = LogSelectAllAction
+      Action = LogSelectAllAction2
     end
   end
   object RemoteFilePopup: TTBXPopupMenu
     Images = GlyphsModule.ExplorerImages
+    Options = [tboShowHint]
     Left = 424
     Top = 336
     object TBXItem23: TTBXItem
@@ -2256,6 +2258,7 @@ object NonVisualDataModule: TNonVisualDataModule
   end
   object ExplorerBarPopup: TTBXPopupMenu
     Images = GlyphsModule.ExplorerImages
+    Options = [tboShowHint]
     Left = 192
     Top = 336
     object Address2: TTBXItem
@@ -2341,6 +2344,7 @@ object NonVisualDataModule: TNonVisualDataModule
   end
   object CommanderBarPopup: TTBXPopupMenu
     Images = GlyphsModule.ExplorerImages
+    Options = [tboShowHint]
     Left = 424
     Top = 264
     object CommandsButtons2: TTBXItem
@@ -2470,6 +2474,7 @@ object NonVisualDataModule: TNonVisualDataModule
   end
   object RemotePanelPopup: TTBXPopupMenu
     Images = GlyphsModule.ExplorerImages
+    Options = [tboShowHint]
     Left = 312
     Top = 264
     object TBXItem32: TTBXItem
@@ -2520,6 +2525,7 @@ object NonVisualDataModule: TNonVisualDataModule
   end
   object LocalPanelPopup: TTBXPopupMenu
     Images = GlyphsModule.ExplorerImages
+    Options = [tboShowHint]
     Left = 312
     Top = 336
     object TBXItem34: TTBXItem
@@ -2570,6 +2576,7 @@ object NonVisualDataModule: TNonVisualDataModule
   end
   object LocalDirViewColumnPopup: TTBXPopupMenu
     Images = GlyphsModule.ExplorerImages
+    Options = [tboShowHint]
     Left = 248
     Top = 88
     object SortAscending1: TTBXItem
@@ -2625,6 +2632,7 @@ object NonVisualDataModule: TNonVisualDataModule
   end
   object RemoteDirViewColumnPopup: TTBXPopupMenu
     Images = GlyphsModule.ExplorerImages
+    Options = [tboShowHint]
     Left = 424
     Top = 88
     object MenuItem1: TTBXItem
@@ -2692,6 +2700,7 @@ object NonVisualDataModule: TNonVisualDataModule
   object QueuePopup: TTBXPopupMenu
     Images = GlyphsModule.ExplorerImages
     OnPopup = QueuePopupPopup
+    Options = [tboShowHint]
     Left = 392
     Top = 176
     object ShowQuery1: TTBXItem
@@ -2805,6 +2814,7 @@ object NonVisualDataModule: TNonVisualDataModule
   object RemoteDirViewPopup: TTBXPopupMenu
     AutoPopup = False
     Images = GlyphsModule.ExplorerImages
+    Options = [tboShowHint]
     Left = 360
     Top = 400
     object GoTo4: TTBXSubmenuItem
@@ -2866,6 +2876,7 @@ object NonVisualDataModule: TNonVisualDataModule
   object LocalDirViewPopup: TTBXPopupMenu
     AutoPopup = False
     Images = GlyphsModule.ExplorerImages
+    Options = [tboShowHint]
     Left = 480
     Top = 400
     object GoTo5: TTBXSubmenuItem
@@ -2926,6 +2937,7 @@ object NonVisualDataModule: TNonVisualDataModule
   end
   object RemoteAddressPopup: TTBXPopupMenu
     Images = GlyphsModule.ExplorerImages
+    Options = [tboShowHint]
     Left = 248
     Top = 400
     object TBXItem33: TTBXItem
@@ -2967,6 +2979,7 @@ object NonVisualDataModule: TNonVisualDataModule
   end
   object SessionsPopup: TTBXPopupMenu
     Images = GlyphsModule.ExplorerImages
+    Options = [tboShowHint]
     Left = 480
     Top = 176
     object TBXItem124: TTBXItem
@@ -3013,6 +3026,7 @@ object NonVisualDataModule: TNonVisualDataModule
   end
   object LocalFilePopup: TTBXPopupMenu
     Images = GlyphsModule.ExplorerImages
+    Options = [tboShowHint]
     Left = 536
     Top = 336
     object LocalOpenMenuItem: TTBXItem

+ 2 - 2
source/forms/NonVisual.h

@@ -75,13 +75,13 @@ class TNonVisualDataModule : public TDataModule
 __published:    // IDE-managed Components
   TActionList *LogActions;
   TAction *LogClearAction;
-  TAction *LogSelectAllAction;
+  TAction *LogSelectAllAction2;
   TAction *LogCopyAction;
   TTBXPopupMenu *LogMemoPopup;
   TTBXItem *Clear1;
   TTBXItem *Close1;
   TTBXItem *Selectall1;
-  TAction *LogPreferencesAction;
+  TAction *LogPreferencesAction2;
   TAction *LocalSortByNameAction;
   TAction *LocalSortAscendingAction;
   TAction *LocalSortBySizeAction;

+ 1 - 1
source/forms/Progress.dfm

@@ -233,7 +233,7 @@ object ProgressForm: TProgressForm
           OnClick = MoveToQueueItemClick
         end
         object CycleOnceDoneItem: TTBXSubmenuItem
-          Caption = 'Once FinishedX'
+          Caption = 'Once Finished'
           DropdownCombo = True
           Hint = 'Action to perform once the operation finishes'
           ImageIndex = 2

+ 8 - 2
source/forms/ScpCommander.cpp

@@ -110,6 +110,7 @@ __fastcall TScpCommanderForm::TScpCommanderForm(TComponent* Owner)
 
   SetShortcuts();
   Splitter->ShowHint = True;
+  LocalPanelSplitter->ShowHint = true;
   reinterpret_cast<TLabel*>(Splitter)->OnDblClick = SplitterDblClick;
   reinterpret_cast<TLabel*>(LocalPanelSplitter)->OnDblClick = PanelSplitterDblClick;
   reinterpret_cast<TLabel*>(RemotePanelSplitter)->OnDblClick = PanelSplitterDblClick;
@@ -782,8 +783,13 @@ void __fastcall TScpCommanderForm::UpdateControls()
   TCustomScpExplorerForm::UpdateControls();
 
   UnicodeString SplitterLongHint = Splitter->Hint;
-  SplitterLongHint.Delete(1, SplitterLongHint.Pos(L"|"));
-  Splitter->Hint = FORMAT(L"%0.0f%%|%s", (LeftPanelWidth*100, SplitterLongHint));
+  int P = SplitterLongHint.Pos(L"|");
+  if (P == 0)
+  {
+    P = SplitterLongHint.Pos(L"\n");
+  }
+  SplitterLongHint.Delete(1, P);
+  Splitter->Hint = FORMAT(L"%0.0f%%\n%s", (LeftPanelWidth*100, SplitterLongHint));
   UnicodeString ACommandLinePromptLabel = LoadStr(COMMAND_LINE_LABEL) + " " +
     ((FCurrentSide == osRemote) ? L"$" : L">");
   if (CommandLinePromptLabel->Caption != ACommandLinePromptLabel)

+ 22 - 0
source/forms/ScpCommander.dfm

@@ -36,6 +36,7 @@ inherited ScpCommanderForm: TScpCommanderForm
       CloseButton = False
       Images = GlyphsModule.ExplorerImages
       MenuBar = True
+      Options = [tboNoAutoHint, tboShowHint]
       ShrinkMode = tbsmWrap
       Stretch = True
       TabOrder = 4
@@ -781,6 +782,7 @@ inherited ScpCommanderForm: TScpCommanderForm
       DockPos = 0
       DockRow = 2
       Images = GlyphsModule.ExplorerImages
+      Options = [tboShowHint]
       ParentShowHint = False
       ShowHint = True
       TabOrder = 1
@@ -817,6 +819,7 @@ inherited ScpCommanderForm: TScpCommanderForm
       DockPos = 0
       DockRow = 1
       Images = GlyphsModule.ExplorerImages
+      Options = [tboShowHint]
       ParentShowHint = False
       ShowHint = True
       TabOrder = 0
@@ -848,6 +851,7 @@ inherited ScpCommanderForm: TScpCommanderForm
       DockPos = -8
       DockRow = 5
       Images = GlyphsModule.ExplorerImages
+      Options = [tboShowHint]
       ParentShowHint = False
       ShowHint = True
       TabOrder = 2
@@ -888,6 +892,7 @@ inherited ScpCommanderForm: TScpCommanderForm
       DockPos = 0
       DockRow = 6
       Images = GlyphsModule.ExplorerImages
+      Options = [tboShowHint]
       ParentShowHint = False
       ShowHint = True
       TabOrder = 3
@@ -922,6 +927,7 @@ inherited ScpCommanderForm: TScpCommanderForm
       DockPos = -7
       DockRow = 7
       Images = GlyphsModule.ExplorerImages
+      Options = [tboShowHint]
       ParentShowHint = False
       ShowHint = True
       TabOrder = 5
@@ -963,6 +969,7 @@ inherited ScpCommanderForm: TScpCommanderForm
       DockPos = 44
       DockRow = 7
       Images = GlyphsModule.ExplorerImages
+      Options = [tboShowHint]
       ParentShowHint = False
       ShowHint = True
       TabOrder = 6
@@ -1107,6 +1114,7 @@ inherited ScpCommanderForm: TScpCommanderForm
         DockPos = -6
         DockRow = 1
         Images = GlyphsModule.ExplorerImages
+        Options = [tboShowHint]
         ParentShowHint = False
         ShowHint = True
         TabOrder = 1
@@ -1126,6 +1134,7 @@ inherited ScpCommanderForm: TScpCommanderForm
         DockPos = 72
         DockRow = 1
         Images = GlyphsModule.ExplorerImages
+        Options = [tboShowHint]
         ParentShowHint = False
         ShowHint = True
         TabOrder = 2
@@ -1161,6 +1170,7 @@ inherited ScpCommanderForm: TScpCommanderForm
         DockMode = dmCannotFloat
         DockPos = 0
         Images = GlyphsModule.ExplorerImages
+        Options = [tboShowHint]
         ParentShowHint = False
         ShowHint = True
         Stretch = True
@@ -1193,6 +1203,7 @@ inherited ScpCommanderForm: TScpCommanderForm
         DockPos = 1
         DockRow = 2
         Images = GlyphsModule.ExplorerImages
+        Options = [tboShowHint]
         ParentShowHint = False
         ShowHint = True
         TabOrder = 3
@@ -1246,6 +1257,7 @@ inherited ScpCommanderForm: TScpCommanderForm
         DockPos = 347
         DockRow = 2
         Images = GlyphsModule.ExplorerImages
+        Options = [tboShowHint]
         ParentShowHint = False
         ShowHint = True
         TabOrder = 4
@@ -1429,6 +1441,7 @@ inherited ScpCommanderForm: TScpCommanderForm
         DockPos = -6
         DockRow = 1
         Images = GlyphsModule.ExplorerImages
+        Options = [tboShowHint]
         ParentShowHint = False
         ShowHint = True
         TabOrder = 1
@@ -1448,6 +1461,7 @@ inherited ScpCommanderForm: TScpCommanderForm
         DockPos = 68
         DockRow = 1
         Images = GlyphsModule.ExplorerImages
+        Options = [tboShowHint]
         ParentShowHint = False
         ShowHint = True
         TabOrder = 2
@@ -1477,6 +1491,7 @@ inherited ScpCommanderForm: TScpCommanderForm
         DockMode = dmCannotFloat
         DockPos = 0
         Images = GlyphsModule.ExplorerImages
+        Options = [tboShowHint]
         ParentShowHint = False
         ShowHint = True
         Stretch = True
@@ -1507,6 +1522,7 @@ inherited ScpCommanderForm: TScpCommanderForm
         DockPos = 0
         DockRow = 2
         Images = GlyphsModule.ExplorerImages
+        Options = [tboShowHint]
         ParentShowHint = False
         ShowHint = True
         TabOrder = 3
@@ -1560,6 +1576,7 @@ inherited ScpCommanderForm: TScpCommanderForm
         DockPos = 329
         DockRow = 2
         Images = GlyphsModule.ExplorerImages
+        Options = [tboShowHint]
         ParentShowHint = False
         ShowHint = True
         TabOrder = 4
@@ -1622,6 +1639,7 @@ inherited ScpCommanderForm: TScpCommanderForm
       DockPos = 0
       DockRow = 1
       Images = GlyphsModule.ExplorerImages
+      Options = [tboShowHint]
       ParentShowHint = False
       ShowHint = False
       Stretch = True
@@ -1748,4 +1766,8 @@ inherited ScpCommanderForm: TScpCommanderForm
     BevelKind = bkFlat
     TabOrder = 7
   end
+  inherited ApplicationEvents: TApplicationEvents
+    Left = 72
+    Top = 352
+  end
 end

+ 9 - 0
source/forms/ScpExplorer.dfm

@@ -24,6 +24,7 @@ inherited ScpExplorerForm: TScpExplorerForm
       CloseButton = False
       Images = GlyphsModule.ExplorerImages
       MenuBar = True
+      Options = [tboNoAutoHint, tboShowHint]
       ShrinkMode = tbsmWrap
       Stretch = True
       TabOrder = 0
@@ -593,6 +594,7 @@ inherited ScpExplorerForm: TScpExplorerForm
       DockPos = -8
       DockRow = 2
       Images = GlyphsModule.ExplorerImages
+      Options = [tboShowHint]
       ParentShowHint = False
       ShowHint = True
       TabOrder = 2
@@ -694,6 +696,7 @@ inherited ScpExplorerForm: TScpExplorerForm
       DockPos = -4
       DockRow = 3
       Images = GlyphsModule.ExplorerImages
+      Options = [tboShowHint]
       ParentShowHint = False
       ShowHint = True
       TabOrder = 3
@@ -725,6 +728,7 @@ inherited ScpExplorerForm: TScpExplorerForm
       DockPos = -4
       DockRow = 4
       Images = GlyphsModule.ExplorerImages
+      Options = [tboShowHint]
       ParentShowHint = False
       ShowHint = True
       TabOrder = 4
@@ -756,6 +760,7 @@ inherited ScpExplorerForm: TScpExplorerForm
       DockPos = -4
       DockRow = 5
       Images = GlyphsModule.ExplorerImages
+      Options = [tboShowHint]
       ParentShowHint = False
       ShowHint = True
       TabOrder = 5
@@ -811,6 +816,7 @@ inherited ScpExplorerForm: TScpExplorerForm
       DockPos = 0
       DockRow = 6
       Images = GlyphsModule.ExplorerImages
+      Options = [tboShowHint]
       ParentShowHint = False
       ShowHint = True
       TabOrder = 6
@@ -854,6 +860,7 @@ inherited ScpExplorerForm: TScpExplorerForm
       DockPos = -8
       DockRow = 1
       Images = GlyphsModule.ExplorerImages
+      Options = [tboShowHint]
       ParentShowHint = False
       PopupMenu = NonVisualDataModule.RemoteAddressPopup
       Resizable = False
@@ -893,6 +900,7 @@ inherited ScpExplorerForm: TScpExplorerForm
       DockPos = -7
       DockRow = 7
       Images = GlyphsModule.ExplorerImages
+      Options = [tboShowHint]
       ParentShowHint = False
       ShowHint = True
       TabOrder = 7
@@ -934,6 +942,7 @@ inherited ScpExplorerForm: TScpExplorerForm
       DockPos = 44
       DockRow = 7
       Images = GlyphsModule.ExplorerImages
+      Options = [tboShowHint]
       ParentShowHint = False
       ShowHint = True
       TabOrder = 8

+ 35 - 4
source/packages/tb2k/TB2Item.pas

@@ -701,6 +701,7 @@ type
     FAnimationDirection: TTBAnimationDirection;
     FView: TTBView;
     procedure CMHintShow(var Message: TCMHintShow); message CM_HINTSHOW;
+    procedure CMHintShowPause(var Message: TMessage); message CM_HINTSHOWPAUSE;
     procedure CMShowingChanged(var Message: TMessage); message CM_SHOWINGCHANGED;
     procedure WMClose(var Message: TWMClose); message WM_CLOSE;
     procedure WMEraseBkgnd(var Message: TWMEraseBkgnd); message WM_ERASEBKGND;
@@ -2743,15 +2744,27 @@ begin
 end;
 
 function TTBItemViewer.GetHintText: String;
-var P: Integer;
+var
+  P: Integer;
+  LongHint: string;
+  HintStyleCaption: string;
 begin
-  Result := GetShortHint(Item.Hint);
+  if Pos('|', Item.Hint) > 0 then
+  begin
+    Result := GetShortHint(Item.Hint);
+    LongHint := GetLongHint(Item.Hint);
+  end
+    else
+  begin
+    LongHint := Item.Hint;
+  end;
+  HintStyleCaption := StripAccelChars(StripTrailingPunctuation(GetCaptionText));
   { If there is no short hint, use the caption for the hint. Like Office,
     strip any trailing colon or ellipsis. }
-  if (Result = '') and not(tboNoAutoHint in Item.EffectiveOptions) and
+  if (Result = '') and (not(tboNoAutoHint in Item.EffectiveOptions) or (LongHint <> '')) and
      (not(tbisSubmenu in Item.ItemStyle) or (tbisCombo in Item.ItemStyle) or
       not CaptionShown) then
-    Result := StripAccelChars(StripTrailingPunctuation(GetCaptionText));
+    Result := HintStyleCaption;
   { Call associated action's OnHint event handler to post-process the hint }
   if Assigned(Item.ActionLink) and
      (Item.ActionLink.Action is TCustomAction) then begin
@@ -2760,6 +2773,13 @@ begin
     { Note: TControlActionLink.DoShowHint actually misinterprets the result
       of DoHint, but we get it right... }
   end;
+  if Result = '' then
+    Result := LongHint;
+  // "Select all" and "Select All" are still the same
+  if SameText(LongHint, Result) then
+    LongHint := '';
+  if CaptionShown and (LongHint = '') and SameText(Result, HintStyleCaption) then
+    Result := '';
   { Add shortcut text }
   if (Result <> '') and Application.HintShortCuts then
   begin
@@ -2771,6 +2791,8 @@ begin
       if (Item.ShortCut <> scNone) then
         Result := Format('%s (%s)', [Result, ShortCutToText(Item.ShortCut)]);
   end;
+  if LongHint <> '' then
+    Result := Result + '|' + GetLongHint(LongHint);
 end;
 
 function TTBItemViewer.CaptionShown: Boolean;
@@ -6673,6 +6695,15 @@ begin
   end;
 end;
 
+procedure TTBPopupWindow.CMHintShowPause(var Message: TMessage);
+begin
+  // Hint was not active previously
+  if not Boolean(Message.WParam) then
+  begin
+    PInteger(Message.LParam)^ := PInteger(Message.LParam)^ * 2;
+  end;
+end;
+
 
 { TTBItemContainer }
 

+ 5 - 0
source/packages/tb2k/TB2Toolbar.pas

@@ -286,6 +286,7 @@ type
   protected
     procedure Paint(const Canvas: TCanvas; const ClientAreaRect: TRect;
       IsSelected, IsPushed, UseDisabledShadow: Boolean); override;
+    function CaptionShown: Boolean; override;
   end;
 
 const
@@ -447,6 +448,10 @@ begin
   end;
 end;
 
+function TTBChevronItemViewer.CaptionShown: Boolean;
+begin
+  Result := False;
+end;
 
 { TTBToolbarView }
 

+ 6 - 0
source/packages/tbx/TBX.pas

@@ -468,6 +468,7 @@ type
   protected
     procedure Paint(const Canvas: TCanvas; const ClientAreaRect: TRect;
       IsHoverItem, IsPushed, UseDisabledShadow: Boolean); override;
+    function CaptionShown: Boolean; override;
   end;
 
   TTBXChevronPopupWindow = class(TTBXPopupWindow);
@@ -2932,6 +2933,11 @@ begin
   CurrentTheme.PaintChevron(Canvas, ClientAreaRect, ItemInfo);
 end;
 
+function TTBXChevronItemViewer.CaptionShown: Boolean;
+begin
+  Result := False;
+end;
+
 
 //============================================================================//
 

+ 0 - 1
source/resource/TextsWin.h

@@ -448,7 +448,6 @@
 #define LOGIN_DELETE_SPECIAL_SESSION 1811
 #define LOGIN_NEW_SESSION_FOLDER_CAPTION 1812
 #define LOGIN_NEW_SESSION_FOLDER_PROMPT 1813
-#define SAVEDSESSIONFOLDER_HINT 1814
 #define ABOUT_REGISTRATION_LINK 1815
 #define REMOTE_TRANSFER_PROMPT2 1816
 #define REMOTE_COPY_COMMAND_SESSION2 1817

+ 0 - 1
source/resource/TextsWin1.rc

@@ -452,7 +452,6 @@ BEGIN
         LOGIN_DELETE_SPECIAL_SESSION, "Cannot delete special site '%s'."
         LOGIN_NEW_SESSION_FOLDER_CAPTION, "Create Site Folder"
         LOGIN_NEW_SESSION_FOLDER_PROMPT, "New folder name:"
-        SAVEDSESSIONFOLDER_HINT, "Open site folder '%s'"
         ABOUT_REGISTRATION_LINK, "How to purchase a license..."
         REMOTE_COPY_COMMAND_SESSION2, "**Do you want to open separate shell session to duplicate the file(s)?**\n \nCurrent session does not support direct duplication of remote files. Separate shell session may be opened to process the duplication. Alternatively your may duplicate the file(s) via local temporary copy."
         EDITOR_AD_HOC, "Editor"

+ 162 - 0
source/windows/GUITools.cpp

@@ -22,6 +22,7 @@
 #include <Animations.h>
 #include <PasTools.hpp>
 #include <VCLCommon.h>
+#include <Vcl.ScreenTips.hpp>
 //---------------------------------------------------------------------------
 #pragma package(smart_init)
 //---------------------------------------------------------------------------
@@ -1139,3 +1140,164 @@ void __fastcall TFrameAnimation::CalculateNextFrameTick()
   FNextFrameTick += StrToInt(Duration) * 10;
 }
 //---------------------------------------------------------------------------
+//---------------------------------------------------------------------------
+// Hints use:
+// - Cleanup list tooltip (multi line)
+// - Combo edit button
+// - Transfer settings label (multi line, follows label size and font)
+// - HintLabel (hint and persistent hint, multipline)
+// - status bar hints
+//---------------------------------------------------------------------------
+__fastcall TScreenTipHintWindow::TScreenTipHintWindow(TComponent * Owner) :
+  THintWindow(Owner)
+{
+  FParentPainting = false;
+  FMargin = ScaleByPixelsPerInch(6);
+}
+//---------------------------------------------------------------------------
+int __fastcall TScreenTipHintWindow::GetTextFlags()
+{
+  return DT_LEFT | DT_WORDBREAK | DT_NOPREFIX | DrawTextBiDiModeFlagsReadingOnly();
+}
+//---------------------------------------------------------------------------
+bool __fastcall TScreenTipHintWindow::UseBoldShortHint(TControl * HintControl)
+{
+  return
+    (dynamic_cast<TTBCustomDockableWindow *>(HintControl) != NULL) ||
+    (dynamic_cast<TTBPopupWindow *>(HintControl) != NULL);
+}
+//---------------------------------------------------------------------------
+TRect __fastcall TScreenTipHintWindow::CalcHintRect(int MaxWidth, const UnicodeString AHint, void * AData)
+{
+  const UnicodeString ShortHint = GetShortHint(AHint);
+  const UnicodeString LongHint = GetLongHintIfAny(AHint);
+
+  // we do not have a parent form here, so we cannot scale by text height
+  const int ScreenTipTextOnlyWidth = ScaleByPixelsPerInch(cScreenTipTextOnlyWidth);
+
+  if (!LongHint.IsEmpty())
+  {
+    // double-margin on the right
+    MaxWidth = ScreenTipTextOnlyWidth - (3 * FMargin);
+  }
+
+  const int Flags = DT_CALCRECT | GetTextFlags();
+
+  // Multi line short hints can be twice as wide, to not break the individual lines unless really necessary.
+  // (login site tree, clean up dialog list, preferences custom command list, persistent hint, etc).
+  // And they also can be twice as wide, to not break the individual lines unless really necessary.
+  if (ShortHint.Pos(L"\n") > 0)
+  {
+    MaxWidth *= 2;
+  }
+
+  if (UseBoldShortHint(GetHintControl(AData)))
+  {
+    Canvas->Font->Style = TFontStyles() << fsBold;
+  }
+  TRect ShortRect(0, 0, MaxWidth, 0);
+  DrawText(Canvas->Handle, ShortHint.c_str(), -1, &ShortRect, Flags);
+  Canvas->Font->Style = TFontStyles();
+
+  TRect Result;
+
+  if (LongHint.IsEmpty())
+  {
+    Result = ShortRect;
+    Result.Right += 3 * FMargin;
+    Result.Bottom += 2 * FMargin;
+  }
+  else
+  {
+    const int LongIndentation = FMargin * 3 / 2;
+    TRect LongRect(0, 0, MaxWidth - LongIndentation, 0);
+    DrawText(Canvas->Handle, LongHint.c_str(), -1, &LongRect, Flags);
+
+    Result.Right = ScreenTipTextOnlyWidth;
+    Result.Bottom = FMargin + ShortRect.Height() + (FMargin / 3 * 5) + LongRect.Height() + FMargin;
+  }
+
+  // To counter the increase in THintWindow::ActivateHintData
+  Result.Bottom -= 4;
+
+  return Result;
+}
+//---------------------------------------------------------------------------
+void __fastcall TScreenTipHintWindow::ActivateHintData(const TRect & ARect, const UnicodeString AHint, void * AData)
+{
+  FShortHint = GetShortHint(AHint);
+  FLongHint = GetLongHintIfAny(AHint);
+  FHintControl = GetHintControl(AData);
+
+  THintWindow::ActivateHintData(ARect, FShortHint, AData);
+}
+//---------------------------------------------------------------------------
+TControl * __fastcall TScreenTipHintWindow::GetHintControl(void * Data)
+{
+  return reinterpret_cast<TControl *>(DebugNotNull(Data));
+}
+//---------------------------------------------------------------------------
+UnicodeString __fastcall TScreenTipHintWindow::GetLongHintIfAny(const UnicodeString & AHint)
+{
+  UnicodeString Result;
+  int P = Pos(L"|", AHint);
+  if (P > 0)
+  {
+    Result = GetLongHint(AHint);
+  }
+  return Result;
+}
+//---------------------------------------------------------------------------
+void __fastcall TScreenTipHintWindow::Dispatch(void * AMessage)
+{
+  TMessage * Message = static_cast<TMessage*>(AMessage);
+  switch (Message->Msg)
+  {
+    case WM_GETTEXTLENGTH:
+      if (FParentPainting)
+      {
+        // make THintWindow::Paint() not paint the Caption
+        Message->Result = 0;
+      }
+      else
+      {
+        THintWindow::Dispatch(AMessage);
+      }
+      break;
+
+    default:
+      THintWindow::Dispatch(AMessage);
+      break;
+  }
+}
+//---------------------------------------------------------------------------
+void __fastcall TScreenTipHintWindow::Paint()
+{
+  // paint frame/background
+  {
+    TAutoFlag ParentPaintingFlag(FParentPainting);
+    THintWindow::Paint();
+  }
+
+  const int Flags = GetTextFlags();
+  const int Margin = FMargin - 1; // 1 = border
+
+  TRect Rect = ClientRect;
+  Rect.Inflate(-Margin, -Margin);
+  Rect.Right -= FMargin;
+  if (UseBoldShortHint(FHintControl))
+  {
+    Canvas->Font->Style = TFontStyles() << fsBold;
+  }
+  DrawText(Canvas->Handle, FShortHint.c_str(), -1, &Rect, Flags);
+  TRect ShortRect = Rect;
+  DrawText(Canvas->Handle, FShortHint.c_str(), -1, &ShortRect, DT_CALCRECT | Flags);
+  Canvas->Font->Style = TFontStyles();
+
+  if (!FLongHint.IsEmpty())
+  {
+    Rect.Left += FMargin * 3 / 2;
+    Rect.Top += ShortRect.Height() + (FMargin / 3 * 5);
+    DrawText(Canvas->Handle, FLongHint.c_str(), -1, &Rect, Flags);
+  }
+}

+ 24 - 0
source/windows/GUITools.h

@@ -119,6 +119,30 @@ private:
   void __fastcall Repaint();
 };
 //---------------------------------------------------------------------------
+class TScreenTipHintWindow : public THintWindow
+{
+public:
+  __fastcall TScreenTipHintWindow(TComponent * Owner);
+  virtual TRect __fastcall CalcHintRect(int MaxWidth, const UnicodeString AHint, void * AData);
+  virtual void __fastcall ActivateHintData(const TRect & Rect, const UnicodeString AHint, void * AData);
+
+protected:
+  virtual void __fastcall Paint();
+  virtual void __fastcall Dispatch(void * AMessage);
+
+private:
+  bool FParentPainting;
+  int FMargin;
+  UnicodeString FShortHint;
+  UnicodeString FLongHint;
+  TControl * FHintControl;
+
+  UnicodeString __fastcall GetLongHintIfAny(const UnicodeString & AHint);
+  int __fastcall GetTextFlags();
+  bool __fastcall UseBoldShortHint(TControl * HintControl);
+  TControl * __fastcall GetHintControl(void * Data);
+};
+//---------------------------------------------------------------------------
 extern const UnicodeString PageantTool;
 extern const UnicodeString PuttygenTool;
 //---------------------------------------------------------------------------

+ 1 - 0
source/windows/TerminalManager.cpp

@@ -756,6 +756,7 @@ void __fastcall TTerminalManager::ApplicationException(TObject * /*Sender*/,
 void __fastcall TTerminalManager::ApplicationShowHint(UnicodeString & HintStr,
   bool & /*CanShow*/, THintInfo & HintInfo)
 {
+  HintInfo.HintData = HintInfo.HintControl;
   TLabel * HintLabel = dynamic_cast<TLabel *>(HintInfo.HintControl);
   if ((HintLabel != NULL) && (HintLabel->Caption == HintStr))
   {

+ 1 - 1
source/windows/VCLCommon.cpp

@@ -1567,7 +1567,7 @@ void __fastcall ShowPersistentHint(TControl * Control, TPoint HintPos)
   {
     PersistentHintControl = Control;
 
-    PersistentHintWindow = new THintWindow(Application);
+    PersistentHintWindow = new TScreenTipHintWindow(Application);
     PersistentHintWindow->BiDiMode = Control->BiDiMode;
     PersistentHintWindow->Color = HintInfo.HintColor;
 

+ 1 - 0
source/windows/WinMain.cpp

@@ -704,6 +704,7 @@ int __fastcall Execute()
     // Some applications use an infinite (Thunderbird, Firefox).
     // Overriden for some controls using THintInfo.HideTimeout
     Application->HintHidePause = 20000;
+    HintWindowClass = __classid(TScreenTipHintWindow);
 
     UnicodeString IniFileName = Params->SwitchValue(INI_SWITCH);
     if (!IniFileName.IsEmpty())